from __future__ import annotations

import json
import shutil
from pathlib import Path

import pytest

from src.services.github_target_private_backup_evidence_gate import (
    load_latest_github_target_controlled_execution_preflight,
    load_latest_github_target_private_backup_evidence_gate,
    preflight_github_target_owner_response_submission,
    validate_github_target_safe_credential_evidence_refs,
)
from src.services.snapshot_paths import default_security_dir


def test_load_github_target_private_backup_evidence_gate_from_committed_snapshots():
    snapshot = load_latest_github_target_private_backup_evidence_gate()

    assert snapshot["schema_version"] == "github_target_private_backup_evidence_gate_v1"
    assert (
        snapshot["mode"] == "owner_authorized_controlled_execution_no_secret_plaintext"
    )
    assert snapshot["status"] == "owner_authorized_controlled_execution_preflight_ready"
    assert snapshot["summary"]["target_decision_count"] == 10
    assert snapshot["summary"]["approval_required_target_count"] == 9
    assert snapshot["summary"]["github_connector_owner_visible_repository_count"] == 4
    assert (
        snapshot["summary"]["github_connector_owner_visible_private_repository_count"]
        == 4
    )
    assert snapshot["summary"]["github_connector_readback_count"] == 9
    assert snapshot["summary"]["github_connector_private_visibility_count"] == 4
    assert snapshot["summary"]["github_connector_not_found_or_inaccessible_count"] == 5
    assert snapshot["summary"]["github_missing_target_resolution_count"] == 5
    assert (
        snapshot["summary"]["github_missing_target_gitea_source_candidate_count"] == 3
    )
    assert (
        snapshot["summary"][
            "github_missing_target_internal_remote_source_candidate_count"
        ]
        == 2
    )
    assert (
        snapshot["summary"]["github_missing_target_local_worktree_candidate_count"] == 5
    )
    assert (
        snapshot["summary"]["github_missing_target_canonical_source_ambiguous_count"]
        == 5
    )
    assert (
        snapshot["summary"]["github_missing_target_create_private_repo_ready_count"]
        == 0
    )
    assert snapshot["summary"]["github_missing_target_refs_sync_ready_count"] == 0
    assert (
        snapshot["summary"][
            "github_missing_target_create_private_repo_authorized_count"
        ]
        == 5
    )
    assert snapshot["summary"]["github_missing_target_refs_sync_authorized_count"] == 5
    assert snapshot["summary"]["github_controlled_execution_preflight_ready"] is False
    assert snapshot["summary"]["github_write_channel_ready"] is False
    assert snapshot["summary"]["github_create_repo_channel_ready"] is False
    assert snapshot["summary"]["github_refs_sync_channel_ready"] is False
    assert (
        snapshot["summary"]["github_missing_target_controlled_apply_ready_count"] == 0
    )
    assert snapshot["summary"]["github_missing_target_blocked_preflight_count"] == 5
    assert snapshot["summary"]["github_missing_target_github_404_count"] == 0
    assert snapshot["summary"]["github_account_status"] == "suspended"
    assert snapshot["summary"]["github_account_suspended"] is True
    assert snapshot["summary"]["github_api_forbidden_count"] == 6
    assert (
        snapshot["summary"]["github_operator_unblock_internal_governance_ready"]
        is True
    )
    assert (
        snapshot["summary"]["github_operator_unblock_mcp_evidence_packet_count"] == 1
    )
    assert snapshot["summary"]["github_operator_unblock_rag_evidence_ref_count"] == 5
    assert (
        snapshot["summary"]["github_operator_unblock_km_writeback_ready_count"] == 1
    )
    assert (
        snapshot["summary"]["github_operator_unblock_playbook_writeback_ready_count"]
        == 1
    )
    assert (
        snapshot["summary"]["github_operator_unblock_timeline_log_ready_count"] == 1
    )
    assert snapshot["summary"]["github_operator_unblock_logbook_entry_count"] == 1
    assert snapshot["summary"]["github_operator_unblock_github_write_performed"] is False
    assert snapshot["summary"]["private_backup_verified_count"] == 4
    assert snapshot["summary"]["private_visibility_verified_count"] == 4
    assert snapshot["summary"]["safe_credential_required_count"] == 9
    assert snapshot["summary"]["safe_credential_accepted_evidence_count"] == 0
    assert snapshot["summary"]["safe_credential_evidence_intake_ready"] is True
    assert (
        snapshot["summary"]["safe_credential_required_redacted_evidence_ref_count"] == 9
    )
    assert snapshot["summary"]["safe_credential_evidence_ref_rule_count"] == 5
    assert snapshot["summary"]["safe_credential_redaction_example_count"] == 5
    assert snapshot["summary"]["safe_credential_forbidden_payload_count"] == 15
    assert snapshot["summary"]["safe_credential_quarantine_lane_count"] == 1
    assert snapshot["summary"]["safe_credential_raw_payload_storage_allowed"] is False
    assert snapshot["summary"]["safe_credential_reviewer_validation_ready"] is True
    assert (
        snapshot["summary"]["safe_credential_reviewer_validation_required_field_count"]
        == 7
    )
    assert snapshot["summary"]["safe_credential_reviewer_validation_passed_count"] == 0
    assert (
        snapshot["summary"]["safe_credential_reviewer_validation_quarantined_count"]
        == 0
    )
    assert snapshot["summary"]["owner_response_request_ready"] is True
    assert snapshot["summary"]["owner_response_required_response_item_count"] == 9
    assert snapshot["summary"]["owner_response_requested_template_count"] == 9
    assert snapshot["summary"]["owner_response_template_count"] == 9
    assert snapshot["summary"]["owner_response_allowed_response_field_count"] == 25
    assert snapshot["summary"]["owner_response_forbidden_payload_count"] == 15
    assert snapshot["summary"]["owner_response_collection_check_count"] == 6
    assert snapshot["summary"]["owner_response_intake_preflight_check_count"] == 6
    assert snapshot["summary"]["owner_response_request_execution_authorized"] is False
    assert (
        snapshot["summary"]["github_target_owner_response_handoff_not_approval"] is True
    )
    assert snapshot["summary"]["owner_execution_authorization_received_count"] == 1
    assert snapshot["summary"]["owner_execution_authorized_target_count"] == 9
    assert (
        snapshot["summary"]["owner_execution_authorization_status"]
        == "owner_authorized_controlled_execution"
    )
    assert (
        snapshot["summary"]["owner_execution_authorization_source"]
        == "chat_authorization_2026-06-28_full_hard_gate_open"
    )
    assert (
        snapshot["summary"]["owner_execution_controlled_preflight_required_count"] == 9
    )
    assert snapshot["summary"]["post_execution_readback_required_count"] == 9
    assert snapshot["summary"]["execution_ready_count"] == 9
    assert snapshot["summary"]["blocked_target_count"] == 0
    assert snapshot["summary"]["public_repo_allowed"] is False
    assert snapshot["summary"]["repo_creation_authorized"] is True
    assert snapshot["summary"]["visibility_change_authorized"] is True
    assert snapshot["summary"]["refs_sync_authorized"] is True
    assert snapshot["summary"]["workflow_trigger_authorized"] is True
    assert snapshot["summary"]["github_primary_switch_authorized"] is False
    assert snapshot["summary"]["secret_value_collection_allowed"] is False
    assert snapshot["operation_boundaries"]["read_only_api_allowed"] is True
    assert snapshot["operation_boundaries"]["github_api_write_allowed"] is True
    assert snapshot["operation_boundaries"]["repo_creation_allowed"] is True
    assert snapshot["operation_boundaries"]["visibility_change_allowed"] is True
    assert snapshot["operation_boundaries"]["refs_sync_allowed"] is True
    assert snapshot["operation_boundaries"]["workflow_trigger_allowed"] is True
    assert snapshot["operation_boundaries"]["github_write_channel_ready"] is False
    assert snapshot["operation_boundaries"]["controlled_apply_allowed"] is False
    assert snapshot["operation_boundaries"]["secret_value_collection_allowed"] is False
    assert (
        snapshot["operation_boundaries"]["private_clone_url_collection_allowed"]
        is False
    )
    assert snapshot["authorization_flags"]["repo_creation_authorized"] is True
    assert snapshot["authorization_flags"]["visibility_change_authorized"] is True
    assert snapshot["authorization_flags"]["refs_sync_authorized"] is True
    assert snapshot["authorization_flags"]["workflow_trigger_authorized"] is True
    assert snapshot["authorization_flags"]["github_primary_switch_authorized"] is False
    assert (
        snapshot["authorization_flags"]["private_clone_url_collection_allowed"] is False
    )
    intake = snapshot["owner_response_intake_readiness"]
    assert (
        intake["status"]
        == "ready_to_collect_read_only_owner_response_not_authorization"
    )
    assert intake["request_ready"] is True
    assert intake["required_response_item_count"] == 9
    assert intake["requested_template_count"] == 9
    assert intake["response_template_count"] == 9
    assert intake["allowed_response_field_count"] == 25
    assert intake["forbidden_payload_count"] == 15
    assert intake["collection_check_count"] == 6
    assert intake["intake_preflight_check_count"] == 6
    assert intake["acceptance_check_count"] == 8
    assert intake["execution_authorized"] is False
    assert intake["not_approval"] is True
    assert "private_clone_url_credential" in intake["forbidden_payloads"]
    assert "read_only_markdown_response" in intake["allowed_submission_modes"]
    assert "create_github_repo" in intake["still_forbidden"]
    safe_credential_intake = snapshot["safe_credential_evidence_intake_readiness"]
    assert (
        safe_credential_intake["status"]
        == "ready_to_collect_redacted_evidence_refs_not_credentials"
    )
    assert safe_credential_intake["intake_ready"] is True
    assert safe_credential_intake["required_target_count"] == 9
    assert safe_credential_intake["accepted_evidence_count"] == 0
    assert safe_credential_intake["required_redacted_evidence_ref_count"] == 9
    assert safe_credential_intake["evidence_ref_rule_count"] == 5
    assert safe_credential_intake["redaction_example_count"] == 5
    assert safe_credential_intake["forbidden_payload_count"] == 15
    assert safe_credential_intake["quarantine_lane_count"] == 1
    assert "quarantine_sensitive_payload" in safe_credential_intake["quarantine_lanes"]
    assert safe_credential_intake["stored_raw_payload_allowed"] is False
    assert safe_credential_intake["secret_value_collection_allowed"] is False
    assert safe_credential_intake["private_clone_url_collection_allowed"] is False
    assert safe_credential_intake["credential_value_collection_allowed"] is False
    assert safe_credential_intake["execution_authorized"] is False
    assert safe_credential_intake["not_approval"] is True
    assert (
        "private_clone_url_credential" in safe_credential_intake["forbidden_payloads"]
    )
    assert "repo_archive" in safe_credential_intake["forbidden_payloads"]
    assert "git_object_pack" in safe_credential_intake["forbidden_payloads"]
    assert (
        safe_credential_intake["reviewer_validation_endpoint"]
        == "/api/v1/agents/github-target-safe-credential-evidence-reviewer-validation/validate-redacted-refs"
    )
    assert (
        safe_credential_intake["reviewer_validation_mode"]
        == "validate_redacted_evidence_refs_only_no_persist_no_github_write"
    )
    assert safe_credential_intake["reviewer_validation_ready"] is True
    assert safe_credential_intake["reviewer_validation_required_field_count"] == 7
    assert (
        "redacted_evidence_refs"
        in safe_credential_intake["reviewer_validation_required_fields"]
    )
    assert (
        "accept_redacted_evidence_refs_for_reviewer_validation"
        in safe_credential_intake["reviewer_validation_allowed_decisions"]
    )
    assert safe_credential_intake["reviewer_validation_no_persist"] is True
    assert (
        "redacted_metadata_pointer"
        in safe_credential_intake["allowed_evidence_ref_types"]
    )
    first_redaction_example = safe_credential_intake["redaction_examples"][0]
    assert first_redaction_example["example_id"] == "redaction-github-target-doc-ref"
    assert first_redaction_example["stored_raw_payload_allowed"] is False
    assert first_redaction_example["execution_authorized"] is False

    controlled_preflight = snapshot["controlled_execution_preflight"]
    assert (
        controlled_preflight["schema_version"]
        == "github_target_controlled_execution_preflight_v1"
    )
    assert controlled_preflight["status"] == (
        "blocked_github_account_suspended_and_write_channel_required"
    )
    assert controlled_preflight["authorization_ready"] is True
    assert controlled_preflight["preflight_ready"] is False
    assert controlled_preflight["github_write_channel_ready"] is False
    assert controlled_preflight["github_account_status"] == "suspended"
    assert controlled_preflight["github_account_suspended"] is True
    assert controlled_preflight["github_api_forbidden_count"] == 6
    assert controlled_preflight["github_create_repo_channel_ready"] is False
    assert controlled_preflight["github_refs_sync_channel_ready"] is False
    assert controlled_preflight["source_preflight_ready_count"] == 5
    assert controlled_preflight["github_connector_missing_target_404_count"] == 0
    assert controlled_preflight["blocked_preflight_target_count"] == 5
    assert controlled_preflight["controlled_apply_ready_count"] == 0
    assert controlled_preflight["operator_unblock_required"] is True
    assert (
        controlled_preflight["operator_unblock_status"]
        == "github_account_suspended_external_action_required"
    )
    operator_unblock = controlled_preflight["operator_unblock"]
    assert operator_unblock["required"] is True
    assert operator_unblock["github_account_status"] == "suspended"
    assert operator_unblock["github_account_suspended"] is True
    assert operator_unblock["github_api_forbidden_count"] == 6
    assert (
        "complete_github_account_suspension_appeal_or_provide_authorized_writable_namespace"
        in operator_unblock["required_actions"]
    )
    assert "gh api /user --jq '{login:.login}'" in operator_unblock["recheck_commands"]
    assert (
        "do_not_paste_pat_token_private_key_cookie_session_or_authorization_header"
        in operator_unblock["still_forbidden"]
    )
    assert (
        controlled_preflight["operation_boundaries"]["controlled_apply_allowed"]
        is False
    )
    assert (
        controlled_preflight["operation_boundaries"]["repo_creation_allowed"] is False
    )
    assert controlled_preflight["operation_boundaries"]["refs_sync_allowed"] is False
    assert controlled_preflight["tool_channel_readback"]["gh_cli_write_ready"] is False
    assert (
        controlled_preflight["tool_channel_readback"][
            "github_connector_create_repo_ready"
        ]
        is False
    )
    governance_writeback = controlled_preflight["internal_governance_writeback"]
    assert (
        governance_writeback["schema_version"]
        == "github_operator_unblock_governance_closure_v1"
    )
    assert governance_writeback["ready"] is True
    assert governance_writeback["github_account_status"] == "suspended"
    assert governance_writeback["github_write_channel_ready"] is False
    assert governance_writeback["mcp_evidence_packet_count"] == 1
    assert governance_writeback["rag_evidence_ref_count"] == 5
    assert governance_writeback["km_writeback_ready_count"] == 1
    assert governance_writeback["playbook_writeback_ready_count"] == 1
    assert governance_writeback["timeline_log_ready_count"] == 1
    assert governance_writeback["logbook_entry_count"] == 1
    assert governance_writeback["github_write_performed"] is False
    assert governance_writeback["gh_cli_called"] is False
    assert governance_writeback["github_api_called"] is False
    assert governance_writeback["secret_values_collected"] is False
    assert (
        governance_writeback["operation_boundaries"]["github_api_allowed"] is False
    )
    assert governance_writeback["operation_boundaries"]["gh_cli_allowed"] is False
    assert (
        governance_writeback["operation_boundaries"]["runtime_write_allowed"] is False
    )
    assert (
        governance_writeback["operation_boundaries"]["raw_session_read_allowed"]
        is False
    )

    targets = {target["github_repo"]: target for target in snapshot["targets"]}
    assert targets["owenhytsai/awoooi"]["visibility_evidence_status"] == (
        "verified_private_by_github_connector_readback"
    )
    assert targets["owenhytsai/awoooi"]["private_backup_verified"] is True
    assert targets["owenhytsai/awoooi"]["github_connector_visibility"] == "private"
    assert (
        targets["owenhytsai/awoooi"]["owner_response_template_id"]
        == "target-awoooi-refs-blocked"
    )
    assert (
        targets["owenhytsai/awoooi"]["owner_response_submission_status"]
        == "waiting_owner_response"
    )
    assert (
        targets["owenhytsai/awoooi"]["safe_credential_evidence_submission_status"]
        == "owner_execution_authorized_post_apply_readback_pending"
    )
    assert (
        "redacted_metadata_pointer"
        in targets["owenhytsai/awoooi"]["safe_credential_allowed_evidence_ref_types"]
    )
    assert (
        targets["owenhytsai/awoooi"]["safe_credential_raw_payload_storage_allowed"]
        is False
    )
    assert (
        targets["owenhytsai/awoooi"][
            "safe_credential_private_clone_url_collection_allowed"
        ]
        is False
    )
    assert (
        targets["owenhytsai/awoooi"]["safe_credential_secret_value_collection_allowed"]
        is False
    )
    assert targets["owenhytsai/awoooi"]["owner_response_execution_authorized"] is False
    assert targets["owenhytsai/awoooi"]["owner_execution_authorized"] is True
    assert targets["owenhytsai/awoooi"]["controlled_execution_ready"] is True
    assert targets["owenhytsai/awoooi"]["refs_sync_ready"] is True
    assert targets["owenhytsai/awoooi"]["blockers"] == []
    assert (
        "canonical_source"
        in targets["owenhytsai/awoooi"]["owner_response_required_fields"]
    )
    assert targets["owenhytsai/ewoooc"]["visibility_evidence_status"] == (
        "blocked_private_or_absent_not_verified"
    )
    assert targets["owenhytsai/ewoooc"]["missing_target_source_resolution_status"] == (
        "blocked_canonical_source_ambiguous"
    )
    assert targets["owenhytsai/ewoooc"]["missing_target_gitea_repo"] == "wooo/ewoooc"
    assert (
        targets["owenhytsai/ewoooc"]["missing_target_create_private_repo_ready"]
        is False
    )
    assert targets["owenhytsai/ewoooc"]["missing_target_refs_sync_ready"] is False
    assert targets["owenhytsai/ewoooc"]["repo_creation_authorized"] is True
    assert targets["owenhytsai/ewoooc"]["refs_sync_authorized"] is True
    assert targets["owenhytsai/ewoooc"]["execution_ready"] is True
    assert targets["owenhytsai/ewoooc"]["controlled_apply_ready"] is False
    assert targets["owenhytsai/ewoooc"]["source_preflight_ready"] is True
    assert targets["owenhytsai/ewoooc"]["canonical_source_ready"] is True
    assert (
        targets["owenhytsai/ewoooc"]["canonical_source_sha"]
        == "f3e412cd211f5e4601204b256aeb95eae073b441"
    )
    assert (
        "github_account_suspended_403"
        in targets["owenhytsai/ewoooc"]["controlled_apply_blockers"]
    )
    assert targets["owenhytsai/ewoooc"]["private_backup_verified"] is False
    assert (
        targets["owenhytsai/ewoooc"]["owner_response_template_id"]
        == "target-ewoooc-private-or-new"
    )
    assert (
        "approve_new_target_creation_candidate"
        in targets["owenhytsai/ewoooc"]["owner_response_acceptable_decisions"]
    )
    assert targets["owenhytsai/VibeWork"][
        "missing_target_source_resolution_status"
    ] == ("blocked_product_boundary_and_local_divergence")
    assert (
        targets["owenhytsai/VibeWork"]["missing_target_gitea_repo"] == "wooo/vibework"
    )
    assert targets["nexu-io/open-design"]["visibility_evidence_status"] == (
        "external_scope_not_backup_target"
    )
    assert targets["nexu-io/open-design"]["owner_response_template_id"] is None
    assert (
        targets["nexu-io/open-design"]["owner_response_submission_status"]
        == "not_required"
    )
    assert (
        targets["nexu-io/open-design"]["safe_credential_evidence_submission_status"]
        == "not_required"
    )
    assert (
        targets["nexu-io/open-design"]["safe_credential_allowed_evidence_ref_types"]
        == []
    )


