from datetime import date
from typing import List

from fastapi import APIRouter, UploadFile, File
from fastapi.responses import HTMLResponse
import shutil

from config import (
    BASE_DIR,
    EINGANG_DIR,
    BEREINIGT_DIR,
    EDITIERBAR_DIR,
    NEU_GENERIERT_DIR,
    is_valid_input_file,
)
from ai_processor import (
    dummy_process_scan,
    describe_scan_with_ai,
    analyze_scan_structure_with_ai,
    build_clean_html_from_analysis,
    remove_handwriting_from_scan,
    generate_mc_from_analysis,
    generate_cloze_from_analysis,
    generate_qa_from_analysis,
    update_leitner_progress,
    get_next_review_items,
    generate_print_version_qa,
    generate_print_version_cloze,
    generate_print_version_mc,
    generate_print_version_worksheet,
    generate_mindmap_data,
    generate_mindmap_html,
    save_mindmap_for_worksheet,
)

router = APIRouter()


@router.get("/")
def home():
    """Basis-Info des Backends (unter /api/ erreichbar)."""
    return {
        "status": "OK",
        "message": "BreakPilot Backend läuft.",
        "base_dir": str(BASE_DIR),
    }


# === UPLOAD ===


@router.post("/upload-scan")
async def upload_scan(file: UploadFile = File(...)):
    """
    Einzelnen Scan hochladen.
    Dateiname bekommt automatisch ein Datum vorne dran: YYYY-MM-DD_originalname.ext
    """
    today = date.today().isoformat()
    safe_name = file.filename.replace("/", "_")
    target_name = f"{today}_{safe_name}"
    target_path = EINGANG_DIR / target_name
    with target_path.open("wb") as buffer:
        shutil.copyfileobj(file.file, buffer)
    return {
        "status": "OK",
        "message": "Scan gespeichert",
        "saved_as": str(target_path),
    }


@router.get("/upload-form", response_class=HTMLResponse)
def upload_form():
    """Einfache HTML-Upload-Seite (für schnelle Tests im Browser)."""
    return """
    <html>
    <body>
      <h1>Arbeitsblätter hochladen</h1>
      <form action="/upload-multi" method="post" enctype="multipart/form-data">
        <input type="file" name="files" multiple required>
        <button type="submit">Hochladen</button>
      </form>
    </body>
    </html>
    """


@router.post("/upload-multi")
async def upload_multi(files: List[UploadFile] = File(...)):
    """
    Mehrere Dateien per Stapel hochladen.
    Alle Dateien landen im Ordner Eingang mit Datumspräfix.
    """
    today = date.today().isoformat()
    saved = []
    for file in files:
        safe_name = file.filename.replace("/", "_")
        target_name = f"{today}_{safe_name}"
        target_path = EINGANG_DIR / target_name
        with target_path.open("wb") as buffer:
            shutil.copyfileobj(file.file, buffer)
        saved.append(str(target_path))
    return {"status": "OK", "message": "Dateien gespeichert", "saved_as": saved}


# === LISTEN & LÖSCHEN ===


@router.get("/eingang-dateien")
def list_eingang_files():
    files = [f.name for f in EINGANG_DIR.iterdir() if is_valid_input_file(f)]
    return {"eingang": files}


@router.delete("/eingang-dateien/{filename}")
def delete_eingang_file(filename: str):
    """
    Löscht eine Datei komplett und entfernt sie aus allen Lerneinheiten.
    """
    from learning_units import get_all_units, update_unit

    path = EINGANG_DIR / filename
    if not path.exists() or not path.is_file():
        return {"status": "ERROR", "message": "Datei nicht gefunden", "filename": filename}

    # Datei aus allen Lerneinheiten entfernen
    units = get_all_units()
    units_updated = 0
    for unit in units:
        if filename in unit.get("worksheet_files", []):
            # Datei aus der Liste entfernen
            unit["worksheet_files"].remove(filename)
            # Lerneinheit aktualisieren
            update_unit(unit["id"], unit)
            units_updated += 1

    # Physische Datei löschen
    path.unlink()

    return {
        "status": "OK",
        "message": "Datei gelöscht",
        "filename": filename,
        "units_updated": units_updated
    }


