"""Analyze a PDF and recommend the best extractor(s).

Checks text density, image coverage, table geometry, and form fields
to classify the PDF and suggest which extractors to run.
"""

import argparse
import json
import sys

import fitz  # pymupdf
import pdfplumber


def _analyze_epub(epub_path: str) -> dict:
    """Return analysis dict for an EPUB file."""
    from extractors.epub import extract as epub_extract

    chapters = epub_extract(epub_path)
    total_chars = sum(len(c["text"]) for c in chapters)

    return {
        "pdf_path": epub_path,
        "page_count": len(chapters),
        "pages_with_text": len(chapters),
        "pages_without_text": 0,
        "total_chars": total_chars,
        "total_images": 0,
        "total_tables": 0,
        "total_form_fields": 0,
        "pdf_type": "epub",
        "auto_extractor": "epub",
        "recommended_extractors": ["epub"],
    }


def analyze(pdf_path: str) -> dict:
    """Return an analysis dict describing the document's characteristics."""
    if pdf_path.lower().endswith(".epub"):
        return _analyze_epub(pdf_path)

    page_count = 0
    total_chars = 0
    pages_with_text = 0
    pages_without_text = 0
    total_images = 0
    total_tables = 0
    total_form_fields = 0

    # pymupdf pass: text, images, form fields
    with fitz.open(pdf_path) as doc:
        page_count = len(doc)
        for page in doc:
            text = page.get_text("text").strip()
            char_count = len(text)
            total_chars += char_count

            if char_count >= 50:
                pages_with_text += 1
            else:
                pages_without_text += 1

            total_images += len(page.get_images(full=True))
            total_form_fields += len(list(page.widgets()))

    # pdfplumber pass: tables
    with pdfplumber.open(pdf_path) as pdf:
        for page in pdf.pages:
            total_tables += len(page.find_tables())

    # Classification
    has_text = pages_with_text > 0
    has_scanned = pages_without_text > 0
    has_tables = total_tables > 0
    has_images = total_images > 0
    has_forms = total_form_fields > 0

    # Determine primary type
    if has_text and not has_scanned:
        pdf_type = "digital"
    elif has_scanned and not has_text:
        pdf_type = "scanned"
    else:
        pdf_type = "mixed"

    # Recommend extractors
    recommended = []
    if pdf_type == "digital":
        recommended.append("native")
    elif pdf_type == "scanned":
        recommended.append("scanned")
    else:
        recommended.append("mixed")

    if has_tables:
        recommended.append("tables")
    if has_images:
        recommended.append("images")
    if has_forms:
        recommended.append("forms")

    # Pick the single best for "auto" mode
    auto_extractor = recommended[0]

    return {
        "pdf_path": pdf_path,
        "page_count": page_count,
        "pages_with_text": pages_with_text,
        "pages_without_text": pages_without_text,
        "total_chars": total_chars,
        "total_images": total_images,
        "total_tables": total_tables,
        "total_form_fields": total_form_fields,
        "pdf_type": pdf_type,
        "auto_extractor": auto_extractor,
        "recommended_extractors": recommended,
    }


def main():
    parser = argparse.ArgumentParser(description="Analyze a PDF and recommend extractors")
    parser.add_argument("pdf", help="Path to input PDF")
    parser.add_argument("--json", action="store_true", help="Output full JSON analysis")
    args = parser.parse_args()

    result = analyze(args.pdf)

    if args.json:
        json.dump(result, sys.stdout, indent=2)
        sys.stdout.write("\n")
    else:
        print(f"Type: {result['pdf_type']}")
        print(f"Pages: {result['page_count']} ({result['pages_with_text']} text, {result['pages_without_text']} scanned)")
        print(f"Images: {result['total_images']}  Tables: {result['total_tables']}  Form fields: {result['total_form_fields']}")
        print(f"Auto extractor: {result['auto_extractor']}")
        print(f"Recommended: {', '.join(result['recommended_extractors'])}")


if __name__ == "__main__":
    main()
