from __future__ import annotations

import datetime
import hashlib
import json
from pathlib import Path

ROOT = Path(__file__).resolve().parents[1]
OUT = ROOT / "results" / "row26_refs" / "result.json"
MAIN_TEX = ROOT / "main.tex"
MAIN_PDF = ROOT / "main.pdf"

EXPECTED_MAIN_TEX_SHA256 = "fd4fe7cf9a0d42e9a9a1def50d49c4a03d8fcd6772f857cc5a269e183986e34a"
EXPECTED_MAIN_PDF_SHA256 = "77b1fd720821e0398337a6a7fceed570dc50093534fe9b60795a1524e4a0cf54"

REQUIRED_PROVENANCE = [
    "research/zero_state/ZS_FOUNDATION_SPEC.md",
    "research/swf_ism/SWF_ISM_FOUNDATION_SPEC.md",
    "research/answf/ANSWF_EFT_POSITIVITY_SPEC.md",
    "research/sanswf/SANSWF_SYMMETRY_STABILITY_SPEC.md",
    "research/utfanswf_embedding/UTFANSWF_EMBEDDING_SPEC.md",
    "research/row19/ROW19_EXECUTABLE_SCOPE_V23.md",
    "research/h0_extended/UTFANSWF_H0_Master_Record_v1.txt",
    "research/jwst_diagnostic/README.md",
    "research/row24/ROW24_AI_EXECUTABLE_SCOPE_V23.md",
    "research/row25/ROW25_STRESS_EXECUTABLE_SCOPE_V23.md",
    "README_ROWS27_28_RESEARCH_EXTENSION.txt",
    "README_ROW29_RESULT04_RESEARCH_EXTENSION.txt",
]

PLACEHOLDER_PATTERNS = ["TODO", "TBD", "XXX", "??"]


def utc_now_z() -> str:
    return datetime.datetime.now(datetime.UTC).isoformat(timespec="seconds").replace("+00:00", "Z")


def sha256(path: Path) -> str | None:
    if not path.exists():
        return None
    h = hashlib.sha256()
    with path.open("rb") as f:
        for chunk in iter(lambda: f.read(1024 * 1024), b""):
            h.update(chunk)
    return h.hexdigest()


def gate_row26_refs() -> dict:
    tex = MAIN_TEX.read_text(encoding="utf-8", errors="ignore") if MAIN_TEX.exists() else ""
    has_bibliography = any(x in tex for x in ["\\bibliography", "\\begin{thebibliography}", "\\printbibliography"])
    has_ack = "acknowledg" in tex.lower()
    has_copyright = "Ronald L. Alexander" in tex and ("©" in tex or "(c)" in tex.lower())
    placeholder_hits = [p for p in PLACEHOLDER_PATTERNS if p in tex]

    tex_hash = sha256(MAIN_TEX)
    pdf_hash = sha256(MAIN_PDF)
    provenance = {rel: (ROOT / rel).exists() for rel in REQUIRED_PROVENANCE}

    checks = {
        "protected_main_tex_hash_matches": tex_hash == EXPECTED_MAIN_TEX_SHA256,
        "protected_main_pdf_hash_matches": pdf_hash == EXPECTED_MAIN_PDF_SHA256,
        "protected_tex_contains_bibliography": has_bibliography,
        "protected_tex_contains_acknowledgments": has_ack,
        "protected_tex_contains_copyright": has_copyright,
        "protected_tex_has_no_obvious_placeholder_tokens": len(placeholder_hits) == 0,
        "required_bundle_provenance_files_present": all(provenance.values()),
        "v23_final_bibliography_not_overclaimed_complete": True,
    }

    verdict = "PASS" if all(checks.values()) else "FAIL"
    status = (
        "PASS_PROTECTED_PUBLICATION_AND_BUNDLE_PROVENANCE__V23_REFERENCE_CONSOLIDATION_OPEN"
        if verdict == "PASS"
        else "FAIL_PROTECTED_PUBLICATION_OR_BUNDLE_PROVENANCE"
    )

    return {
        "row": 26,
        "gate": "protected_publication_and_bundle_provenance_integrity",
        "signature": "ROW26_V23_BUNDLE_PROVENANCE_SCOPE_v1",
        "context": "LIVE",
        "tier": "Informational",
        "blocking": False,
        "timestamp_utc": utc_now_z(),
        "verdict": verdict,
        "status": status,
        "checks": checks,
        "protected_publication": {
            "main_tex_sha256": tex_hash,
            "main_pdf_sha256": pdf_hash,
            "expected_main_tex_sha256": EXPECTED_MAIN_TEX_SHA256,
            "expected_main_pdf_sha256": EXPECTED_MAIN_PDF_SHA256,
            "historical_source_shell_has_bibliography": has_bibliography,
            "historical_source_shell_has_acknowledgments": has_ack,
            "historical_source_shell_has_copyright": has_copyright,
            "placeholder_hits": placeholder_hits,
        },
        "bundle_provenance_files": provenance,
        "open_boundary": "The final v23 bibliography, citations, acknowledgments, version/date text, and public-facing provenance are a later manuscript task owned by Ronald L. Alexander; this gate does not claim they are complete.",
        "notes": "Informational PASS protects the unchanged publication artifacts and verifies the current bundle provenance shell; final v23 reference consolidation remains open.",
    }


def main() -> None:
    OUT.parent.mkdir(parents=True, exist_ok=True)
    res = gate_row26_refs()
    OUT.write_text(json.dumps(res, indent=2, sort_keys=True), encoding="utf-8")
    print(json.dumps({"row": 26, "status": res.get("status"), "verdict": res.get("verdict")}, indent=2))


if __name__ == "__main__":
    main()
