# rd_api_injector.py
# Minimal RD API Key Injector for Kodi add-on
# Put this file in your addon modules folder and import/run from your menu.

import xbmc
import xbmcgui
import xbmcaddon
import xbmcvfs
import os
import re

ADDON = xbmcaddon.Addon(id="plugin.program.rdtplayer")  # change if your addon id differs
SETTING_KEY_ID = "api_key"  # matches your settings.xml. See settings.xml id: api_key. :contentReference[oaicite:1]{index=1}

def _read_key_from_file(path):
    """Read first non-empty line from a text file (trimmed). Returns None on error/empty."""
    try:
        if not xbmcvfs.exists(path):
            xbmc.log(f"[RD-INJECT] file not found: {path}", xbmc.LOGWARNING)
            return None
        # use xbmcvfs to support Kodi paths
        with xbmcvfs.File(path, 'r') as f:
            for raw in f.read().splitlines():
                line = raw.strip()
                if line:
                    return line
    except Exception as e:
        xbmc.log(f"[RD-INJECT] error reading file {path}: {e}", xbmc.LOGERROR)
    return None

def _validate_key_candidate(key):
    """Basic sanity checks: length and allowed chars. Adjust regex/length to your token format."""
    if not key:
        return False, "Empty key"
    # Most RD tokens are long alphanumeric; allow hyphens too if needed
    if len(key) < 8:
        return False, "Key too short"
    if not re.match(r'^[A-Za-z0-9\-_]+$', key):
        return False, "Key has invalid characters"
    return True, ""

def _confirm_and_save_key(key):
    """Ask the user to confirm overwrite and save via xbmc addon settings API."""
    old = ADDON.getSettingString(SETTING_KEY_ID) or ""
    if old:
        confirm = xbmcgui.Dialog().yesno("RD API Injector",
                                         "Replace existing Real-Debrid API token?\n\nExisting (partial):\n" +
                                         (old[:6] + "..." + old[-4:] if len(old) > 10 else old),
                                         yeslabel="Replace", nolabel="Cancel")
        if not confirm:
            xbmcgui.Dialog().notification("RD API Injector", "Cancelled — key not changed", xbmcgui.NOTIFICATION_INFO, 2500)
            return False

    ADDON.setSettingString(SETTING_KEY_ID, key)
    xbmc.log(f"[RD-INJECT] Real-Debrid API key updated (stored in settings).", xbmc.LOGINFO)
    xbmcgui.Dialog().notification("RD API Injector", "API key injected and saved", xbmcgui.NOTIFICATION_INFO, 3000)
    return True

def choose_textfile_and_inject():
    """Allow user to choose a local text file and inject the first non-empty line as the API key."""
    kb = xbmcgui.Dialog()
    start_dir = xbmcvfs.translatePath("special://profile/")  # polite default; change if you prefer
    path = kb.browse(1, "Select text file containing your RD API key", "files", ".txt|.key|.conf|.json", False, False, start_dir)
    if not path:
        xbmcgui.Dialog().notification("RD API Injector", "No file selected", xbmcgui.NOTIFICATION_INFO, 2000)
        return False

    # Some systems return windows paths; normalize
    path = xbmcvfs.translatePath(path)
    key = _read_key_from_file(path)
    if not key:
        xbmcgui.Dialog().notification("RD API Injector", "No key found in file", xbmcgui.NOTIFICATION_ERROR, 3500)
        return False

    ok, why = _validate_key_candidate(key)
    if not ok:
        xbmcgui.Dialog().yesno("RD API Injector", f"Key looks suspicious: {why}\n\nUse anyway?", yeslabel="Yes, save", nolabel="No, cancel") \
            and _confirm_and_save_key(key)
        return True

    return _confirm_and_save_key(key)

def paste_manual_and_inject():
    """Ask the user to paste/type their API key and inject it."""
    keyboard = xbmc.Keyboard("", "Paste or type your Real-Debrid API token")
    keyboard.doModal()
    if not keyboard.isConfirmed():
        xbmcgui.Dialog().notification("RD API Injector", "Cancelled", xbmcgui.NOTIFICATION_INFO, 1500)
        return False
    key = keyboard.getText().strip()
    ok, why = _validate_key_candidate(key)
    if not ok:
        # warn but allow override
        if not xbmcgui.Dialog().yesno("RD API Injector", f"Key looks suspicious: {why}\n\nSave anyway?", yeslabel="Save", nolabel="Cancel"):
            return False
    return _confirm_and_save_key(key)

def run_ui():
    """Small two-option UI: choose file or paste key."""
    dialog = xbmcgui.Dialog()
    choice = dialog.select("RD API Key Injector", ["Paste / Type API key", "Load key from text file", "Show current key (partial)"])
    if choice == 0:
        paste_manual_and_inject()
    elif choice == 1:
        choose_textfile_and_inject()
    elif choice == 2:
        current = ADDON.getSettingString(SETTING_KEY_ID) or "(not set)"
        snippet = current if len(current) <= 20 else (current[:8] + "..." + current[-6:])
        xbmcgui.Dialog().ok("Current RD API Key (partial)", snippet)
    else:
        # cancel / closed
        return

# Example: If you want to wire into router, call run_ui() from your menu action.
if __name__ == "__main__":
    run_ui()