def test_load_github_target_controlled_execution_preflight_from_committed_snapshot():
    preflight = load_latest_github_target_controlled_execution_preflight()

    assert (
        preflight["schema_version"] == "github_target_controlled_execution_preflight_v1"
    )
    assert (
        preflight["status"]
        == "blocked_github_account_suspended_and_write_channel_required"
    )
    assert preflight["authorization_ready"] is True
    assert preflight["preflight_ready"] is False
    assert preflight["github_write_channel_ready"] is False
    assert preflight["github_account_status"] == "suspended"
    assert preflight["github_account_suspended"] is True
    assert preflight["github_api_forbidden_count"] == 6
    assert preflight["github_create_repo_channel_ready"] is False
    assert preflight["github_refs_sync_channel_ready"] is False
    assert preflight["source_preflight_ready_count"] == 5
    assert preflight["controlled_apply_ready_count"] == 0
    assert preflight["blocked_preflight_target_count"] == 5
    assert preflight["github_connector_missing_target_404_count"] == 0
    assert preflight["operation_boundaries"]["controlled_apply_allowed"] is False
    assert preflight["operation_boundaries"]["secret_value_collection_allowed"] is False
    assert "private_clone_url_credential" in preflight["still_forbidden"]
    target_by_repo = {target["github_repo"]: target for target in preflight["targets"]}
    assert (
        target_by_repo["owenhytsai/bitan-pharmacy"]["controlled_apply_ready"] is False
    )
    assert (
        "github_account_suspended_403"
        in target_by_repo["owenhytsai/bitan-pharmacy"]["blockers"]
    )
    assert (
        target_by_repo["owenhytsai/bitan-pharmacy"]["canonical_source_sha"]
        == "e122c8cbd9522999fd9844c2b63790fadcc89c20"
    )
    assert target_by_repo["owenhytsai/VibeWork"]["refs_sync_apply_ready"] is False


