"""Tests for PayerConfig277CA loading from YAML. SP10 T4. Mirrors ``test_payer_config_loading.py`` but for the new ``PayerConfig277CA`` block that the 277CA parser and Inbox lane consume for status-code classification. """ from __future__ import annotations from pathlib import Path import pytest import yaml from cyclone.payers import ( DEFAULT_CONFIG_PATH, _tx_to_model, all_configs, get_config, load_payer_configs, reset, ) from cyclone.providers import PayerConfig277CA @pytest.fixture(autouse=True) def _clear_registry(): """Each test starts with an empty config registry.""" reset() yield reset() class TestPayerConfig277CALoading: def test_loads_default_config_with_277ca_block(self): """The default config/payers.yaml must have a CO_TXIX 277CA block.""" load_payer_configs(DEFAULT_CONFIG_PATH) cfg = get_config("CO_TXIX", "277CA") assert cfg is not None # Defaults from PayerConfig277CA. assert "A6" in cfg["rejected_status_codes"] assert "A8" in cfg["pended_status_codes"] assert "A3" in cfg["accepted_status_codes"] assert "P1" in cfg["paid_status_codes"] assert "277CA" in cfg["transaction_set_ids_allowed"] def test_model_rejects_bad_status_code_type(self, tmp_path: Path): """A non-list rejected_status_codes value must fail validation.""" bad = { "payers": [ { "payer_id": "BAD_PAYER", "name": "Bad", "receiver_name": "BAD", "receiver_id": "BADID", "configs": { "277CA": { "rejected_status_codes": "A6", # must be list "pended_status_codes": ["A8"], "accepted_status_codes": ["A1"], "paid_status_codes": ["P1"], "transaction_set_ids_allowed": ["277", "277CA"], "implementation_guide": "005010X214", }, }, }, ], } p = tmp_path / "bad.yaml" p.write_text(yaml.safe_dump(bad)) with pytest.raises(ValueError, match="BAD_PAYER"): load_payer_configs(p) class TestPayerConfig277CAModel: def test_default_factory_values(self): """A minimal PayerConfig277CA defaults to the canonical HCPF sets.""" cfg = PayerConfig277CA() assert "A4" in cfg.rejected_status_codes assert "A6" in cfg.rejected_status_codes assert "A7" in cfg.rejected_status_codes assert "A8" in cfg.pended_status_codes assert "277CA" in cfg.transaction_set_ids_allowed def test_explicit_override(self): cfg = PayerConfig277CA( rejected_status_codes=["X1"], pended_status_codes=["X2"], accepted_status_codes=["X3"], paid_status_codes=["X4"], ) assert cfg.rejected_status_codes == ["X1"] assert cfg.pended_status_codes == ["X2"] class TestTxToModelFor277CA: def test_int_key_routes_to_277ca_model(self): """PyYAML may parse numeric keys as int — _tx_to_model must handle both.""" # 277CA as int isn't likely (not pure digits), but 277 as int is. # Test the canonical string. assert _tx_to_model("277CA") is PayerConfig277CA def test_string_key_routes_correctly(self): assert _tx_to_model("277CA") is PayerConfig277CA assert _tx_to_model("835") is not PayerConfig277CA # it's 835 model