@router.get("/bereinigt-dateien")
def list_bereinigt_files():
    files = [f.name for f in BEREINIGT_DIR.iterdir() if f.is_file()]
    return {"bereinigt": files}


# === VERARBEITUNG: Dummy / Beschreiben / Analysieren / HTML erzeugen ===


@router.post("/process-all")
def process_all_scans():
    """
    Einfache Dummy-Verarbeitung aller Eingangsdateien.
    Dient vor allem als Fallback / Debug.
    """
    processed = []
    skipped = []
    for f in EINGANG_DIR.iterdir():
        if is_valid_input_file(f):
            out = dummy_process_scan(f)
            processed.append(out.name)
        else:
            skipped.append(f.name)
    return {
        "status": "OK",
        "processed_files": processed,
        "skipped": skipped,
    }


@router.post("/remove-handwriting-all")
def remove_handwriting_all():
    """
    MVP-Version: erzeugt *_clean-Bilder im Ordner Bereinigt.
    Die eigentliche inhaltliche „Bereinigung“ (keine Handschrift, keine durchgestrichenen Wörter)
    passiert später beim HTML-Neuaufbau.
    """
    cleaned = []
    errors = []
    skipped = []
    for f in EINGANG_DIR.iterdir():
        if not is_valid_input_file(f):
            skipped.append(f.name)
            continue
        if f.suffix.lower() not in {".jpg", ".jpeg", ".png"}:
            skipped.append(f.name)
            continue
        try:
            out = remove_handwriting_from_scan(f)
            cleaned.append(out.name)
        except Exception as e:
            errors.append({"file": f.name, "error": str(e)})
    return {
        "status": "OK" if cleaned else "ERROR",
        "cleaned": cleaned,
        "errors": errors,
        "skipped": skipped,
    }


@router.post("/describe-all")
def describe_all_scans():
    """
    Vision-Modell beschreibt alle gültigen Eingangsdateien kurz.
    Ergebnis: *_beschreibung.txt in Bereinigt.
    """
    described = []
    errors = []
    skipped = []
    for f in EINGANG_DIR.iterdir():
        if not is_valid_input_file(f):
            skipped.append(f.name)
            continue
        try:
            out = describe_scan_with_ai(f)
            described.append(out.name)
        except Exception as e:
            errors.append({"file": f.name, "error": str(e)})
    return {"status": "OK", "described": described, "errors": errors, "skipped": skipped}


@router.post("/analyze-all")
def analyze_all_scans():
    """
    Vision-Modell analysiert Struktur aller Eingangsdateien.
    Ergebnis: *_analyse.json in Bereinigt.
    """
    analyzed = []
    errors = []
    skipped = []
    for f in EINGANG_DIR.iterdir():
        if not is_valid_input_file(f):
            skipped.append(f.name)
            continue
        try:
            out = analyze_scan_structure_with_ai(f)
            analyzed.append(out.name)
        except Exception as e:
            errors.append({"file": f.name, "error": str(e)})
    return {"status": "OK", "analyzed": analyzed, "errors": errors, "skipped": skipped}


@router.post("/generate-clean")
def generate_clean_worksheets():
    """
    Baut aus allen *_analyse.json Dateien saubere HTML-Arbeitsblätter.
    Ergebnis: *_clean.html in Bereinigt.
    """
    generated = []
    errors = []
    for f in BEREINIGT_DIR.iterdir():
        if f.suffix == ".json" and f.name.endswith("_analyse.json"):
            try:
                out = build_clean_html_from_analysis(f)
                generated.append(out.name)
            except Exception as e:
                errors.append({"file": f.name, "error": str(e)})
    return {"status": "OK", "generated": generated, "errors": errors}


# === Mapping Alt vs. Neu + HTML-/Image-Auslieferung ===