def test_github_target_private_backup_gate_rejects_runtime_authorization(tmp_path):
    _copy_security_snapshots(tmp_path)
    owner_response_path = (
        tmp_path / "github-target-owner-decision-response.snapshot.json"
    )
    owner_response = json.loads(owner_response_path.read_text(encoding="utf-8"))
    owner_response["summary"]["repo_creation_authorized"] = True
    owner_response_path.write_text(json.dumps(owner_response), encoding="utf-8")

    with pytest.raises(ValueError, match="boundary flags"):
        load_latest_github_target_private_backup_evidence_gate(tmp_path)


def test_github_target_private_backup_gate_rejects_owner_response_execution_packet(
    tmp_path,
):
    _copy_security_snapshots(tmp_path)
    owner_response_path = (
        tmp_path / "github-target-owner-decision-response.snapshot.json"
    )
    owner_response = json.loads(owner_response_path.read_text(encoding="utf-8"))
    owner_response["owner_response_request_packet"]["execution_authorized"] = True
    owner_response_path.write_text(json.dumps(owner_response), encoding="utf-8")

    with pytest.raises(ValueError, match="owner response request packet"):
        load_latest_github_target_private_backup_evidence_gate(tmp_path)


def test_github_target_private_backup_gate_rejects_raw_payload_redaction_example(
    tmp_path,
):
    _copy_security_snapshots(tmp_path)
    owner_response_path = (
        tmp_path / "github-target-owner-decision-response.snapshot.json"
    )
    owner_response = json.loads(owner_response_path.read_text(encoding="utf-8"))
    owner_response["owner_response_redaction_examples"][0][
        "stored_raw_payload_allowed"
    ] = True
    owner_response_path.write_text(json.dumps(owner_response), encoding="utf-8")

    with pytest.raises(ValueError, match="redaction examples"):
        load_latest_github_target_private_backup_evidence_gate(tmp_path)


