Model/domain/epc/property_overlays/water_heating_overlay.py
Jun-te Kim d8ab3f6ec7 Decode from-main oil/LPG/coal and gas boiler-circulator water heating 🟩
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-19 14:20:24 +00:00

47 lines
2 KiB
Python

"""Map a Landlord-Override water-heating value to a heating Simulation Overlay.
A water-heating value is one canonical "<system>, <fuel>" description ("From main
system, mains gas", "Electric immersion, electricity"). The calculator reads the
hot-water arrangement from `sap_heating.water_heating_code` (the SAP Table 4a
system code) and `water_heating_fuel`, so the overlay decomposes the value into
those two int codes and emits a whole-dwelling `HeatingOverlay` (water heating is
not per-building-part, so `building_part` is ignored). It composes field-wise with
the main_fuel / main_heating overlays. Unresolvable values produce no overlay.
"""
from __future__ import annotations
from typing import Optional
from domain.modelling.simulation import EpcSimulation, HeatingOverlay
# Canonical "<system>, <fuel>" description → (water_heating_code, water_heating_fuel).
# water_heating_code: 901 "from main system" (SAP Table 4a inherit-from-main),
# 903 "electric immersion". Fuel codes are the modern RdSAP "(not community)"
# family (26 mains gas, 29 electricity), matching the main_fuel overlay.
_WATER_HEATING_CODES: dict[str, tuple[int, int]] = {
"From main system, mains gas": (901, 26),
"From main system, electricity": (901, 29),
"From main system, oil": (901, 28),
"From main system, LPG (bulk)": (901, 27),
"From main system, bottled LPG": (901, 3),
"From main system, house coal": (901, 33),
"Electric immersion, electricity": (903, 29),
# "boiler/circulator for water heating only" — SAP Table 4a code 911 (gas).
"Gas boiler/circulator, mains gas": (911, 26),
}
def water_heating_overlay_for(
water_heating_value: str, building_part: int
) -> Optional[EpcSimulation]:
codes = _WATER_HEATING_CODES.get(water_heating_value)
if codes is None:
return None
water_heating_code, water_heating_fuel = codes
return EpcSimulation(
heating=HeatingOverlay(
water_heating_code=water_heating_code,
water_heating_fuel=water_heating_fuel,
)
)