fix(booth): backfill the live-feed plate + make plate search work
Two booth feed fixes: - Plate not showing until refresh. Plate recognition is async/advisory (snapshot.ts recognizePlate → a kind:"read" device_event keyed by the session identity), so it lands AFTER the entry/exit event already shipped over the WS without a plate; a refresh re-fetched via the bulk enrich path and showed it. Added a `plate-recognized` bus event (device-events.ts) emitted when the read is written; ws.ts forwards it; the client patchPlate(identity, plate) (live-store) backfills the already-rendered feed row in place and invalidates the Query-owned active-sessions list. No refresh. - Plate search didn't filter. Both the live-feed (BoothScreen) and active-sessions (ActiveSessions) search haystacks matched the wrong field — the displayed plate is the ENRICHED top-level e.plate/s.plate (set by enrichEvent), not payload.plate (the plate is unsigned, never in the signed payload). Switched the haystacks to the displayed field. Claude-Session: https://claude.ai/code/session_01Xcm6ikLgGoCxxHrxtjkk5V
This commit is contained in:
@@ -86,6 +86,18 @@ export interface LaneStatusEvent {
|
||||
readonly exit: boolean; // true = busy (a vehicle is at the exit vicinity)
|
||||
}
|
||||
|
||||
/** A plate was RECOGNIZED for a session AFTER its entry/exit event already shipped. Plate
|
||||
* recognition is async/advisory (a vision round-trip off the snapshot), so it lands a
|
||||
* moment after the signed event — too late for the event's own WS push to carry it. This
|
||||
* notifies the booth so it can fill in the plate badge on the already-rendered feed row /
|
||||
* active session in place, no refresh. Advisory; never touches the signed ledger. See
|
||||
* snapshot.ts (recognizePlate) + event-enrich.ts. */
|
||||
export interface PlateRecognizedEvent {
|
||||
readonly identity: string; // the session identity the plate is tied to
|
||||
readonly plate: string; // normalized plate text (trimmed, upper)
|
||||
readonly direction: "entry" | "exit";
|
||||
}
|
||||
|
||||
/** Per-lane RADAR presence — a vehicle-presence INPUT (loop/radar) is shorted at the
|
||||
* entry/exit barrier, i.e. "something is in the lane vicinity" BEFORE the camera has
|
||||
* confirmed a vehicle. Same signal that makes the physical button lamp (relay 3) blink:
|
||||
@@ -168,6 +180,16 @@ class DeviceEventBus extends EventEmitter {
|
||||
this.on("lane-presence", cb);
|
||||
return () => this.off("lane-presence", cb);
|
||||
}
|
||||
|
||||
/** Emitted when an async plate recognition completes for a session (after its event
|
||||
* already shipped). Lets the booth backfill the plate badge in place. Advisory only. */
|
||||
emitPlateRecognized(event: PlateRecognizedEvent): void {
|
||||
this.emit("plate-recognized", event);
|
||||
}
|
||||
onPlateRecognized(cb: (event: PlateRecognizedEvent) => void): () => void {
|
||||
this.on("plate-recognized", cb);
|
||||
return () => this.off("plate-recognized", cb);
|
||||
}
|
||||
}
|
||||
|
||||
/** Process-wide device event bus. */
|
||||
|
||||
Reference in New Issue
Block a user