REOPENED. L3 future-supply rows are computed per (district_name, dev_group_name) but dev_group_name was never a key column — only embedded in method text. With complex_id/obj_class NULL for L3, every dev_group of a district collapsed to one upsert key → ~95.6% loss. Ground-truth (Академический, prod): should be 13,808 units / 15 dev_groups / 54 objects; only 1 row / 607 units survived. Migration 128: ADD COLUMN supply_layers.dev_group_name TEXT + rebuild uq_supply_layers_logical to (layer, district_name, complex_id, obj_class, dev_group_name, source, snapshot_date) NULLS NOT DISTINCT (L1/L2 dev_group_name NULL stays transparent → their dedup unchanged; L3 distinct groups no longer collapse). Dry-run-verified vs prod catalog (applies clean, ROLLBACK clean). Worker: SupplyLayerRow gains dev_group_name (L1/L2=None, L3=group); _UPSERT_SQL adds it to INSERT/VALUES (CAST(:dev_group_name AS text)) + ON CONFLICT (key col, not in DO UPDATE SET). Service+worker regression tests assert same-district/ different-dev_group → distinct keys (no collapse). 234 supply tests pass. Deploy applies migration before container restart; collapsed data self-heals on next supply_layers_refresh. Verification = prod re-measure post-deploy. Refs #970 |
||
|---|---|---|
| .. | ||
| tasks | ||
| __init__.py | ||
| beat_schedule.py | ||
| celery_app.py | ||
| lifecycle.py | ||