import pytest
import yaml

from mcard.ptr.runner import CLMRunner


@pytest.fixture
def secured_clm_path(tmp_path):
    """Create a CLM that requires a specific VCard."""
    clm_content = {
        "chapter": {"id": "secure_op", "title": "Secure Operation"},
        "clm": {
            "abstract": {"type": "secure_op"},
            "concrete": {"runtime": "python", "code": "result='ok'"},
            "balanced": {},
            "verification": {
                "pcard_refs": [
                    {"hash": "sha256:auth_token_hash", "purpose": "authenticate"}
                ]
            },
        },
    }
    path = tmp_path / "secure.yaml"
    with open(path, "w") as f:
        yaml.dump(clm_content, f)
    return str(path)


def test_gatekeeper_allows_execution_without_enforcement(secured_clm_path):
    """By default (or with enforce_gatekeeper=False), missing VCards warn but allow execution."""
    runner = CLMRunner()

    # Run without context (defaults ensure warning only)
    try:
        result = runner.run_file(secured_clm_path, context={})
        # If execution happens, great. If it fails due to runtime, that's expected but NOT PermissionError.
    except PermissionError:
        pytest.fail("Gatekeeper should have allowed execution (warning mode)")


def test_gatekeeper_blocks_execution_with_enforcement(secured_clm_path):
    """With enforce_gatekeeper=True, missing VCards raise PermissionError."""
    runner = CLMRunner()

    context = {"enforce_gatekeeper": True, "vcard_manifest": {}}  # Empty wallet

    with pytest.raises(PermissionError) as exc:
        runner.run_file(secured_clm_path, context=context)

    assert "Gatekeeper Rejection" in str(exc.value)


def test_gatekeeper_allows_execution_with_valid_vcard(secured_clm_path):
    """With enforce_gatekeeper=True, providing the VCard allows execution."""
    runner = CLMRunner()

    context = {
        "enforce_gatekeeper": True,
        "vcard_manifest": {"auth://sha256:auth_token_hash": "sha256:auth_token_hash"},
    }

    try:
        runner.run_file(secured_clm_path, context=context)
    except PermissionError:
        pytest.fail("Gatekeeper should have allowed execution with valid VCard")