@router.get("/worksheet-pairs")
def list_worksheet_pairs():
    """
    Für jede Datei im Eingang wird nach einem passenden „sauberen“ Pendant gesucht:

    - HTML:
      - <stem>_clean.html
      - <stem>__clean.html  (kompatibel zu früherem Bug mit doppeltem Unterstrich)
      - <stem>.html

    - Bild:
      - <stem>_clean.(jpg|jpeg|png|JPG|JPEG|PNG)
      - <stem>__clean.(...) (falls so erzeugt)
    """
    pairs = []
    for f in EINGANG_DIR.iterdir():
        if not is_valid_input_file(f):
            continue
        base = f.stem
        clean_html = None
        clean_image = None

        # HTML-Kandidaten
        html_candidates = [
            f"{base}_clean.html",
            f"{base}__clean.html",
            f"{base}.html",
        ]
        for cand in html_candidates:
            p = BEREINIGT_DIR / cand
            if p.exists() and p.is_file():
                clean_html = cand
                break

        # Bild-Kandidaten (immer suchen, unabhängig von HTML)
        exts = [".jpg", ".jpeg", ".png", ".JPG", ".JPEG", ".PNG"]
        found = False
        for ext in exts:
            for suffix in ["_clean", "__clean"]:
                cand_img = f"{base}{suffix}{ext}"
                p = BEREINIGT_DIR / cand_img
                if p.exists() and p.is_file():
                    clean_image = cand_img
                    found = True
                    break
            if found:
                break

        pairs.append(
            {
                "original": f.name,
                "clean_html": clean_html,
                "clean_image": clean_image,
            }
        )

    return {"pairs": pairs}


@router.get("/clean-html/{filename}", response_class=HTMLResponse)
def get_clean_html(filename: str):
    """
    Liefert eine der erzeugten clean-HTML-Dateien aus dem Ordner Bereinigt.
    Wird im Frontend für die „neu aufgebautes Arbeitsblatt"-Vorschau genutzt.
    """
    path = BEREINIGT_DIR / filename
    if not path.exists() or not path.is_file() or path.suffix != ".html":
        return HTMLResponse(
            "<html><body><p>Kein neu aufgebautes Arbeitsblatt gefunden.</p></body></html>",
            status_code=404,
        )
    content = path.read_text(encoding="utf-8")
    return HTMLResponse(content)


# === MULTIPLE CHOICE ===


@router.post("/generate-mc")
def generate_mc_all():
    """
    Generiert Multiple-Choice-Fragen für alle analysierten Arbeitsblätter.

    Voraussetzung: Die Analyse (*_analyse.json) muss bereits existieren.
    Ergebnis: *_mc.json Dateien im Ordner Bereinigt.

    Die MC-Fragen:
    - Entsprechen dem Schwierigkeitsgrad des Originals
    - Haben zufällig angeordnete Antworten (nicht immer A = richtig)
    """
    generated = []
    errors = []
    skipped = []

    for f in BEREINIGT_DIR.iterdir():
        if f.suffix == ".json" and f.name.endswith("_analyse.json"):
            try:
                out = generate_mc_from_analysis(f)
                generated.append(out.name)
            except Exception as e:
                errors.append({"file": f.name, "error": str(e)})
        elif f.suffix == ".json":
            skipped.append(f.name)

    return {
        "status": "OK" if generated else "ERROR",
        "generated": generated,
        "errors": errors,
        "skipped": skipped,
    }


@router.get("/mc-data/{filename}")
def get_mc_data(filename: str):
    """
    Liefert die generierten MC-Fragen für ein Arbeitsblatt.

    Args:
        filename: Name der Original-Datei (z.B. "2024-12-10_mathe.jpg")
                  oder der MC-Datei (z.B. "2024-12-10_mathe_mc.json")

    Returns:
        JSON mit questions und metadata
    """
    import json

    # Versuche verschiedene Dateinamen-Formate
    base = filename
    if base.endswith("_mc.json"):
        mc_filename = base
    else:
        # Entferne Dateiendung und füge _mc.json hinzu
        base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
        mc_filename = f"{base_stem}_mc.json"

    path = BEREINIGT_DIR / mc_filename
    if not path.exists() or not path.is_file():
        return {"status": "NOT_FOUND", "message": f"MC-Daten nicht gefunden: {mc_filename}"}

    try:
        data = json.loads(path.read_text(encoding="utf-8"))
        return {"status": "OK", "data": data, "filename": mc_filename}
    except json.JSONDecodeError as e:
        return {"status": "ERROR", "message": f"Ungültige JSON-Datei: {e}"}