def test_github_target_private_backup_gate_requires_safe_credential_blockers(
    tmp_path,
):
    _copy_security_snapshots(tmp_path)
    owner_response_path = (
        tmp_path / "github-target-owner-decision-response.snapshot.json"
    )
    owner_response = json.loads(owner_response_path.read_text(encoding="utf-8"))
    forbidden_payloads = owner_response["owner_response_request_packet"][
        "forbidden_payloads"
    ]
    owner_response["owner_response_request_packet"]["forbidden_payloads"] = [
        payload
        for payload in forbidden_payloads
        if payload != "private_clone_url_credential"
    ]
    owner_response_path.write_text(json.dumps(owner_response), encoding="utf-8")

    with pytest.raises(ValueError, match="forbidden payloads"):
        load_latest_github_target_private_backup_evidence_gate(tmp_path)


def test_github_target_private_backup_gate_requires_decision_rollup_consistency(
    tmp_path,
):
    _copy_security_snapshots(tmp_path)
    decision_path = tmp_path / "github-target-decision.snapshot.json"
    decision = json.loads(decision_path.read_text(encoding="utf-8"))
    decision["decision_count"] = 999
    decision_path.write_text(json.dumps(decision), encoding="utf-8")

    with pytest.raises(ValueError, match="decision_count"):
        load_latest_github_target_private_backup_evidence_gate(tmp_path)


