#!/usr/bin/env python3
"""
Simple HTTP server that exposes the generated Jellyfin plugin repository.

Jellyfin Dashboard -> Plugins -> Repositories -> Add:
    http://localhost:8097/jellyfin-plugin-repo.json

Run:
    python3 serve_repo.py

Environment variables:
    REPO_BIND_HOST   interface to bind to (default: 0.0.0.0)
    REPO_PUBLIC_HOST hostname used in manifest sourceUrls (default: localhost)
    REPO_PORT        port to listen on (default: 8097)
"""

import json
import os
import sys
from http.server import HTTPServer, SimpleHTTPRequestHandler
from pathlib import Path

BIND_HOST = os.environ.get("REPO_BIND_HOST", "0.0.0.0")
PUBLIC_HOST = os.environ.get("REPO_PUBLIC_HOST", "localhost")
PUBLIC_SCHEME = os.environ.get("REPO_PUBLIC_SCHEME", "http")
PUBLIC_PORT = int(os.environ.get("REPO_PUBLIC_PORT", os.environ.get("REPO_PORT", "8097")))
PORT = int(os.environ.get("REPO_PORT", "8097"))
MANIFEST = Path(__file__).with_name("jellyfin-plugin-repo.json")


class RepoHandler(SimpleHTTPRequestHandler):
    def do_GET(self):
        if self.path == "/jellyfin-plugin-repo.json":
            served_manifest = Path(__file__).with_name("jellyfin-plugin-repo.served.json")
            if not served_manifest.exists():
                self.send_error(404, "Manifest not generated yet. Run fetch_releases.py and serve_repo.py first.")
                return
            data = served_manifest.read_bytes()
            self.send_response(200)
            self.send_header("Content-Type", "application/json")
            self.send_header("Content-Length", str(len(data)))
            self.send_header("Access-Control-Allow-Origin", "*")
            self.end_headers()
            self.wfile.write(data)
            return
        return super().do_GET()

    def log_message(self, fmt, *args):
        print(f"[{self.address_string()}] {fmt % args}")


def rewrite_manifest_source_urls():
    """
    Rewrite file:// sourceUrls to point at this local server.
    Safe to re-run; creates/updates jellyfin-plugin-repo.served.json.
    """
    if not MANIFEST.exists():
        return
    manifest = json.loads(MANIFEST.read_text(encoding="utf-8"))
    served_manifest = Path(__file__).with_name("jellyfin-plugin-repo.served.json")
    for entry in manifest:
        for version in entry.get("versions", []):
            src = version.get("sourceUrl", "")
            if src.startswith("file://"):
                zip_name = Path(src.replace("file://", "")).name
                public_port = "" if PUBLIC_PORT == 443 else f":{PUBLIC_PORT}"
                version["sourceUrl"] = f"{PUBLIC_SCHEME}://{PUBLIC_HOST}{public_port}/plugin-zips/{zip_name}"
    served_manifest.write_text(json.dumps(manifest, indent=2), encoding="utf-8")
    print(f"Rewrote manifest for public host {PUBLIC_HOST}:{PORT}: {served_manifest}")


def main() -> int:
    rewrite_manifest_source_urls()
    os.chdir(Path(__file__).parent)
    server = HTTPServer((BIND_HOST, PORT), RepoHandler)
    public_port = "" if PUBLIC_PORT == 443 else f":{PUBLIC_PORT}"
    print(f"Serving Jellyfin plugin repo at {PUBLIC_SCHEME}://{PUBLIC_HOST}{public_port}/jellyfin-plugin-repo.json")
    print(f"Bind address: {BIND_HOST}:{PORT}")
    print("Add that URL to Jellyfin Dashboard -> Plugins -> Repositories")
    try:
        server.serve_forever()
    except KeyboardInterrupt:
        print("\nShutting down.")
    return 0


if __name__ == "__main__":
    sys.exit(main())