@router.get("/mc-list")
def list_mc_files():
    """
    Listet alle generierten MC-Dateien auf.

    Returns:
        Liste der MC-Dateien mit zugehörigen Original-Dateinamen
    """
    mc_files = []

    for f in BEREINIGT_DIR.iterdir():
        if f.suffix == ".json" and f.name.endswith("_mc.json"):
            # Versuche Original-Datei zu finden
            base_stem = f.stem.replace("_mc", "")
            original = None

            # Suche nach passender Datei im Eingang
            for ext in [".jpg", ".jpeg", ".png", ".JPG", ".JPEG", ".PNG", ".pdf", ".PDF"]:
                candidate = EINGANG_DIR / f"{base_stem}{ext}"
                if candidate.exists():
                    original = candidate.name
                    break

            mc_files.append({
                "mc_file": f.name,
                "original": original,
                "base_name": base_stem,
            })

    return {"mc_files": mc_files}


# === LÜCKENTEXT ===


@router.post("/generate-cloze")
def generate_cloze_all(target_language: str = "tr"):
    """
    Generiert Lückentexte für alle analysierten Arbeitsblätter.

    Voraussetzung: Die Analyse (*_analyse.json) muss bereits existieren.
    Ergebnis: *_cloze.json Dateien im Ordner Bereinigt.

    Die Lückentexte:
    - Haben mehrere sinnvolle Lücken pro Satz
    - Entsprechen dem Schwierigkeitsgrad des Originals
    - Enthalten eine Übersetzung mit denselben Lücken

    Args:
        target_language: Sprachcode für Übersetzung (default: "tr" für Türkisch)
                        Unterstützt: tr, ar, ru, en, fr, es, pl, uk
    """
    generated = []
    errors = []
    skipped = []

    for f in BEREINIGT_DIR.iterdir():
        if f.suffix == ".json" and f.name.endswith("_analyse.json"):
            try:
                out = generate_cloze_from_analysis(f, target_language)
                generated.append(out.name)
            except Exception as e:
                errors.append({"file": f.name, "error": str(e)})
        elif f.suffix == ".json":
            skipped.append(f.name)

    return {
        "status": "OK" if generated else "ERROR",
        "generated": generated,
        "errors": errors,
        "skipped": skipped,
        "target_language": target_language,
    }


@router.get("/cloze-data/{filename}")
def get_cloze_data(filename: str):
    """
    Liefert die generierten Lückentexte für ein Arbeitsblatt.

    Args:
        filename: Name der Original-Datei (z.B. "2024-12-10_deutsch.jpg")
                  oder der Cloze-Datei (z.B. "2024-12-10_deutsch_cloze.json")

    Returns:
        JSON mit cloze_items und metadata
    """
    import json

    # Versuche verschiedene Dateinamen-Formate
    base = filename
    if base.endswith("_cloze.json"):
        cloze_filename = base
    else:
        # Entferne Dateiendung und füge _cloze.json hinzu
        base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
        cloze_filename = f"{base_stem}_cloze.json"

    path = BEREINIGT_DIR / cloze_filename
    if not path.exists() or not path.is_file():
        return {"status": "NOT_FOUND", "message": f"Lückentext-Daten nicht gefunden: {cloze_filename}"}

    try:
        data = json.loads(path.read_text(encoding="utf-8"))
        return {"status": "OK", "data": data, "filename": cloze_filename}
    except json.JSONDecodeError as e:
        return {"status": "ERROR", "message": f"Ungültige JSON-Datei: {e}"}