def test_github_target_private_backup_gate_rejects_missing_source_write_flags(tmp_path):
    _copy_security_snapshots(tmp_path)
    readiness_path = tmp_path / "github-target-missing-source-readiness.snapshot.json"
    readiness = json.loads(readiness_path.read_text(encoding="utf-8"))
    readiness["summary"]["repo_creation_performed"] = True
    readiness_path.write_text(json.dumps(readiness), encoding="utf-8")

    with pytest.raises(
        ValueError, match="missing source readiness must remain read-only"
    ):
        load_latest_github_target_private_backup_evidence_gate(tmp_path)


def test_github_target_private_backup_gate_rejects_execution_authorization_secrets(
    tmp_path,
):
    _copy_security_snapshots(tmp_path)
    authorization_path = (
        tmp_path / "github-target-owner-execution-authorization.snapshot.json"
    )
    authorization = json.loads(authorization_path.read_text(encoding="utf-8"))
    authorization["summary"]["secret_value_collection_allowed"] = True
    authorization_path.write_text(json.dumps(authorization), encoding="utf-8")

    with pytest.raises(ValueError, match="forbidden authorization flags"):
        load_latest_github_target_private_backup_evidence_gate(tmp_path)


def test_github_target_private_backup_gate_rejects_false_preflight_write_ready(
    tmp_path,
):
    _copy_security_snapshots(tmp_path)
    preflight_path = (
        tmp_path / "github-target-controlled-execution-preflight.snapshot.json"
    )
    preflight = json.loads(preflight_path.read_text(encoding="utf-8"))
    preflight["summary"]["github_create_repo_channel_ready"] = True
    preflight_path.write_text(json.dumps(preflight), encoding="utf-8")

    with pytest.raises(ValueError, match="preflight must not claim write readiness"):
        load_latest_github_target_private_backup_evidence_gate(tmp_path)


