feat(setup): "Test ANPR" probe on ANPR-enabled cameras

Adds a bottom-of-modal "Test ANPR" button (shown only when a camera's
Plate recognition opt-in is checked) that captures a live snapshot off
the camera and runs it through the vision service, reporting the plate
read + confidence + elapsed time, or which stage failed.

- New POST /api/setup/test-anpr: builds the camera from the unsaved
  config (no DB write/device change, like /test), captures a snapshot,
  runs vision.analyze. Fail-soft like the runtime path (snapshot.ts):
  camera/vision failures are reported results, never a 500.
- Thread the existing VisionClient into setupRoutes; add an isCamera()
  type guard to @parking/devices.
- Web: testAnpr() client + AnprTestResult; button, hint, result line.
- i18n keys in sq + en (Catalog parity).

Claude-Session: https://claude.ai/code/session_01Xcm6ikLgGoCxxHrxtjkk5V
This commit is contained in:
2026-06-22 00:02:31 +02:00
parent 66c1291578
commit 742653aefb
7 changed files with 193 additions and 8 deletions
+4
View File
@@ -173,6 +173,10 @@ export interface CameraDevice extends Device {
captureSnapshot(ctx: SnapshotContext): Promise<Snapshot>;
}
export function isCamera(device: Device): device is Device & CameraDevice {
return typeof (device as Partial<CameraDevice>).captureSnapshot === "function";
}
export interface SnapshotContext {
readonly direction: "entry" | "exit";
}