@router.get("/cloze-list")
def list_cloze_files():
    """
    Listet alle generierten Lückentext-Dateien auf.

    Returns:
        Liste der Cloze-Dateien mit zugehörigen Original-Dateinamen
    """
    cloze_files = []

    for f in BEREINIGT_DIR.iterdir():
        if f.suffix == ".json" and f.name.endswith("_cloze.json"):
            # Versuche Original-Datei zu finden
            base_stem = f.stem.replace("_cloze", "")
            original = None

            # Suche nach passender Datei im Eingang
            for ext in [".jpg", ".jpeg", ".png", ".JPG", ".JPEG", ".PNG", ".pdf", ".PDF"]:
                candidate = EINGANG_DIR / f"{base_stem}{ext}"
                if candidate.exists():
                    original = candidate.name
                    break

            cloze_files.append({
                "cloze_file": f.name,
                "original": original,
                "base_name": base_stem,
            })

    return {"cloze_files": cloze_files}


# === FRAGE-ANTWORT (Q&A) MIT LEITNER-SYSTEM ===


@router.post("/generate-qa")
def generate_qa_all(num_questions: int = 8):
    """
    Generiert Frage-Antwort-Paare für alle analysierten Arbeitsblätter.

    Voraussetzung: Die Analyse (*_analyse.json) muss bereits existieren.
    Ergebnis: *_qa.json Dateien im Ordner Bereinigt.

    Die Q&A-Paare:
    - Fragen sind fast wörtlich aus dem Text entnommen
    - Schlüsselbegriffe sind markiert für Spaced Repetition
    - Enthalten Leitner-Box Metadaten für Lernfortschritt

    Args:
        num_questions: Anzahl der zu generierenden Fragen (default: 8)
    """
    generated = []
    errors = []
    skipped = []

    for f in BEREINIGT_DIR.iterdir():
        if f.suffix == ".json" and f.name.endswith("_analyse.json"):
            try:
                out = generate_qa_from_analysis(f, num_questions)
                generated.append(out.name)
            except Exception as e:
                errors.append({"file": f.name, "error": str(e)})
        elif f.suffix == ".json":
            skipped.append(f.name)

    return {
        "status": "OK" if generated else "ERROR",
        "generated": generated,
        "errors": errors,
        "skipped": skipped,
        "num_questions": num_questions,
    }


@router.get("/qa-data/{filename}")
def get_qa_data(filename: str):
    """
    Liefert die generierten Q&A-Paare für ein Arbeitsblatt.

    Args:
        filename: Name der Original-Datei (z.B. "2024-12-10_deutsch.jpg")
                  oder der QA-Datei (z.B. "2024-12-10_deutsch_qa.json")

    Returns:
        JSON mit qa_items und metadata inkl. Leitner-Fortschritt
    """
    import json

    # Versuche verschiedene Dateinamen-Formate
    base = filename
    if base.endswith("_qa.json"):
        qa_filename = base
    else:
        # Entferne Dateiendung und füge _qa.json hinzu
        base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
        qa_filename = f"{base_stem}_qa.json"

    path = BEREINIGT_DIR / qa_filename
    if not path.exists() or not path.is_file():
        return {"status": "NOT_FOUND", "message": f"Q&A-Daten nicht gefunden: {qa_filename}"}

    try:
        data = json.loads(path.read_text(encoding="utf-8"))
        return {"status": "OK", "data": data, "filename": qa_filename}
    except json.JSONDecodeError as e:
        return {"status": "ERROR", "message": f"Ungültige JSON-Datei: {e}"}


@router.get("/qa-list")
def list_qa_files():
    """
    Listet alle generierten Q&A-Dateien auf.

    Returns:
        Liste der QA-Dateien mit zugehörigen Original-Dateinamen
    """
    qa_files = []

    for f in BEREINIGT_DIR.iterdir():
        if f.suffix == ".json" and f.name.endswith("_qa.json"):
            # Versuche Original-Datei zu finden
            base_stem = f.stem.replace("_qa", "")
            original = None

            # Suche nach passender Datei im Eingang
            for ext in [".jpg", ".jpeg", ".png", ".JPG", ".JPEG", ".PNG", ".pdf", ".PDF"]:
                candidate = EINGANG_DIR / f"{base_stem}{ext}"
                if candidate.exists():
                    original = candidate.name
                    break

            qa_files.append({
                "qa_file": f.name,
                "original": original,
                "base_name": base_stem,
            })

    return {"qa_files": qa_files}


