feat: add governed Mol nature value layer
This commit is contained in:
@@ -24,6 +24,7 @@ FULL_AREA_CLIPPED_OPERATOR_TOOLS = {
|
||||
"provision_regional_grb_buildings.py",
|
||||
"provision_regional_grb_context.py",
|
||||
"provision_waterinfo_station_history.py",
|
||||
"provision_mol_bwk_natura2000.py",
|
||||
}
|
||||
|
||||
|
||||
@@ -84,6 +85,7 @@ SEMANTIC_SELECTION_METRICS: dict[str, tuple[dict[str, Any], ...]] = {
|
||||
"warning": "GRB-percelen zijn een grafische referentie en vormen geen juridische grensopmeting.",
|
||||
},
|
||||
),
|
||||
"nature_value": (),
|
||||
}
|
||||
|
||||
SEMANTIC_COUNT_LABELS = {
|
||||
@@ -93,6 +95,7 @@ SEMANTIC_COUNT_LABELS = {
|
||||
"water": "Waterobjecten",
|
||||
"roads": "Wegsegmenten",
|
||||
"parcels": "Percelen",
|
||||
"nature_value": "BWK-kaartvlakken",
|
||||
}
|
||||
|
||||
|
||||
@@ -114,6 +117,10 @@ class VectorFeatureService:
|
||||
"waterways": "water",
|
||||
"road": "roads",
|
||||
"parcel": "parcels",
|
||||
"nature": "nature_value",
|
||||
"biodiversity": "nature_value",
|
||||
"bwk": "nature_value",
|
||||
"natura2000": "nature_value",
|
||||
}
|
||||
for candidate in candidates:
|
||||
if not isinstance(candidate, str) or not candidate.strip():
|
||||
@@ -356,6 +363,17 @@ class VectorFeatureService:
|
||||
primary_config = semantic_metrics[0]
|
||||
|
||||
metric_configs = [primary_config]
|
||||
configured_metrics = source_metadata.get("selection_metrics")
|
||||
if isinstance(configured_metrics, list):
|
||||
existing_metric_keys = {str(primary_config.get("metric_key") or "")}
|
||||
for configured_item in configured_metrics:
|
||||
if not isinstance(configured_item, dict):
|
||||
continue
|
||||
metric_key = str(configured_item.get("metric_key") or "").strip()
|
||||
if not metric_key or metric_key in existing_metric_keys:
|
||||
continue
|
||||
metric_configs.append(dict(configured_item))
|
||||
existing_metric_keys.add(metric_key)
|
||||
for semantic_metric in semantic_metrics:
|
||||
signature = (semantic_metric["method"], semantic_metric["unit"])
|
||||
existing = {
|
||||
@@ -419,6 +437,20 @@ class VectorFeatureService:
|
||||
metric_filter = selection_filter
|
||||
if dimension in {1, 2}:
|
||||
metric_filter += (func.ST_Dimension(VectorFeature.geometry) == int(dimension),)
|
||||
filter_property = str(config.get("filter_property") or "").strip()
|
||||
filter_values = config.get("filter_values")
|
||||
if filter_property:
|
||||
if not isinstance(filter_values, list) or not filter_values:
|
||||
raise AppError(
|
||||
code="INVALID_SELECTION_AGGREGATION",
|
||||
message="Dataset selection metric filter requires one or more values",
|
||||
details={"dataset_id": str(dataset.id), "filter_property": filter_property},
|
||||
status_code=500,
|
||||
)
|
||||
normalized_filter_values = [str(value) for value in filter_values]
|
||||
metric_filter += (
|
||||
VectorFeature.properties_json.op("->>")(filter_property).in_(normalized_filter_values),
|
||||
)
|
||||
|
||||
if method == "intersection_area":
|
||||
measured_geometry = (
|
||||
@@ -461,7 +493,7 @@ class VectorFeatureService:
|
||||
aggregate_function = func.avg if method == "mean" else func.sum
|
||||
aggregate_value = (
|
||||
db.query(func.coalesce(aggregate_function(value_expression), 0.0))
|
||||
.filter(*selection_filter)
|
||||
.filter(*metric_filter)
|
||||
.filter(VectorFeature.properties_json.op("->>")(property_name).isnot(None))
|
||||
.scalar()
|
||||
)
|
||||
@@ -469,16 +501,16 @@ class VectorFeatureService:
|
||||
if method == "area_weighted_sum" and not full_dataset_area:
|
||||
partial_feature_count = (
|
||||
db.query(func.count(VectorFeature.id))
|
||||
.filter(*selection_filter)
|
||||
.filter(*metric_filter)
|
||||
.filter(coverage_ratio < 0.999999)
|
||||
.scalar()
|
||||
)
|
||||
is_estimate = bool(partial_feature_count)
|
||||
is_estimate = bool(config.get("is_estimate", False)) or bool(partial_feature_count)
|
||||
if not is_estimate and config.get("warning_only_when_estimate", True):
|
||||
warning = None
|
||||
elif method == "area_weighted_sum":
|
||||
is_estimate = False
|
||||
if config.get("warning_only_when_estimate", True):
|
||||
is_estimate = bool(config.get("is_estimate", False))
|
||||
if not is_estimate and config.get("warning_only_when_estimate", True):
|
||||
warning = None
|
||||
elif method != "feature_count":
|
||||
raise AppError(
|
||||
|
||||
Reference in New Issue
Block a user