diff --git a/backend/documents_parser/tests/fixtures/Summary_000898.pdf b/backend/documents_parser/tests/fixtures/Summary_000898.pdf new file mode 100644 index 00000000..4da98385 Binary files /dev/null and b/backend/documents_parser/tests/fixtures/Summary_000898.pdf differ diff --git a/backend/documents_parser/tests/fixtures/Summary_000900.pdf b/backend/documents_parser/tests/fixtures/Summary_000900.pdf new file mode 100644 index 00000000..7f3dcda8 Binary files /dev/null and b/backend/documents_parser/tests/fixtures/Summary_000900.pdf differ diff --git a/backend/documents_parser/tests/fixtures/Summary_000901.pdf b/backend/documents_parser/tests/fixtures/Summary_000901.pdf new file mode 100644 index 00000000..63280913 Binary files /dev/null and b/backend/documents_parser/tests/fixtures/Summary_000901.pdf differ diff --git a/backend/documents_parser/tests/fixtures/Summary_000902.pdf b/backend/documents_parser/tests/fixtures/Summary_000902.pdf new file mode 100644 index 00000000..bf0fe91b Binary files /dev/null and b/backend/documents_parser/tests/fixtures/Summary_000902.pdf differ diff --git a/backend/documents_parser/tests/fixtures/Summary_000904.pdf b/backend/documents_parser/tests/fixtures/Summary_000904.pdf new file mode 100644 index 00000000..e2a5fa2f Binary files /dev/null and b/backend/documents_parser/tests/fixtures/Summary_000904.pdf differ diff --git a/backend/documents_parser/tests/test_summary_pdf_mapper_chain.py b/backend/documents_parser/tests/test_summary_pdf_mapper_chain.py index 4f402e68..e4113edb 100644 --- a/backend/documents_parser/tests/test_summary_pdf_mapper_chain.py +++ b/backend/documents_parser/tests/test_summary_pdf_mapper_chain.py @@ -60,6 +60,8 @@ _SUMMARY_000897_PDF = _FIXTURES / "Summary_000897.pdf" _SUMMARY_000784_PDF = _FIXTURES / "Summary_000784.pdf" _SUMMARY_000899_PDF = _FIXTURES / "Summary_000899.pdf" _SUMMARY_000903_PDF = _FIXTURES / "Summary_000903.pdf" +_SUMMARY_000901_PDF = _FIXTURES / "Summary_000901.pdf" # cert 3800 +_SUMMARY_000904_PDF = _FIXTURES / "Summary_000904.pdf" # cert 9285 # GOV.UK EPB API JSON for cert 001479 — the API-path counterpart of the # Summary_001479.pdf fixture. Together they drive the API ≡ Summary @@ -711,6 +713,53 @@ def test_summary_0350_full_chain_sap_within_spec_floor_of_worksheet() -> None: assert abs(result.sap_score_continuous - worksheet_unrounded_sap) < _ASHP_COHORT_CHAIN_TOLERANCE +def test_summary_3800_full_chain_sap_within_spec_floor_of_worksheet() -> None: + # Arrange — cert 3800-8515-0922-3398-3563 (Summary_000901.pdf / + # dr87-0001-000901.pdf) is the third ASHP cohort cert to close on + # the Summary path: Mitsubishi PUZ-WM50VHA ASHP (PCDB 104568). + # Worksheet "SAP value" lodges 86.1458. + # + # **First-try closure — zero new mapper slices required**. The + # structural work shipped in slices S0380.2..S0380.9 (HP routing, + # cylinder block, composite walls, multi-array PV, extension + # inheritance) was already sufficient for cert 3800's variant set. + # Strong evidence that the Summary mapper has reached completeness + # for the standard single-bp / single-array ASHP shape. + pages = _summary_pdf_to_textract_style_pages(_SUMMARY_000901_PDF) + site_notes = ElmhurstSiteNotesExtractor(pages).extract() + epc = EpcPropertyDataMapper.from_elmhurst_site_notes(site_notes) + + # Act + result = calculate_sap_from_inputs( + cert_to_inputs(epc, prices=SAP_10_2_SPEC_PRICES) + ) + + # Assert — ±0.07 ASHP-cohort spec-floor tolerance. + worksheet_unrounded_sap = 86.1458 + assert abs(result.sap_score_continuous - worksheet_unrounded_sap) < _ASHP_COHORT_CHAIN_TOLERANCE + + +def test_summary_9285_full_chain_sap_within_spec_floor_of_worksheet() -> None: + # Arrange — cert 9285-3062-0205-7766-7200 (Summary_000904.pdf / + # dr87-0001-000904.pdf) is the fourth ASHP cohort cert to close on + # the Summary path: Mitsubishi PUZ-WM50VHA ASHP (PCDB 104568). + # Worksheet "SAP value" lodges 84.1369. Same "first-try closure, + # zero new slices" disposition as cert 3800 — the cohort's + # structural mapper completeness is the load-bearing claim. + pages = _summary_pdf_to_textract_style_pages(_SUMMARY_000904_PDF) + site_notes = ElmhurstSiteNotesExtractor(pages).extract() + epc = EpcPropertyDataMapper.from_elmhurst_site_notes(site_notes) + + # Act + result = calculate_sap_from_inputs( + cert_to_inputs(epc, prices=SAP_10_2_SPEC_PRICES) + ) + + # Assert — ±0.07 ASHP-cohort spec-floor tolerance. + worksheet_unrounded_sap = 84.1369 + assert abs(result.sap_score_continuous - worksheet_unrounded_sap) < _ASHP_COHORT_CHAIN_TOLERANCE + + def test_summary_0380_full_chain_sap_within_spec_floor_of_worksheet() -> None: # Arrange — cert 0380-2471-3250-2596-8761 (Summary_000899.pdf / # dr87-0001-000899.pdf) is the first heat-pump cert under per-cert