@router.post("/qa-progress")
def update_qa_progress(filename: str, item_id: str, correct: bool):
    """
    Aktualisiert den Leitner-Lernfortschritt für eine Q&A-Frage.

    Das Leitner-System:
    - Box 0 (neu): Wiederholung nach 1 Tag
    - Box 1 (gelernt): Wiederholung nach 3 Tagen
    - Box 2 (gefestigt): Wiederholung nach 7 Tagen
    - Falsche Antwort: Eine Box zurück, Wiederholung nach 4 Stunden

    Args:
        filename: Name der QA-Datei
        item_id: ID der Frage (z.B. "q_0")
        correct: True wenn richtig beantwortet, False wenn falsch

    Returns:
        Aktualisierter Fortschritt für die Frage
    """
    # Finde QA-Datei
    base = filename
    if base.endswith("_qa.json"):
        qa_filename = base
    else:
        base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
        qa_filename = f"{base_stem}_qa.json"

    path = BEREINIGT_DIR / qa_filename
    if not path.exists() or not path.is_file():
        return {"status": "NOT_FOUND", "message": f"Q&A-Daten nicht gefunden: {qa_filename}"}

    try:
        result = update_leitner_progress(path, item_id, correct)
        return {"status": "OK", "progress": result, "filename": qa_filename}
    except Exception as e:
        return {"status": "ERROR", "message": str(e)}


@router.get("/qa-review/{filename}")
def get_qa_review_items(filename: str, limit: int = 5):
    """
    Liefert die nächsten zu wiederholenden Fragen basierend auf dem Leitner-System.

    Priorisierung:
    1. Überfällige Fragen (nach next_review Zeit)
    2. Niedrigere Boxen zuerst (Box 0 vor Box 1 vor Box 2)
    3. Längere Zeit nicht gesehen

    Args:
        filename: Name der QA-Datei
        limit: Maximale Anzahl zurückzugebender Fragen (default: 5)

    Returns:
        Liste der zu wiederholenden Fragen mit Leitner-Metadaten
    """
    # Finde QA-Datei
    base = filename
    if base.endswith("_qa.json"):
        qa_filename = base
    else:
        base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
        qa_filename = f"{base_stem}_qa.json"

    path = BEREINIGT_DIR / qa_filename
    if not path.exists() or not path.is_file():
        return {"status": "NOT_FOUND", "message": f"Q&A-Daten nicht gefunden: {qa_filename}"}

    try:
        items = get_next_review_items(path, limit)
        return {"status": "OK", "review_items": items, "filename": qa_filename, "count": len(items)}
    except Exception as e:
        return {"status": "ERROR", "message": str(e)}


# === PRINT-VERSIONEN ===


@router.get("/print-qa/{filename}", response_class=HTMLResponse)
def get_print_qa(filename: str, show_answers: bool = False):
    """
    Liefert eine druckbare HTML-Version der Q&A-Fragen.

    Args:
        filename: Name der QA-Datei oder Original-Datei
        show_answers: True für Lösungsblatt, False für Fragenblatt

    Returns:
        Druckbare HTML-Seite
    """
    # Finde QA-Datei
    base = filename
    if base.endswith("_qa.json"):
        qa_filename = base
    else:
        base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
        qa_filename = f"{base_stem}_qa.json"

    path = BEREINIGT_DIR / qa_filename
    if not path.exists() or not path.is_file():
        return HTMLResponse(
            "<html><body><p>Q&A-Daten nicht gefunden.</p></body></html>",
            status_code=404,
        )

    try:
        html = generate_print_version_qa(path, show_answers)
        return HTMLResponse(html)
    except Exception as e:
        return HTMLResponse(
            f"<html><body><p>Fehler: {e}</p></body></html>",
            status_code=500,
        )


