ViewPane
ReleasedFrigate NVR Companion App
A polished native mobile app — direct-connect, no CampbellSoft servers, zero data collection, encrypted credential storage, and a fully self-hostable push pipeline. Built to feel like a first-party app, not a third-party afterthought.
About
ViewPane is a production-grade mobile app, live on iOS with Android to follow, built end-to-end on React Native + Expo. The bar was an app-store-quality experience for users who already chose to keep their data on their own hardware: fast, opinionated, and free of the upsell patterns that dominate the consumer mobile-app market.
Existing third-party apps in this space are hobbyist quality, abandoned, or poorly reviewed. ViewPane fills that gap with polish, a privacy posture that holds up to scrutiny, and a push notification stack that keeps camera events and alert rules on the user’s own hardware.
ViewPane is live on the App Store. Android is heading into Google Play closed testing: testers get it first, and there is no date for the public listing yet. Android users can get on the list for the opt-in email when the test opens. The product site is at viewpane.app.
Architecture
- Direct-connect — App talks directly to the user’s server REST API on their LAN or VPN
- No CampbellSoft servers — Nothing of ours in the loop, ever. No account system, no telemetry, no analytics
- Optional self-hosted push relay — A small Node.js + SQLite container the user runs on their own hardware, subscribing to a local MQTT event stream and forwarding alerts (best-effort, via platform push) so they can arrive even when the app is closed. Binds to localhost or VPN by default; never expands a user’s attack surface
- Encrypted credentials — Server URLs, tokens, and passwords stored in iOS Keychain / Android Keystore via expo-secure-store
- Dual-URL auto-failover — Configure both a LAN URL and an external URL (Tailscale, Cloudflare Tunnel, or reverse proxy). The app tries local first, falls back to external automatically when off-network, and switches back when home Wi-Fi reappears — no manual toggling
- Tailscale-first remote access — WireGuard-encrypted end-to-end, no port forwarding required
Features
Live Views
- Multi-server support with one-tap edit
- Static thumbnail grid (2- or 3-column, user’s choice) with manual refresh-all + scheduled auto-refresh
- Live Wall mode — multi-pane grid with configurable polling rate (1–10 fps)
- Fullscreen view with auto-hiding controls
- Connection status indicator shows whether the app is on LAN or External path
Events & Clips
- Filter chips for source, object type, and time range
- Persistent event thumbnails with snapshot + clip playback
- Download-first clip playback — pre-fetches the full mp4 to local cache before play, sidestepping streaming-mp4 truncation issues common with the upstream clip endpoint
- Motion-vs-clip duration shown separately so users know when a clip extends beyond the actual motion event
- Zone display — surfaces which zones an object entered
Recordings Timeline
- Pull continuous footage for any window where the server has recordings
- Quick presets (Last 1 / 5 / 15 / 30 min) plus custom date + duration
- Files cache briefly during playback, auto-clear on exit
Notifications
- Per-source notification rules synced to the relay so server-side filtering is per-device
- Schedule — Always, Night (10pm–6am), Day (6am–10pm), Custom (user-set 24-hour window with midnight wrap support), or muted via a per-source toggle
- Critical Schedule — independent of the alert schedule, designates when alerts route to a MAX-importance Android channel that overrides Do Not Disturb
- Tap a notification → app opens directly to that event’s detail page
- Relay-side filters: configurable minimum confidence, label blacklist/whitelist, per source+label cooldown, stationary-object filter
Diagnostics
- Server Status screen — per-source FPS, per-detector inference time, service uptime + version, storage usage with progress bars
- Cache management — clear thumbnails, clear video cache (with size readout)
Tech Stack
- React Native + Expo SDK 54 — iOS + Android from one codebase
- TypeScript strict mode throughout
- expo-router — file-based navigation
- expo-secure-store — encrypted credential storage
- expo-notifications + expo-device — push handling, foreground display, deep-link tap routing
- expo-video — native mp4 / fMP4 playback with hardware decode
- expo-image — efficient snapshot rendering with built-in memory caching
- expo-file-system — download-first video pipeline
- Self-hosted Push Relay — Node.js 22 + better-sqlite3 + mqtt.js, multi-arch Docker image published to GHCR, no external dependencies beyond the user’s own stack and Expo’s free Push API
What Makes It Different
Most consumer mobile apps in adjacent categories are built around a vendor cloud that locks users into subscriptions and stores their data on someone else’s servers. ViewPane assumes the opposite — the user already owns their stack, and the app’s job is to be a polished mobile surface for it. No telemetry, no account system, no upsells toward a cloud tier that doesn’t exist, and no third-party SDK ever sees a frame of user data.
The push notification stack in particular is a clean break from how most mobile apps handle background alerts. Instead of handing camera events to a vendor cloud, ViewPane ships a small Docker container the user runs themselves. The relay subscribes to a local MQTT stream, decides on the user’s own hardware which events deserve an alert, and hands only the finished notification to Expo’s push service for delivery through Apple and Google. Video and camera credentials are never sent to Expo or to us.
Privacy
ViewPane collects zero data. No analytics, no telemetry, no crash reporting. All traffic flows directly between the user’s phone and their server. Notification metadata flows through Expo’s Push API on its way to the device — no images, no clips, no location, no account info. Full privacy policy and terms.