#!/usr/bin/env python3
import sys
import os
import json
import subprocess
import urllib.request
import xml.etree.ElementTree as ET

CONFIG_DIR = os.path.expanduser("~/.config/ys")
CONFIG_FILE = os.path.join(CONFIG_DIR, "config.json")
BASE_SYNC_DIR = os.path.expanduser("~/YS_Shared_Folders")
ST_CONFIG_PATH = os.path.expanduser("~/.config/syncthing/config.xml")

def load_config():
    if not os.path.exists(CONFIG_FILE):
        os.makedirs(CONFIG_DIR, exist_ok=True)
        return {"notifications": True}
    with open(CONFIG_FILE, "r") as f:
        try: return json.load(f)
        except: return {"notifications": True}

def save_config(config):
    with open(CONFIG_FILE, "w") as f:
        json.dump(config, f)

def get_syncthing_info():
    """Extracts the local Syncthing API Key and Device ID directly from its config XML."""
    if not os.path.exists(ST_CONFIG_PATH):
        # Force syncthing to generate configs if running for the first time
        subprocess.run(["syncthing", "--generate=" + os.path.expanduser("~/.config/syncthing")], stdout=subprocess.DEVNULL)
    
    try:
        tree = ET.parse(ST_CONFIG_PATH)
        root = tree.getroot()
        api_key = root.find(".//apikey").text
        
        # Get Device ID
        result = subprocess.run(["syncthing", "--device-id"], capture_output=True, text=True, check=True)
        return api_key, result.stdout.strip()
    except Exception:
        return None, None

def syncthing_api_post(endpoint, data, api_key):
    """Sends a configuration update to the local Syncthing daemon."""
    url = f"http://localhost:8384/rest/{endpoint}"
    req = urllib.request.Request(url, data=json.dumps(data).encode('utf-8'), method='POST')
    req.add_header('X-API-Key', api_key)
    req.add_header('Content-Type', 'application/json')
    try:
        with urllib.request.urlopen(req) as response:
            return response.read()
    except Exception as e:
        return None

def main():
    if len(sys.argv) < 2:
        print("Usage: ys [create|connect|settings]")
        sys.exit(1)

    cmd = sys.argv[1].lower()
    api_key, my_id = get_syncthing_info()

    if cmd == "create":
        if len(sys.argv) < 3:
            print("Usage: ys create <folderName>")
            sys.exit(1)
        
        folder_name = sys.argv[2]
        target_path = os.path.join(BASE_SYNC_DIR, folder_name)
        os.makedirs(target_path, exist_ok=True)
        
        print(f"🛠️  Created folder locally at: {target_path}")
        print(f"📢  Your YS Server ID is: {my_id}")
        print("\nShare this exact ID with your friend so they can join!")
        
        # Spin up background engines
        subprocess.Popen(["syncthing", "--no-browser"], stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL)
        subprocess.Popen(["ys-watcher", target_path, folder_name], stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL)

    elif cmd == "connect":
        if len(sys.argv) < 3:
            print("Usage: ys connect <Server_ID>")
            sys.exit(1)
            
        server_id = sys.argv[2]
        room_short = server_id[:6]
        friend_folder = os.path.join(BASE_SYNC_DIR, f"shared_{room_short}")
        os.makedirs(friend_folder, exist_ok=True)
        
        print(f"🔗 Connecting to YS Server ID: {server_id}")
        
        if api_key:
            # 1. Tell local Syncthing to trust your friend's machine ID
            device_data = {"deviceID": server_id, "name": f"Friend_{room_short}", "addresses": ["dynamic"]}
            syncthing_api_post("config/devices", device_data, api_key)
            
            # 2. Map the folder to sync with them automatically
            folder_data = {
                "id": f"ys_shared_{room_short}",
                "path": friend_folder,
                "devices": [{"deviceID": my_id}, {"deviceID": server_id}]
            }
            syncthing_api_post("config/folders", folder_data, api_key)
        
        # Ensure sync & watcher processes are fully active
        subprocess.Popen(["syncthing", "--no-browser"], stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL)
        subprocess.Popen(["ys-watcher", friend_folder, f"Shared Room ({room_short})"], stdout=subprocess.DEVNULL, stderr=subprocess.DEVNULL)
        
        print(f"📁 Mirror folder live at: {friend_folder}")
        os.system(f'notify-send "YS Connected" "Now syncing with room {room_short}"')

    elif cmd == "settings":
        if len(sys.argv) < 3:
            print("Usage: ys settings [+notifications|-notifications]")
            sys.exit(1)
            
        action = sys.argv[2]
        config = load_config()
        
        if action == "+notifications":
            config["notifications"] = True
            save_config(config)
            print("Exported: 🔔 Notifications turned ON.")
        elif action == "-notifications":
            config["notifications"] = False
            save_config(config)
            print("Exported: 🔕 Notifications turned OFF.")
        else:
            print("❌ Invalid setting option. Use +notifications or -notifications.")
    else:
        print(f"❌ Unknown command: {cmd}")

if __name__ == "__main__":
    main()

