Model/tests/domain/sap10_calculator/worksheet
Khalim Conn-Kowlessar f326e4eb53 mapper: Elmhurst path populates roof_construction (int) for cross-mapper parity
The gov-EPC API mapper sets BOTH roof_construction (int) and
roof_construction_type (str, derived via _API_ROOF_CONSTRUCTION_TO_STR),
but the Elmhurst mapper set only the string — leaving roof_construction
None on every site-notes cert. The SAP cascade reads the STRING (so SAP
cross-mapper parity always held), but consumers of the int (e.g.
domain/sap10_ml/transform.py ML aggregates `main_dwelling_roof_
construction`) silently saw None on the Elmhurst path.

New `_elmhurst_roof_construction_int` maps the Elmhurst roof-type code to
the same SAP10 int the API lodges (F→1, PN→3, PA→4, PS→8, S/A→7),
harvested from the committed Summary fixtures. Unlike the wall map it
returns None (not a strict-raise) for unmapped codes: the int is not
cascade-load-bearing, so an unknown roof must not block the cert (vaulted
5 / thatched 6 / NR omitted until a fixture surfaces them).

The 6 hand-built U985 reference fixtures gain the matching
roof_construction int (4/4/3 etc.) so test_from_elmhurst_site_notes_
matches_hand_built_* still asserts structural parity. SAP output is
unchanged (cascade reads the string). §4 suite green (2407 passed); the
two pre-existing stone-§5.6 sap10_ml failures are unrelated/out of scope.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-04 21:16:20 +00:00
..
fixtures Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
__init__.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
_elmhurst_fixtures.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
_elmhurst_worksheet_000474.py mapper: Elmhurst path populates roof_construction (int) for cross-mapper parity 2026-06-04 21:16:20 +00:00
_elmhurst_worksheet_000477.py mapper: Elmhurst path populates roof_construction (int) for cross-mapper parity 2026-06-04 21:16:20 +00:00
_elmhurst_worksheet_000480.py mapper: Elmhurst path populates roof_construction (int) for cross-mapper parity 2026-06-04 21:16:20 +00:00
_elmhurst_worksheet_000487.py mapper: Elmhurst path populates roof_construction (int) for cross-mapper parity 2026-06-04 21:16:20 +00:00
_elmhurst_worksheet_000490.py mapper: Elmhurst path populates roof_construction (int) for cross-mapper parity 2026-06-04 21:16:20 +00:00
_elmhurst_worksheet_000516.py mapper: Elmhurst path populates roof_construction (int) for cross-mapper parity 2026-06-04 21:16:20 +00:00
_elmhurst_worksheet_000565.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
_elmhurst_worksheet_001431.py S0380.191: pin simulated 001431 gas-combi end-to-end at 1e-4 (e2e harness) 2026-06-02 22:44:32 +00:00
_elmhurst_worksheet_001431_6035.py S0380.195: pin sim case 4 (6035 floor geometry) e2e at 1e-4 — 6035 +19 PE is lodged divergence 2026-06-03 09:56:39 +00:00
_elmhurst_worksheet_001431_case5.py S0380.197: simulated case 5 e2e fixture — detached sandstone RR validates S0380.196 (RdSAP 10 §3.9.1 + Table 4 p.22) 2026-06-03 11:41:16 +00:00
_elmhurst_worksheet_001431_case6.py S0380.207: promote simulated case 6 to a full SapResult e2e fixture 2026-06-03 16:14:48 +00:00
_elmhurst_worksheet_001431_case7.py S0380.208: case 7 combi e2e fixture — condensing-oil-combi path validated exact 2026-06-03 17:57:22 +00:00
_elmhurst_worksheet_001431_rr.py S0380.193: suspended-floor (12) sealed rule fires only on a SUPPLIED U-value 2026-06-03 09:16:25 +00:00
_elmhurst_worksheet_001431_rr8.py S0380.194: pin sim case 3 (near-exact 6035 replica) e2e at 1e-4 2026-06-03 09:46:56 +00:00
_xlsx_loader.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_appendix_h_solar.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_dimensions.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_e2e_elmhurst_sap_score.py S0380.208: case 7 combi e2e fixture — condensing-oil-combi path validated exact 2026-06-03 17:57:22 +00:00
test_energy_requirements.py S0380.200: SAP 10.2 §9a two-main-heating split (203)/(205)/(207)/(213) 2026-06-03 13:09:43 +00:00
test_fabric_energy_efficiency.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_fuel_cost.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_heat_transmission.py mapper: disambiguate SY system-built from B basement wall (both share code 6) 2026-06-04 19:39:18 +00:00
test_internal_gains.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_mean_internal_temperature.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_mev.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_photovoltaic.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_rating.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_section_cascade_pins.py S0380.206: Eq D1 Q_space uses the DHW boiler's own (204) share, not (202) 2026-06-03 16:10:42 +00:00
test_solar_gains.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_space_cooling.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_space_heating.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_utilisation_factor.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_ventilation.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00
test_water_heating.py Move sap10_calculator tests to tests/domain/sap10_calculator/ for CI 2026-06-02 16:58:00 +00:00