Add debugging
This commit is contained in:
@@ -128,6 +128,7 @@ async def correlate_call(
|
||||
coords: Optional[dict] = location_coords or call_doc.get("location_coords")
|
||||
|
||||
matched_incident: Optional[dict] = None
|
||||
corr_debug: dict = {}
|
||||
|
||||
# A "thin" call carries no scene-identifying information — it is a pure
|
||||
# status transmission (10-4, en route, acknowledgement). Detected by the
|
||||
@@ -170,6 +171,10 @@ async def correlate_call(
|
||||
# Status/ack call — no scene data to reason about.
|
||||
# Attach to whichever recent incident was most recently active on this TGID.
|
||||
matched_incident = max(tg_recent, key=lambda inc: inc.get("updated_at", ""))
|
||||
corr_debug = {
|
||||
"corr_path": "fast/thin",
|
||||
"corr_incident_idle_min": round(_incident_idle_minutes(matched_incident, now), 1),
|
||||
}
|
||||
logger.info(
|
||||
f"Correlator fast-path (thin→last TGID incident): "
|
||||
f"call {call_id} → {matched_incident['incident_id']}"
|
||||
@@ -181,6 +186,10 @@ async def correlate_call(
|
||||
settings.location_proximity_km, is_dispatch=is_dispatch,
|
||||
):
|
||||
matched_incident = candidate
|
||||
corr_debug = {
|
||||
"corr_path": "fast/single",
|
||||
"corr_incident_idle_min": round(_incident_idle_minutes(candidate, now), 1),
|
||||
}
|
||||
logger.info(
|
||||
f"Correlator fast-path: call {call_id} → {candidate['incident_id']}"
|
||||
)
|
||||
@@ -193,6 +202,11 @@ async def correlate_call(
|
||||
matched_incident = _disambiguate(
|
||||
tg_recent, call_units, call_vehicles, coords, call_embedding
|
||||
)
|
||||
corr_debug = {
|
||||
"corr_path": "fast/disambig",
|
||||
"corr_incident_idle_min": round(_incident_idle_minutes(matched_incident, now), 1),
|
||||
"corr_candidates": len(tg_recent),
|
||||
}
|
||||
logger.info(
|
||||
f"Correlator fast-path (disambig {len(tg_recent)} candidates): "
|
||||
f"call {call_id} → {matched_incident['incident_id']}"
|
||||
@@ -210,6 +224,7 @@ async def correlate_call(
|
||||
)
|
||||
if dist_km <= settings.location_proximity_km:
|
||||
matched_incident = inc
|
||||
corr_debug = {"corr_path": "location", "corr_distance_km": round(dist_km, 3)}
|
||||
logger.info(
|
||||
f"Correlator location-path: call {call_id} → {inc['incident_id']} "
|
||||
f"(dist={dist_km:.2f}km)"
|
||||
@@ -246,10 +261,15 @@ async def correlate_call(
|
||||
best_cross_inc = inc
|
||||
if best_cross_inc and best_cross_score >= settings.embedding_cross_tg_threshold:
|
||||
matched_incident = best_cross_inc
|
||||
shared = len(call_unit_set & set(best_cross_inc.get("units") or []))
|
||||
corr_debug = {
|
||||
"corr_path": "cross-tg",
|
||||
"corr_score": round(best_cross_score, 4),
|
||||
"corr_shared_units": shared,
|
||||
}
|
||||
logger.info(
|
||||
f"Correlator cross-TG path: call {call_id} → {best_cross_inc['incident_id']} "
|
||||
f"(sim={best_cross_score:.3f}, "
|
||||
f"shared_units={len(call_unit_set & set(best_cross_inc.get('units') or []))})"
|
||||
f"(sim={best_cross_score:.3f}, shared_units={shared})"
|
||||
)
|
||||
|
||||
# ── 3. Slow path: embedding similarity (time-limited, same type) ──────────
|
||||
@@ -282,6 +302,11 @@ async def correlate_call(
|
||||
)
|
||||
if dist_km <= settings.location_proximity_km * 4:
|
||||
matched_incident = best_inc
|
||||
corr_debug = {
|
||||
"corr_path": "slow",
|
||||
"corr_score": round(best_score, 4),
|
||||
"corr_distance_km": round(dist_km, 3),
|
||||
}
|
||||
logger.info(
|
||||
f"Correlator slow-path: call {call_id} → {best_inc['incident_id']} "
|
||||
f"(sim={best_score:.3f}, dist={dist_km:.2f}km)"
|
||||
@@ -290,6 +315,10 @@ async def correlate_call(
|
||||
# High-confidence semantic match; geocode unavailable on one or
|
||||
# both sides — content similarity alone is sufficient evidence.
|
||||
matched_incident = best_inc
|
||||
corr_debug = {
|
||||
"corr_path": "slow/no-location",
|
||||
"corr_score": round(best_score, 4),
|
||||
}
|
||||
logger.info(
|
||||
f"Correlator slow-path (high-confidence, no location): "
|
||||
f"call {call_id} → {best_inc['incident_id']} (sim={best_score:.3f})"
|
||||
@@ -309,10 +338,19 @@ async def correlate_call(
|
||||
tags, location, location_coords,
|
||||
call_units, call_vehicles, call_embedding, call_severity, now,
|
||||
)
|
||||
corr_debug["corr_path"] = "new"
|
||||
else:
|
||||
# No match and either no type or creation suppressed — nothing to do
|
||||
return None
|
||||
|
||||
# Persist the correlation decision to the call document so it can be
|
||||
# inspected in Firestore or the admin UI without log-scraping.
|
||||
if corr_debug:
|
||||
try:
|
||||
await fstore.doc_set("calls", call_id, corr_debug)
|
||||
except Exception as e:
|
||||
logger.warning(f"Could not write corr_debug for call {call_id}: {e}")
|
||||
|
||||
return incident_id
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user