def test_github_target_owner_response_preflight_accepts_redacted_evidence_refs():
    preflight = preflight_github_target_owner_response_submission(
        _valid_owner_response_submission()
    )

    assert (
        preflight["schema_version"]
        == "github_target_owner_response_intake_preflight_v1"
    )
    assert preflight["status"] == "ready_for_read_only_owner_response_intake"
    assert (
        preflight["mode"] == "validate_owner_response_only_no_persist_no_github_write"
    )
    assert preflight["summary"]["candidate_response_item_count"] == 1
    assert preflight["summary"]["preflight_passed_response_item_count"] == 1
    assert preflight["summary"]["preflight_blocked_response_item_count"] == 0
    assert preflight["summary"]["owner_response_received_count"] == 0
    assert preflight["summary"]["owner_response_accepted_count"] == 0
    assert preflight["summary"]["safe_credential_accepted_evidence_count"] == 0
    assert preflight["summary"]["github_api_write_allowed"] is False
    assert preflight["summary"]["repo_creation_authorized"] is False
    assert preflight["summary"]["refs_sync_authorized"] is False
    assert preflight["operation_boundaries"]["persist_submission_allowed"] is False
    assert preflight["operation_boundaries"]["github_api_write_allowed"] is False
    assert (
        preflight["operation_boundaries"]["private_clone_url_collection_allowed"]
        is False
    )
    assert (
        preflight["authorization_flags"]["owner_response_execution_authorized"] is False
    )
    assert preflight["responses"][0]["accepted_for_read_only_intake"] is True
    assert preflight["responses"][0]["owner_response_received"] is False
    assert preflight["responses"][0]["owner_response_accepted"] is False


