ArcCluster: Local-First Desktop Monitor for a Face Detection Agent
Two processes, one socket, one data directory — and the handful of places where that arrangement is honest about being unfinished.
The problem
Deploying a face detection and clustering system on a Jetson edge device required a local-only desktop monitor that could receive real-time events without cloud dependencies, handle model swapping (YuNet ONNX detector, ONNX/histogram embedder) without code changes, and synchronize state across a Rust desktop app and a Python pipeline over an unreliable local network.
The solution
Built a Tauri desktop shell that serves a Dioxus WebAssembly UI from the local filesystem, paired with a Python pipeline on Jetson that runs YuNet ONNX detection with a histogram fallback embedder and online cosine-similarity clustering; both sides share a data directory (ARC_DATA_DIR) for events.jsonl and clusters.json and push updates over a TCP JSONL socket (default 0.0.0.0:8787) with all model and clustering knobs controlled by environment variables.
Outcomes
- A YuNet ONNX detector and an ONNX or histogram embedder, both swappable at startup through `ARC_*` environment variables, so no model change needs a recompile.
- Cluster assignment is gated on both similarity and cluster size, so one bad embedding cannot define a face on its own.
- The desktop UI is a Dioxus WebAssembly bundle served locally by Tauri — no CDN, no webfonts, no network dependency at render time.
+2 more in the write-up
Inside the write-up
- Two processes and a socket
- Swapping models without rebuilding
- Clustering is deliberately slow to trust itself
- Persistence is two files and no more
- The socket is the weakest part, on purpose
- What is not finished