@router.get("/print-cloze/{filename}", response_class=HTMLResponse)
def get_print_cloze(filename: str, show_answers: bool = False):
    """
    Liefert eine druckbare HTML-Version der Lückentexte.

    Args:
        filename: Name der Cloze-Datei oder Original-Datei
        show_answers: True für Lösungsblatt mit ausgefüllten Lücken,
                     False für Übungsblatt mit Wortbank

    Returns:
        Druckbare HTML-Seite
    """
    # Finde Cloze-Datei
    base = filename
    if base.endswith("_cloze.json"):
        cloze_filename = base
    else:
        base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
        cloze_filename = f"{base_stem}_cloze.json"

    path = BEREINIGT_DIR / cloze_filename
    if not path.exists() or not path.is_file():
        return HTMLResponse(
            "<html><body><p>Lückentext-Daten nicht gefunden.</p></body></html>",
            status_code=404,
        )

    try:
        html = generate_print_version_cloze(path, show_answers)
        return HTMLResponse(html)
    except Exception as e:
        return HTMLResponse(
            f"<html><body><p>Fehler: {e}</p></body></html>",
            status_code=500,
        )


@router.get("/print-mc/{filename}", response_class=HTMLResponse)
def get_print_mc(filename: str, show_answers: bool = False):
    """
    Liefert eine druckbare HTML-Version der Multiple-Choice-Fragen.

    Args:
        filename: Name der MC-Datei oder Original-Datei
        show_answers: True für Lösungsblatt mit markierten Antworten,
                     False für Testblatt zum Ausfüllen

    Returns:
        Druckbare HTML-Seite
    """
    # Finde MC-Datei
    base = filename
    if base.endswith("_mc.json"):
        mc_filename = base
    else:
        base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
        mc_filename = f"{base_stem}_mc.json"

    path = BEREINIGT_DIR / mc_filename
    if not path.exists() or not path.is_file():
        return HTMLResponse(
            "<html><body><p>MC-Daten nicht gefunden.</p></body></html>",
            status_code=404,
        )

    try:
        html = generate_print_version_mc(path, show_answers)
        return HTMLResponse(html)
    except Exception as e:
        return HTMLResponse(
            f"<html><body><p>Fehler beim Erstellen der MC-Druckversion: {e}</p></body></html>",
            status_code=500,
        )


@router.get("/print-worksheet/{filename}", response_class=HTMLResponse)
def get_print_worksheet(filename: str):
    """
    Liefert eine druckoptimierte HTML-Version des neu aufgebauten Arbeitsblatts.

    - Große, klare Schrift
    - Schwarz-weiß / Graustufen-tauglich
    - Direkt druckbar für Eltern
    """
    # Analysedatei finden
    base = filename.rsplit(".", 1)[0]  # Entfernt Dateiendung
    analysis_path = BEREINIGT_DIR / f"{base}_analyse.json"

    if not analysis_path.exists():
        return HTMLResponse(
            f"<html><body><p>Keine Analyse gefunden für: {filename}</p></body></html>",
            status_code=404,
        )

    try:
        html = generate_print_version_worksheet(analysis_path)
        return HTMLResponse(html)
    except Exception as e:
        return HTMLResponse(
            f"<html><body><p>Fehler beim Erstellen der Druckversion: {e}</p></body></html>",
            status_code=500,
        )


# === MINDMAP LERNPOSTER ===


@router.post("/generate-mindmap/{filename}")
def generate_mindmap(filename: str):
    """
    Generiert eine kindgerechte Mindmap aus einem analysierten Arbeitsblatt.

    Die Mindmap:
    - Zeigt das Hauptthema in der Mitte
    - Gruppiert Fachbegriffe in farbige Kategorien
    - Enthält Emojis für bessere visuelle Orientierung
    - Kann als A3 Poster gedruckt werden

    Args:
        filename: Name der Original-Datei (z.B. "2024-12-10_biologie.jpg")

    Returns:
        Status und Dateiname der generierten Mindmap
    """
    # Analysedatei finden
    base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
    analysis_path = BEREINIGT_DIR / f"{base_stem}_analyse.json"

    if not analysis_path.exists():
        return {
            "status": "NOT_FOUND",
            "message": f"Keine Analyse gefunden für: {filename}. Bitte zuerst analysieren."
        }

    try:
        # Mindmap-Daten generieren
        mindmap_data = generate_mindmap_data(analysis_path)

        # Mindmap speichern
        mindmap_path = save_mindmap_for_worksheet(analysis_path, mindmap_data)

        return {
            "status": "OK",
            "message": "Mindmap erfolgreich generiert",
            "filename": mindmap_path.name,
            "topic": mindmap_data.get("topic", ""),
            "categories_count": len(mindmap_data.get("categories", [])),
        }
    except Exception as e:
        return {
            "status": "ERROR",
            "message": f"Fehler bei der Mindmap-Generierung: {e}"
        }