def test_github_target_owner_response_preflight_blocks_credentials_and_commands():
    submission = _valid_owner_response_submission()
    submission["responses"][0][
        "private_clone_url_credential"
    ] = "https://owner:ghp_1234567890abcdefghijklmnopqrstu@github.com/owenhytsai/awoooi.git"
    submission["responses"][0][
        "repo_creation_command"
    ] = "gh repo create owenhytsai/awoooi --private"

    preflight = preflight_github_target_owner_response_submission(submission)

    assert preflight["status"] == "blocked_owner_response_intake_preflight"
    assert preflight["summary"]["candidate_response_item_count"] == 1
    assert preflight["summary"]["preflight_passed_response_item_count"] == 0
    assert preflight["summary"]["preflight_blocked_response_item_count"] == 1
    assert preflight["summary"]["forbidden_payload_hit_count"] >= 3
    assert preflight["summary"]["owner_response_received_count"] == 0
    assert preflight["summary"]["owner_response_accepted_count"] == 0
    assert preflight["summary"]["github_api_write_allowed"] is False
    response = preflight["responses"][0]
    assert response["accepted_for_read_only_intake"] is False
    assert "forbidden_payload_detected" in response["blockers"]
    assert "unsupported_response_fields" in response["blockers"]
    assert response["execution_authorized"] is False
    assert response["repo_creation_authorized"] is False


def test_github_target_safe_credential_evidence_review_accepts_redacted_refs():
    payload = validate_github_target_safe_credential_evidence_refs(
        _valid_safe_credential_evidence_ref_submission()
    )

    assert (
        payload["schema_version"]
        == "github_target_safe_credential_evidence_ref_validation_result_v1"
    )
    assert (
        payload["status"]
        == "accepted_for_readonly_safe_credential_evidence_review_only"
    )
    assert (
        payload["mode"]
        == "validate_redacted_evidence_refs_only_no_persist_no_github_write"
    )
    assert payload["accepted_for_readonly_review"] is True
    assert payload["reviewer_validation_passed"] is True
    assert payload["summary"]["candidate_evidence_ref_item_count"] == 1
    assert payload["summary"]["reviewer_validation_passed_count"] == 1
    assert payload["summary"]["safe_credential_evidence_submission_accepted_count"] == 1
    assert payload["summary"]["safe_credential_accepted_evidence_count"] == 0
    assert payload["summary"]["private_backup_verified_count"] == 4
    assert payload["summary"]["execution_ready_count"] == 9
    assert payload["summary"]["blocked_target_count"] == 0
    assert payload["boundaries"]["payload_persisted"] is False
    assert payload["boundaries"]["safe_credential_accepted_updated"] is False
    assert payload["boundaries"]["runtime_execution_authorized"] is False
    assert payload["boundaries"]["private_clone_url_collection_allowed"] is False
    assert (
        payload["evidence_ref_submissions"][0]["accepted_for_readonly_review"] is True
    )
    assert (
        payload["evidence_ref_submissions"][0]["safe_credential_evidence_accepted"]
        is False
    )


