117 lines
4.6 KiB
Python
117 lines
4.6 KiB
Python
#!/usr/bin/env python3
|
||
"""
|
||
Script to mimic the web UI call when hitting "Save Garmin Credentials".
|
||
This script loads Garmin credentials from a .env file and sends them to the backend API.
|
||
"""
|
||
|
||
import os
|
||
import requests
|
||
import json
|
||
from dotenv import load_dotenv
|
||
import sys
|
||
|
||
# Load environment variables from .env file
|
||
load_dotenv()
|
||
|
||
def save_garmin_credentials():
|
||
# Get credentials from environment variables
|
||
garmin_username = os.getenv('GARMIN_USERNAME')
|
||
garmin_password = os.getenv('GARMIN_PASSWORD')
|
||
garmin_is_china = os.getenv('GARMIN_IS_CHINA', 'false').lower() == 'true'
|
||
|
||
if not garmin_username or not garmin_password:
|
||
print("Error: GARMIN_USERNAME and GARMIN_PASSWORD must be set in the .env file")
|
||
return False
|
||
|
||
# Backend API details
|
||
backend_host = os.getenv('BACKEND_HOST', 'localhost')
|
||
backend_port = os.getenv('BACKEND_PORT', '8000')
|
||
|
||
# Construct the API endpoint URL
|
||
api_url = f"http://{backend_host}:{backend_port}/api/setup/garmin"
|
||
|
||
# Prepare the payload
|
||
payload = {
|
||
"username": garmin_username,
|
||
"password": garmin_password,
|
||
"is_china": garmin_is_china
|
||
}
|
||
|
||
headers = {
|
||
"Content-Type": "application/json"
|
||
}
|
||
|
||
print(f"Sending Garmin credentials to: {api_url}")
|
||
print(f"Username: {garmin_username}")
|
||
print(f"Is China: {garmin_is_china}")
|
||
|
||
try:
|
||
# Make the POST request to the API endpoint
|
||
response = requests.post(api_url, json=payload, headers=headers, timeout=30)
|
||
|
||
print(f"Response Status Code: {response.status_code}")
|
||
|
||
if response.status_code == 200:
|
||
response_data = response.json()
|
||
print(f"Response: {json.dumps(response_data, indent=2)}")
|
||
|
||
if response_data.get("status") == "success":
|
||
print("✓ Garmin credentials saved and authenticated successfully!")
|
||
return True
|
||
elif response_data.get("status") == "mfa_required":
|
||
print("ℹ Multi-factor authentication required!")
|
||
session_id = response_data.get("session_id")
|
||
print(f"MFA Session ID: {session_id}")
|
||
return "mfa_required" # Return special value to indicate MFA required
|
||
else:
|
||
print(f"⚠ Unexpected response status: {response_data.get('status')}")
|
||
return False
|
||
else:
|
||
print(f"Error Response: {response.text}")
|
||
|
||
# Provide helpful error messages based on common issues
|
||
if response.status_code == 500:
|
||
error_resp = response.json() if response.content else {}
|
||
error_msg = error_resp.get('message', '')
|
||
|
||
if 'could not translate host name "db" to address' in error_msg:
|
||
print("\nNote: This error occurs when the database container is not running.")
|
||
print("You might need to start the full stack with Docker Compose:")
|
||
print(" docker-compose up -d")
|
||
elif 'Invalid credentials' in error_msg or 'Authentication' in error_msg:
|
||
print("\nNote: Invalid Garmin username or password. Please check your credentials.")
|
||
elif 'MFA' in error_msg or 'mfa' in error_msg:
|
||
print("\nNote: Multi-factor authentication required.")
|
||
|
||
return False
|
||
|
||
except requests.exceptions.ConnectionError:
|
||
print(f"❌ Error: Could not connect to the backend at {api_url}")
|
||
print("Make sure the backend service is running on the specified host and port.")
|
||
print("\nTo start the backend service:")
|
||
print(" cd backend")
|
||
print(" docker-compose up -d")
|
||
return False
|
||
except requests.exceptions.Timeout:
|
||
print(f"❌ Error: Request timed out. The backend at {api_url} might be slow to respond or unavailable.")
|
||
return False
|
||
except requests.exceptions.RequestException as e:
|
||
print(f"❌ Request failed: {str(e)}")
|
||
return False
|
||
except json.JSONDecodeError:
|
||
print(f"❌ Error: Could not parse the response from the server.")
|
||
print(f"Raw response: {response.text}")
|
||
return False
|
||
|
||
if __name__ == "__main__":
|
||
result = save_garmin_credentials()
|
||
|
||
if result is True:
|
||
print("\n✓ Script executed successfully")
|
||
sys.exit(0)
|
||
elif result == "mfa_required":
|
||
print("\n✓ Script executed successfully (MFA required)")
|
||
sys.exit(0) # Exit with success code since this is expected behavior
|
||
else:
|
||
print("\n❌ Script execution failed")
|
||
sys.exit(1) |