diff --git a/CHANGELOG.md b/CHANGELOG.md
index 705c5e3f..b5d44d57 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -19,6 +19,19 @@
feature limits and one canonical regional Dataset upload per theme/year.
- Extended the regional time-series coordinator and release packaging without
changing API contracts, database migrations or frontend architecture.
+- Provisioned all nine snapshots on live Tower/PostGIS: 207,717 persisted
+ polygon features across three complete 28-municipality temporal series.
+ Every Dataset is ready, has one immutable DatasetVersion and was reused by
+ the idempotency run without duplicate persistence.
+- Added the exact-area fast path for these already-clipped regional artifacts,
+ reducing complete-Kempen comparisons from minutes to 0.9-4.1 seconds in the
+ live audit while preserving the calculated values.
+- Suppressed inapplicable generic line metrics for historical polygon classes;
+ results now show governed hectares plus object counts, never artificial
+ `0 km` road/watercourse measurements.
+- Kept the top workbench source context synchronized with the selected
+ Evolution series. Browser verification covered complete Kempen, Mol and a
+ 3440 x 1440 viewport with no console warnings or errors.
## Sprint 208 Governed VMM flood-hazard scenarios (2026-07-15)
diff --git a/backend/tests/test_sprint169_long_context_name_readability.py b/backend/tests/test_sprint169_long_context_name_readability.py
index 87d7cf64..87f927fb 100644
--- a/backend/tests/test_sprint169_long_context_name_readability.py
+++ b/backend/tests/test_sprint169_long_context_name_readability.py
@@ -15,7 +15,8 @@ def test_long_context_names_remain_compact_and_inspectable() -> None:
assert "selectedProject?.name === REGIONAL_WORKSPACE_PROJECT_NAME" in app
assert "? REGIONAL_WORKSPACE_LABEL" in app
- assert "const datasetContextLabel = analysisMapLayerActive && mapFeatureCollection" in app
+ assert "const datasetContextLabel = activeWorkspace === 'map' && mapContextSourceLabel" in app
+ assert ": analysisMapLayerActive && mapFeatureCollection" in app
assert "? getDatasetDisplayName(selectedDataset)" in app
assert "`${mapLayerLabel} · controle vereist`" in app
assert "{projectContextLabel}" in app
diff --git a/backend/tests/test_sprint209_regional_historical_landuse.py b/backend/tests/test_sprint209_regional_historical_landuse.py
index d72caafc..d947d4f9 100644
--- a/backend/tests/test_sprint209_regional_historical_landuse.py
+++ b/backend/tests/test_sprint209_regional_historical_landuse.py
@@ -239,6 +239,10 @@ def test_upload_contract_is_regional_temporal_and_partition_audited(tmp_path: Pa
def test_regional_historical_operator_is_packaged_and_release_checked() -> None:
dockerfile = (ROOT / "deploy/unraid/Dockerfile.all-in-one").read_text(encoding="utf-8")
readiness = (ROOT / "scripts/run_readiness_check.sh").read_text(encoding="utf-8")
+ app = (ROOT / "frontend/src/App.tsx").read_text(encoding="utf-8")
+ workspace = (ROOT / "frontend/src/components/map/MapWorkspace.tsx").read_text(encoding="utf-8")
assert "COPY scripts/provision_regional_historical_landuse.py" in dockerfile
assert "py_compile scripts/provision_regional_historical_landuse.py" in readiness
+ assert "onSetContextSourceLabel={setMapContextSourceLabel}" in app
+ assert "analysisMode === 'evolution' ? activeTemporalSeriesGroup?.label" in workspace
diff --git a/docs/CODEX_EXECUTION_LOG.md b/docs/CODEX_EXECUTION_LOG.md
index d1b3eee0..2e12948a 100644
--- a/docs/CODEX_EXECUTION_LOG.md
+++ b/docs/CODEX_EXECUTION_LOG.md
@@ -8833,12 +8833,39 @@ Implemented:
- Extended `provision_regional_timeseries.py`, all-in-one packaging, readiness
compilation and operator/source documentation.
-Validation evidence before live provisioning:
-- Fourteen focused partition, raw-evidence, clipping, assembly, upload,
- coordinator and packaging tests pass.
-- The official source catalog still reports the production WFS and the three
- governed historical collections. Live partition provisioning and browser
- Evolution validation follow in this pass.
+Validation and live evidence:
+- The final release gate passes with 685 backend tests, frontend typecheck and
+ production build, one Alembic head (`202607150001`) and script syntax checks.
+- Live Tower/PostGIS provisioning completed all 252 municipality/theme/year
+ partitions and nine combined snapshots. No snapshot has an empty municipal
+ partition. The retained regional historical audit cache is about 518 MB.
+- Persisted feature counts are: buildings 14,245 / 22,036 / 69,869; water
+ 9,010 / 13,571 / 8,188; roads 6,305 / 33,578 / 30,915 for 1778 / 1873 /
+ 1969 respectively. Total persisted geometry count is 207,717.
+- Each of the nine ready Datasets belongs to regional Area
+ `46ab5614-fcf8-4e63-8ea8-6049f34c14fd`, exposes one immutable
+ DatasetVersion/checksum and participates in one of three ordered temporal
+ series. A second complete operator run returned `existing` for all nine with
+ identical audited feature counts.
+- The live audit found that the full-Area fast path did not yet recognize the
+ new clipped operator. Adding its governed provenance reduced exact complete-
+ Kempen comparisons from multi-minute redundant clipping to 4.0 s for
+ buildings, 0.9 s for water and 1.9 s for roads.
+- Complete-Kempen 1778 -> 1969 results are 481.62 -> 1,833.23 ha built land,
+ 1,546.89 -> 2,198.80 ha mapped water and 4,382.49 -> 6,978.12 ha mapped
+ roads. These are map-class surfaces, not modern footprints, centreline
+ lengths, bathymetry or volume.
+- Browser validation selected the historical buildings series, analyzed the
+ complete persisted Kempen Area and then municipality Mol. Mol returned
+ 24.35 / 32.45 / 120.81 ha for 1778 / 1873 / 1969 and explicitly disclosed
+ the cartographic-method and unstable-object-identity limitations.
+- The irrelevant generic `0 km` metrics for polygon-only historical water and
+ road classes were removed. The workbench source context now follows the
+ selected Evolution series. Normal and 3440 x 1440 visual checks found no
+ overlap; browser console warnings/errors were empty.
+- Each deployment passed live PostGIS 3.6 connectivity, required schema/index
+ checks, database collation, Alembic head `202607150001`, frontend/API proxy
+ and icon verification.
Known limitations:
- Historical `buildings` are mapped built land-use surfaces, not individual
@@ -8849,6 +8876,7 @@ Known limitations:
continuous equivalent to modern GRB or 10 m land-use products.
Next:
-- Run the complete nine-snapshot operator on live Tower/PostGIS, verify all 28
- partition manifests and then validate regional/municipality Evolution in the
- browser before marking the backlog item complete.
+- Keep permanent inland bathymetry blocked on a governed depth source. The
+ next implementation pass can focus on current-only nature/terrain/flood
+ regional expansion or on a benchmarked data-refresh scheduler; it must not
+ reinterpret these historical surfaces as modern object lineage.
diff --git a/docs/TODO.md b/docs/TODO.md
index f002d159..f4c110b9 100644
--- a/docs/TODO.md
+++ b/docs/TODO.md
@@ -26,7 +26,7 @@
- [x] Add bounded historical orthophoto acquisition for official 1971-2025 products with a map overlay and no current-GRB QA on old imagery.
- [x] Add BWK/Natura 2000 through an explicit provider/operator contract.
- [x] Add annual agricultural-use parcels through an explicit provider/operator contract.
-- [ ] Extend the official 1778/1873/1969 historical buildings, water and roads series from Mol to the approved regional scope with partitioned source audits.
+- [x] Extend the official 1778/1873/1969 historical buildings, water and roads series from Mol to the approved regional scope with partitioned source audits.
- [x] Connect a drawn rectangle to bounded official orthophoto acquisition, local configured-YOLO detection and persisted GRB QA.
## Governed source expansion backlog
diff --git a/frontend/README.md b/frontend/README.md
index c44bdbdb..99004faf 100644
--- a/frontend/README.md
+++ b/frontend/README.md
@@ -31,6 +31,11 @@ selectable and is never merged into the same trend.
Regional building, water and road evolution uses the same selector after the
partition-audited 1778/1873/1969 snapshots are provisioned. Historical built
surfaces never replace current GRB building footprints in Latest state.
+The persistent top context bar follows the selected historical series while
+Evolution is active, so its source label cannot disagree with the result panel.
+Because these historical WFS classes are polygonal map surfaces, their metrics
+are hectares plus a supporting object count; generic live road/water line
+metrics are deliberately not shown.
Selection results use dataset-specific PostGIS summaries with end-user units.
Building footprints, forest, water surfaces and parcels show intersected
diff --git a/frontend/src/App.tsx b/frontend/src/App.tsx
index 14d7e479..3ea4b771 100644
--- a/frontend/src/App.tsx
+++ b/frontend/src/App.tsx
@@ -65,6 +65,7 @@ function App(): JSX.Element {
const [activeWorkspace, setActiveWorkspace] = useState('map')
const [inspectorOpen, setInspectorOpen] = useState(false)
const [mapContentMode, setMapContentMode] = useState<'dataset' | 'analysis'>('dataset')
+ const [mapContextSourceLabel, setMapContextSourceLabel] = useState(null)
useEffect(() => {
window.scrollTo({ top: 0, left: 0 })
setInspectorOpen(false)
@@ -715,7 +716,9 @@ function App(): JSX.Element {
? REGIONAL_WORKSPACE_LABEL
: selectedProject?.name ?? 'Geen werkruimte'
const areaContextLabel = selectedArea?.name ?? (areas.length > 0 ? 'Kies een gebied' : 'Geen gebied')
- const datasetContextLabel = analysisMapLayerActive && mapFeatureCollection
+ const datasetContextLabel = activeWorkspace === 'map' && mapContextSourceLabel
+ ? mapContextSourceLabel
+ : analysisMapLayerActive && mapFeatureCollection
? `${mapLayerLabel} · controle vereist`
: selectedDataset
? getDatasetDisplayName(selectedDataset)
@@ -1035,6 +1038,7 @@ function App(): JSX.Element {
selectedMapDatasetId={selectedDataset && availableMapDatasets.some((dataset) => dataset.id === selectedDataset.id) ? selectedDataset.id : ''}
selectedFeature={selectedMapFeature}
onSelectMapArea={setSelectedMapAreaId}
+ onSetContextSourceLabel={setMapContextSourceLabel}
onOpenDatasetInMap={openDatasetInMap}
onSetAreaLayerVisible={setAreaLayerVisible}
onSetAreaLayerOpacity={setAreaLayerOpacity}
diff --git a/frontend/src/components/map/MapWorkspace.tsx b/frontend/src/components/map/MapWorkspace.tsx
index 93440b56..a181c14d 100644
--- a/frontend/src/components/map/MapWorkspace.tsx
+++ b/frontend/src/components/map/MapWorkspace.tsx
@@ -559,6 +559,7 @@ interface MapWorkspaceProps {
availableMapDatasets: DatasetCreateResponse[]
selectedMapDatasetId: string
onSelectMapArea: (areaId: string) => void
+ onSetContextSourceLabel: (label: string | null) => void
onOpenDatasetInMap: (dataset: DatasetCreateResponse) => void
onSetAreaLayerVisible: (visible: boolean) => void
onSetAreaLayerOpacity: (opacity: number) => void
@@ -639,6 +640,7 @@ export function MapWorkspace({
availableMapDatasets,
selectedMapDatasetId,
onSelectMapArea,
+ onSetContextSourceLabel,
onOpenDatasetInMap,
onSetAreaLayerVisible,
onSetAreaLayerOpacity,
@@ -776,6 +778,14 @@ export function MapWorkspace({
const activeTemporalSeriesGroup = activeTemporalSeriesGroups.find((group) => group.key === selectedTemporalSeriesKey)
?? activeTemporalSeriesGroups[0]
const activeTemporalSeries = activeTemporalSeriesGroup?.items ?? EMPTY_TEMPORAL_SERIES
+
+ useEffect(() => {
+ onSetContextSourceLabel(
+ analysisMode === 'evolution' ? activeTemporalSeriesGroup?.label ?? null : null,
+ )
+ return () => onSetContextSourceLabel(null)
+ }, [activeTemporalSeriesGroup?.label, analysisMode, onSetContextSourceLabel])
+
const themeResults = useMemo(
() =>
themeInsights.flatMap((insight) => {