from app.models.knowledge import FileType

_BINARY_SIGNATURES = {
    b"%PDF-": "PDF",
    b"PK\x03\x04": "ZIP/Office",
    b"PK\x05\x06": "ZIP/Office (empty)",
    b"\x7fELF": "ELF executable",
    b"MZ": "Windows executable",
    b"\x89PNG": "PNG image",
    b"\xff\xd8\xff": "JPEG image",
    b"GIF8": "GIF image",
}

_TEXT_TYPES = {FileType.txt, FileType.markdown, FileType.html, FileType.csv, FileType.json, FileType.xml}


def _sniff(content: bytes) -> str | None:
    for sig, label in _BINARY_SIGNATURES.items():
        if content.startswith(sig):
            return label
    return None


def verify_file_signature(content: bytes, declared_type: FileType) -> tuple[bool, str | None]:
    """Cheap magic-byte sanity check so a spoofed extension can't slip a binary past
    the text-extraction pipeline. Not a full antivirus/content scan."""
    if not content:
        return False, "empty file"

    sniffed = _sniff(content)

    if declared_type == FileType.pdf:
        return (sniffed == "PDF", "does not start with a PDF header")

    if declared_type == FileType.docx:
        return (sniffed in ("ZIP/Office", "ZIP/Office (empty)"), "does not look like a valid DOCX (zip) file")

    if declared_type in _TEXT_TYPES:
        if sniffed is not None:
            return False, f"looks like a {sniffed} file, not text"
        try:
            content[:65536].decode("utf-8")
        except UnicodeDecodeError:
            return False, "not valid UTF-8 text"
        return True, None

    return True, None
