#!/usr/bin/env python3
"""Independently verify the published PHH before/after fixture with stdlib TOML."""

from __future__ import annotations

import hashlib
import json
from pathlib import Path
import sys
import tomllib

HERE = Path(__file__).resolve().parent
ORIGINAL = HERE / "phh-privacy-example-original.phh"
MINIMIZED = HERE / "phh-privacy-example-minimized.phh"
REPORT = HERE / "phh-privacy-transform-report.json"
CORE_FIELDS = (
    "variant", "antes", "blinds_or_straddles", "bring_in", "small_bet",
    "big_bet", "min_bet", "starting_stacks", "actions",
)
ALLOWED_FIELDS = set(CORE_FIELDS) | {"players", "ante_trimming_status"}
PRIVATE_SENTINELS = (
    "rhea", "noor", "milo", "exampleville", "window table",
    "birthday", "concert", "88421", "rhea@example.invalid",
)


def strip_action_commentary(value: str) -> str:
    for index, character in enumerate(value):
        if (character == "#"
                and (index == 0 or value[index - 1].isspace())
                and (index == len(value) - 1 or value[index + 1].isspace())):
            value = value[:index]
            break
    return " ".join(value.split())


def strategic_payload(document: dict) -> dict:
    payload = {
        field: ([strip_action_commentary(item) for item in document[field]]
                if field == "actions" else document[field])
        for field in CORE_FIELDS if field in document
    }
    payload["ante_trimming_status"] = document.get("ante_trimming_status") is True
    return payload


def sha256(path: Path) -> str:
    return hashlib.sha256(path.read_bytes()).hexdigest()


def main() -> int:
    original = tomllib.loads(ORIGINAL.read_text(encoding="utf-8"))
    minimized_text = MINIMIZED.read_text(encoding="utf-8")
    minimized = tomllib.loads(minimized_text)
    report = json.loads(REPORT.read_text(encoding="utf-8"))

    if strategic_payload(original) != strategic_payload(minimized):
        raise AssertionError("Strategic payload differs after minimization.")
    if set(minimized) - ALLOWED_FIELDS:
        raise AssertionError(f"Unexpected minimized fields: {sorted(set(minimized) - ALLOWED_FIELDS)}")
    if minimized.get("players") != ["Player 1", "Player 2", "Player 3"]:
        raise AssertionError("Player labels were not deterministically pseudonymized.")
    folded = minimized_text.casefold()
    leaked = [value for value in PRIVATE_SENTINELS if value in folded]
    if leaked:
        raise AssertionError(f"Synthetic private sentinels remain: {leaked}")
    if any("#" in action for action in minimized["actions"]):
        raise AssertionError("An action commentary delimiter remains.")
    if report["inputSha256"] != sha256(ORIGINAL) or report["outputSha256"] != sha256(MINIMIZED):
        raise AssertionError("Published fixture hashes differ from the transform report.")
    if report["phhSpecVersion"] != "0.0.2" or report["corePreserved"] is not True:
        raise AssertionError("Unexpected PHH profile or preservation result.")
    expected_removed = [field for field in original if field not in minimized]
    expected_custom = [field for field in original if field.startswith("_")]
    expected_commentaries = sum(
        strip_action_commentary(action) != " ".join(action.split())
        for action in original["actions"]
    )
    if report["fieldsRemoved"] != expected_removed:
        raise AssertionError("Reported removed fields do not match the fixture diff.")
    if report["customFieldsRemoved"] != expected_custom or report["unknownFieldsRemoved"] != []:
        raise AssertionError("Reported custom or unknown fields do not match the fixture.")
    if report["actionCommentariesRemoved"] != expected_commentaries:
        raise AssertionError("Reported commentary-removal count does not match the fixture.")
    if (report["playerMode"] != "pseudonymize" or report["keepAccounting"] is not False
            or report["playerLabelsChanged"] is not True):
        raise AssertionError("Unexpected published transform mode flags.")

    print("Verified PHH v0.0.2 payload, removal report, privacy sentinels, and fixture hashes.")
    return 0


if __name__ == "__main__":
    try:
        raise SystemExit(main())
    except (AssertionError, KeyError, OSError, tomllib.TOMLDecodeError) as error:
        print(f"Verification failed: {error}", file=sys.stderr)
        raise SystemExit(1)
