from backend.agents.disputes import annotate_clusters, find_disputes


def _a(id_, attribute, value):
    return {"id": id_, "attribute": attribute, "value": value,
            "source_text": value}


def test_find_disputes_flags_same_attribute_different_values():
    assertions = [
        _a("a1", "stud_pack_size", "(2) 2x6 STUD PACK"),
        _a("a2", "stud_pack_size", "(5) 2x6 STUD PACK"),
        _a("a3", "beam_size", "HSS16X4X5/8"),
    ]
    disputes = find_disputes(assertions)
    assert len(disputes) == 1
    assert disputes[0]["attribute"] == "stud_pack_size"
    assert disputes[0]["values"] == ["(2) 2x6 STUD PACK", "(5) 2x6 STUD PACK"]
    assert disputes[0]["assertion_ids"] == ["a1", "a2"]


def test_find_disputes_ignores_agreeing_values_and_blanks():
    assertions = [
        _a("a1", "beam_size", "HSS16X4X5/8"),
        _a("a2", "beam_size", "  hss16x4x5/8 "),   # same after normalize
        _a("a3", "", "orphan"),                     # no attribute -> skipped
        _a("a4", "beam_size", ""),                  # no value -> skipped
    ]
    assert find_disputes(assertions) == []


def test_annotate_clusters_writes_disputed_attributes():
    clusters = [
        {"key": "c1", "assertions": [
            _a("a1", "stud_pack_size", "(2) 2x6"),
            _a("a2", "stud_pack_size", "(5) 2x6"),
        ]},
        {"key": "c2", "assertions": [_a("a3", "x", "1"), _a("a4", "x", "1")]},
    ]
    assert annotate_clusters(clusters) == 1
    assert clusters[0]["disputed_attributes"][0]["attribute"] == "stud_pack_size"
    assert "disputed_attributes" not in clusters[1]


def test_slim_clusters_preserves_disputed_attributes():
    from backend.pipeline._serialize import slim_clusters
    cluster = {"key": "c1", "assertions": [],
               "disputed_attributes": [{"attribute": "a", "values": ["1", "2"],
                                         "assertion_ids": ["x", "y"]}]}
    slim = slim_clusters([cluster])[0]
    assert slim["disputed_attributes"][0]["values"] == ["1", "2"]


def test_find_disputes_handles_none_and_zero_values():
    # None value/attribute -> skipped; numeric 0 is a real value, not blank
    assertions = [
        {"id": "a1", "attribute": "count", "value": 0},
        {"id": "a2", "attribute": "count", "value": 1},
        {"id": "a3", "attribute": None, "value": "x"},
        {"id": "a4", "attribute": "count", "value": None},
    ]
    disputes = find_disputes(assertions)
    assert len(disputes) == 1
    assert disputes[0]["values"] == ["0", "1"]


def test_find_disputes_empty_input():
    assert find_disputes([]) == []
    assert annotate_clusters([]) == 0
