"""Tests for policy.py — load/save round-trips and error handling."""

from importlib import resources
from pathlib import Path

import pytest

from noisegate.exceptions import PolicyParseError
from noisegate.models import Policy
from noisegate.policy import load_policy, save_policy


def _default_policy_path() -> Path:
    with resources.as_file(resources.files("noisegate.data").joinpath("default_policy.yaml")) as p:
        return p


def test_load_default_policy():
    policy = load_policy(_default_policy_path())

    assert len(policy.checks) == 5
    ids = [c.id for c in policy.checks]
    assert ids == [
        "asset_in_scope",
        "finding_ineligible",
        "required_sections_present",
        "reproduction_quality",
        "impact_quality",
    ]


def test_hard_fail_values():
    policy = load_policy(_default_policy_path())
    hard_fail_map = {c.id: c.hard_fail for c in policy.checks}

    assert hard_fail_map["asset_in_scope"] is True
    assert hard_fail_map["finding_ineligible"] is True
    assert hard_fail_map["required_sections_present"] is False
    assert hard_fail_map["reproduction_quality"] is False
    assert hard_fail_map["impact_quality"] is False


def test_unknown_plugin_check_id_accepted():
    policy = Policy.model_validate(
        {"checks": [{"id": "my_org.custom_poc_runner", "hard_fail": True}]}
    )
    assert policy.checks[0].id == "my_org.custom_poc_runner"


def test_invalid_yaml_raises_policy_parse_error(tmp_path: Path):
    bad = tmp_path / "policy.yaml"
    bad.write_text("checks: [unclosed")

    with pytest.raises(PolicyParseError):
        load_policy(bad)


def test_missing_file_raises_policy_parse_error(tmp_path: Path):
    with pytest.raises(PolicyParseError):
        load_policy(tmp_path / "nonexistent.yaml")


def test_round_trip(tmp_path: Path):
    original = load_policy(_default_policy_path())
    out = tmp_path / "policy.yaml"

    save_policy(original, out)
    restored = load_policy(out)

    assert restored == original
