mirror of
https://github.com/Hestia-Homes/Model.git
synced 2026-06-08 11:17:27 +00:00
§6 slice 3: _g_perpendicular honours SapWindow.window_transmission_details
Elmhurst lodges per-window g⊥ via Manufacturer-source window_transmission_details.solar_transmittance on every window — the Table 6b code lookup is the cascade fallback, not the primary path. Without this the orchestrator picks Table 6b defaults that don't match the worksheet (e.g. glazing_type=4 defaults to low-E soft 0.63, but the manufacturer-declared value 0.76 is what the §6 row uses). Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
parent
4b83e7023f
commit
d56fef4d62
2 changed files with 36 additions and 2 deletions
|
|
@ -258,7 +258,12 @@ class SolarGainsResult:
|
|||
|
||||
|
||||
def _g_perpendicular(w: SapWindow) -> float:
|
||||
"""Table 6b g⊥ by glazing_type code, defaulting to 0.76 for unknowns."""
|
||||
"""Table 6b g⊥. Prefer the cert's measured value
|
||||
(`window_transmission_details.solar_transmittance`) when present —
|
||||
Elmhurst lodges it for every window; Table 6b is the cascade fallback.
|
||||
"""
|
||||
if w.window_transmission_details is not None:
|
||||
return float(w.window_transmission_details.solar_transmittance)
|
||||
if isinstance(w.glazing_type, int) and w.glazing_type in _G_PERPENDICULAR_BY_GLAZING_TYPE:
|
||||
return _G_PERPENDICULAR_BY_GLAZING_TYPE[w.glazing_type]
|
||||
return _G_PERPENDICULAR_DEFAULT
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ Appendix U §U3.2 (pages 127-129), Table U4 (latitudes), Table U5
|
|||
|
||||
import pytest
|
||||
|
||||
from datatypes.epc.domain.epc_property_data import SapWindow
|
||||
from datatypes.epc.domain.epc_property_data import SapWindow, WindowTransmissionDetails
|
||||
from domain.ml.tests._fixtures import make_minimal_sap10_epc, make_window
|
||||
from domain.sap.worksheet.internal_gains import OvershadingCategory
|
||||
from domain.sap.worksheet.solar_gains import (
|
||||
|
|
@ -63,6 +63,35 @@ def test_solar_gains_from_cert_reproduces_000490_line_83_total() -> None:
|
|||
), f"(83) month {m+1}"
|
||||
|
||||
|
||||
def test_solar_gains_from_cert_prefers_manufacturer_g_perpendicular_over_table_6b() -> None:
|
||||
# Arrange — SAP 10.2 §6.1 + Table 6b note 2: when the manufacturer
|
||||
# supplies a measured solar transmittance via the cert's
|
||||
# `window_transmission_details`, it overrides the Table 6b code lookup.
|
||||
# Elmhurst lodges this for every window (Source = "Manufacturer"). Same
|
||||
# 5.52 m² SE window as 000490 SE, but glazing_type=4 (low-E soft, table
|
||||
# default 0.63) with manufacturer g⊥=0.76 — the manufacturer value must
|
||||
# win, reproducing the worksheet gain.
|
||||
window = make_window(
|
||||
orientation=4, width=5.52, height=1.0, glazing_type=4,
|
||||
)
|
||||
window.window_transmission_details = WindowTransmissionDetails(
|
||||
u_value=2.8, data_source=1, solar_transmittance=0.76,
|
||||
)
|
||||
epc = make_minimal_sap10_epc(
|
||||
total_floor_area_m2=53.0,
|
||||
sap_windows=[window],
|
||||
)
|
||||
|
||||
# Act
|
||||
result = solar_gains_from_cert(
|
||||
epc=epc, region=0, overshading=OvershadingCategory.AVERAGE,
|
||||
)
|
||||
|
||||
# Assert — single SE window, Jan UK-avg flux 36.7938, gain 74.8788 W
|
||||
assert result.southeast_monthly_w[0] == pytest.approx(74.8788, abs=5e-3)
|
||||
assert result.total_solar_gains_monthly_w[0] == pytest.approx(74.8788, abs=5e-3)
|
||||
|
||||
|
||||
def test_z_solar_for_overshading_returns_table_6d_first_column() -> None:
|
||||
# Arrange — SAP 10.2 Table 6d "Winter solar access factor (for calculation
|
||||
# of solar gains for heating)" — first numeric column on p178. Used for
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue