diff --git a/tests/domain/epc/test_main_heating_system_overlay.py b/tests/domain/epc/test_main_heating_system_overlay.py index 0710837e..e161dbf5 100644 --- a/tests/domain/epc/test_main_heating_system_overlay.py +++ b/tests/domain/epc/test_main_heating_system_overlay.py @@ -8,6 +8,7 @@ from __future__ import annotations import pytest +from domain.epc.main_heating_system_type import MainHeatingSystemType from domain.epc.property_overlays.main_fuel_overlay import fuel_overlay_for from domain.epc.property_overlays.main_heating_system_overlay import ( main_heating_overlay_for, @@ -103,3 +104,17 @@ def test_the_three_heating_overrides_compose_without_conflict() -> None: assert main.sap_main_heating_code == 404 assert result.sap_heating.water_heating_code == 903 assert result.sap_heating.water_heating_fuel == 29 + + +@pytest.mark.parametrize( + "member", + [m for m in MainHeatingSystemType if m is not MainHeatingSystemType.UNKNOWN], +) +def test_every_resolvable_main_heating_value_decodes( + member: MainHeatingSystemType, +) -> None: + # Act + simulation = main_heating_overlay_for(member.value, 0) + + # Assert + assert simulation is not None diff --git a/tests/domain/epc/test_water_heating_overlay.py b/tests/domain/epc/test_water_heating_overlay.py index 7dd8c2d0..6e0b1fdb 100644 --- a/tests/domain/epc/test_water_heating_overlay.py +++ b/tests/domain/epc/test_water_heating_overlay.py @@ -11,6 +11,7 @@ import pytest from domain.epc.property_overlays.water_heating_overlay import ( water_heating_overlay_for, ) +from domain.epc.water_heating_type import WaterHeatingType from domain.modelling.scoring.overlay_applicator import apply_simulations from tests.domain.sap10_calculator.worksheet._elmhurst_worksheet_000490 import ( build_epc, @@ -71,3 +72,16 @@ def test_water_heating_override_remaps_the_hot_water_arrangement() -> None: # Assert — the calculator reads these off sap_heating. assert result.sap_heating.water_heating_code == 903 assert result.sap_heating.water_heating_fuel == 29 + + +@pytest.mark.parametrize( + "member", [m for m in WaterHeatingType if m is not WaterHeatingType.UNKNOWN] +) +def test_every_resolvable_water_heating_value_decodes( + member: WaterHeatingType, +) -> None: + # Act + simulation = water_heating_overlay_for(member.value, 0) + + # Assert + assert simulation is not None diff --git a/tests/repositories/property/test_override_component_consistency.py b/tests/repositories/property/test_override_component_consistency.py new file mode 100644 index 00000000..df830cd0 --- /dev/null +++ b/tests/repositories/property/test_override_component_consistency.py @@ -0,0 +1,24 @@ +"""Every override component must be wired through the WHOLE chain. + +The finaliser reader (`_ROW_TYPES`, component -> landlord table) and the overlay +registry (`_COMPONENT_OVERLAYS`, component -> overlay mapper) must cover exactly +the same set of components. If a component is classified + stored but has no +reader entry, the finaliser silently never writes its `property_overrides` rows; +if it has no overlay entry, the row never reaches the calculator. This guard +keeps the two registries in lock-step (it would have caught the missing +main_fuel / glazing / construction_age_band reader entries). +""" + +from __future__ import annotations + +from infrastructure.landlord_overrides.landlord_override_reader_postgres_repository import ( # pyright: ignore[reportPrivateUsage] + _ROW_TYPES, +) +from repositories.property.landlord_override_overlays import ( # pyright: ignore[reportPrivateUsage] + _COMPONENT_OVERLAYS, +) + + +def test_reader_and_overlay_registries_cover_the_same_components() -> None: + # Assert + assert set(_ROW_TYPES) == set(_COMPONENT_OVERLAYS)