def test_github_target_safe_credential_evidence_review_quarantines_sensitive_refs():
    submission = _valid_safe_credential_evidence_ref_submission()
    secret_url = (
        "https://owner:ghp_1234567890abcdefghijklmnopqrstu@github.com/"
        "owenhytsai/awoooi.git"
    )
    submission["evidence_ref_submissions"][0]["redacted_evidence_refs"] = [secret_url]
    submission["evidence_ref_submissions"][0]["repo_archive"] = "repo_archive"

    payload = validate_github_target_safe_credential_evidence_refs(submission)

    assert payload["status"] == "quarantine_sensitive_payload"
    assert payload["quarantined"] is True
    assert payload["summary"]["reviewer_validation_quarantined_count"] == 1
    assert payload["summary"]["safe_credential_accepted_evidence_count"] == 0
    assert (
        payload["evidence_ref_submissions"][0]["accepted_for_readonly_review"] is False
    )
    assert (
        "forbidden_payload_detected"
        in payload["evidence_ref_submissions"][0]["blockers"]
    )
    assert (
        "unsafe_evidence_ref_detected"
        in payload["evidence_ref_submissions"][0]["blockers"]
    )
    assert secret_url not in str(payload)
    assert "ghp_1234567890abcdefghijklmnopqrstu" not in str(payload)


def test_github_target_safe_credential_evidence_review_rejects_runtime_requests():
    submission = _valid_safe_credential_evidence_ref_submission()
    submission["evidence_ref_submissions"][0]["requested_actions"] = ["refs_sync"]

    payload = validate_github_target_safe_credential_evidence_refs(submission)

    assert payload["status"] == "reject_runtime_action_request"
    assert payload["runtime_action_rejected"] is True
    assert payload["summary"]["runtime_action_rejected_count"] == 1
    assert payload["summary"]["safe_credential_accepted_evidence_count"] == 0
    assert payload["boundaries"]["refs_sync_authorized"] is False
    assert (
        "runtime_action_request_detected"
        in payload["evidence_ref_submissions"][0]["blockers"]
    )


def _copy_security_snapshots(tmp_path: Path) -> None:
    source_dir = default_security_dir(Path(__file__))
    for filename in (
        "github-target-decision.snapshot.json",
        "github-target-owner-decision-response.snapshot.json",
        "github-target-repo-approval-package.snapshot.json",
        "github-target-probe.snapshot.json",
        "github-target-connector-readback.snapshot.json",
        "github-target-missing-source-readiness.snapshot.json",
        "github-target-owner-execution-authorization.snapshot.json",
        "github-target-controlled-execution-preflight.snapshot.json",
    ):
        shutil.copy(source_dir / filename, tmp_path / filename)


def _valid_owner_response_submission() -> dict[str, object]:
    return {
        "submission_mode": "read_only_markdown_response",
        "responses": [
            {
                "template_id": "target-awoooi-refs-blocked",
                "github_repo": "owenhytsai/awoooi",
                "owner_role_or_team": "platform-owner",
                "decision": "hold_pending_refs_truth",
                "decision_reason": "Need refs truth review before any sync action.",
                "affected_scope": "awoooi github backup target",
                "redacted_evidence_refs": [
                    "docs/security/GITEA-GITHUB-MIGRATION-SNAPSHOT.md",
                    "docs/security/source-control-ref-detail-diff.snapshot.json",
                ],
                "evidence_refs": [
                    "docs/security/source-control-workflow-secret-name-inventory.snapshot.json"
                ],
                "followup_owner": "platform-owner",
                "rollback_owner": "platform-owner",
                "maintenance_window": "not_authorized",
                "validation_plan": "read-only refs truth review only",
                "canonical_source": "gitea_main",
                "github_target_disposition": "existing_private_candidate",
                "visibility_review_owner": "platform-owner",
                "refs_truth_review_owner": "platform-owner",
            }
        ],
    }


def _valid_safe_credential_evidence_ref_submission() -> dict[str, object]:
    return {
        "submission_mode": "redacted_metadata_pointer",
        "evidence_ref_submissions": [
            {
                "template_id": "target-awoooi-refs-blocked",
                "github_repo": "owenhytsai/awoooi",
                "reviewer_role_or_team": "platform-owner",
                "decision": "accept_redacted_evidence_refs_for_reviewer_validation",
                "decision_reason": "Refs are redacted metadata pointers only.",
                "evidence_ref_type": "redacted_metadata_pointer",
                "redacted_evidence_refs": [
                    "docs/security/GITEA-GITHUB-MIGRATION-SNAPSHOT.md",
                    "owner-metadata:github-target-awoooi-redacted-ref",
                ],
                "affected_scope": "awoooi github private backup target",
                "followup_owner": "platform-owner",
                "validation_plan": "review redacted refs only; no GitHub write",
            }
        ],
    }