@router.get("/mindmap-data/{filename}")
def get_mindmap_data(filename: str):
    """
    Liefert die generierten Mindmap-Daten für ein Arbeitsblatt.

    Args:
        filename: Name der Original-Datei oder der Mindmap-Datei

    Returns:
        JSON mit topic, subject und categories
    """
    import json

    # Versuche verschiedene Dateinamen-Formate
    base = filename
    if base.endswith("_mindmap.json"):
        mindmap_filename = base
    else:
        base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
        mindmap_filename = f"{base_stem}_mindmap.json"

    path = BEREINIGT_DIR / mindmap_filename
    if not path.exists() or not path.is_file():
        return {"status": "NOT_FOUND", "message": f"Mindmap-Daten nicht gefunden: {mindmap_filename}"}

    try:
        data = json.loads(path.read_text(encoding="utf-8"))
        return {"status": "OK", "data": data, "filename": mindmap_filename}
    except json.JSONDecodeError as e:
        return {"status": "ERROR", "message": f"Ungültige JSON-Datei: {e}"}


@router.get("/mindmap-html/{filename}", response_class=HTMLResponse)
def get_mindmap_html(filename: str, format: str = "a3"):
    """
    Liefert die Mindmap als druckbares HTML mit SVG.

    Args:
        filename: Name der Original-Datei oder der Mindmap-Datei
        format: Druckformat - "a3" (Standard, Poster) oder "a4"

    Returns:
        HTML-Seite mit SVG-Mindmap, druckoptimiert
    """
    import json

    # Versuche verschiedene Dateinamen-Formate
    base = filename
    if base.endswith("_mindmap.json"):
        mindmap_filename = base
    else:
        base_stem = filename.rsplit(".", 1)[0] if "." in filename else filename
        mindmap_filename = f"{base_stem}_mindmap.json"

    path = BEREINIGT_DIR / mindmap_filename
    if not path.exists() or not path.is_file():
        return HTMLResponse(
            "<html><body><p>Mindmap-Daten nicht gefunden. Bitte zuerst generieren.</p></body></html>",
            status_code=404,
        )

    try:
        data = json.loads(path.read_text(encoding="utf-8"))
        html = generate_mindmap_html(data, format)
        return HTMLResponse(html)
    except json.JSONDecodeError:
        return HTMLResponse(
            "<html><body><p>Ungültige Mindmap-Datei.</p></body></html>",
            status_code=500,
        )
    except Exception as e:
        return HTMLResponse(
            f"<html><body><p>Fehler beim Erstellen der Mindmap: {e}</p></body></html>",
            status_code=500,
        )


@router.get("/mindmap-list")
def list_mindmap_files():
    """
    Listet alle generierten Mindmap-Dateien auf.

    Returns:
        Liste der Mindmap-Dateien mit zugehörigen Original-Dateinamen
    """
    mindmap_files = []

    for f in BEREINIGT_DIR.iterdir():
        if f.suffix == ".json" and f.name.endswith("_mindmap.json"):
            # Versuche Original-Datei zu finden
            base_stem = f.stem.replace("_mindmap", "")
            original = None

            # Suche nach passender Datei im Eingang
            for ext in [".jpg", ".jpeg", ".png", ".JPG", ".JPEG", ".PNG", ".pdf", ".PDF"]:
                candidate = EINGANG_DIR / f"{base_stem}{ext}"
                if candidate.exists():
                    original = candidate.name
                    break

            mindmap_files.append({
                "mindmap_file": f.name,
                "original": original,
                "base_name": base_stem,
            })

    return {"mindmap_files": mindmap_files}
