Vordr Camera Viewer
A self-hosted, view-only live viewer for eight PoE cameras that installs on an iPhone home screen. WebRTC with no transcoding, pinch-zoom and PTZ, and private cameras that unlock with a passkey. Nothing leaves the private network.
- J1–J8
PoE cameras
RTSP, H.264 / H.265
- U1
go2rtc
WebRTC, no transcode
- U2
Backend
credentials, PTZ, passkeys
- U3
PWA
iPhone home screen
The camera vendor’s iOS app relays through its cloud and fails off Wi-Fi, even with a VPN up. A browser over the VPN works fine, so this is a browser app that feels native.
How it works
- go2rtc pulls each camera’s RTSP stream and serves WebRTC, with MSE as a fallback. There is no transcoding: tiles use the H.264 sub-stream, and full screen uses the H.265 main stream wherever the browser can decode it.
- The backend holds every credential, makes the camera API calls for PTZ and presets, health-checks each camera, and proxies the stream socket while accepting only known stream names. The browser never sees a camera password or stream URL.
- The PWA has pinch-zoom, swipe between cameras, lens switching and a PTZ thumb pad. Off-screen tiles pause, and every visible stream restarts when the app returns from the background.
Decisions
- Tiles request video only. With audio in the offer the player preferred MSE over WebRTC. Dropping audio from muted tiles gets lower latency and less data. Full screen adds Opus audio on demand only.
- No STUN or TURN. The WebRTC address is fixed and the player’s default public STUN servers are overridden, so no request leaves the network.
- The network is the perimeter, because a login inside an iOS home-screen app is the fragile part. Cameras can be marked private: they’re hidden and refused by the server until a passkey (Face ID) unlocks them for twelve hours.
The bug worth writing down
The reverse proxy’s access list only applied to its default route. The custom location for the video socket bypassed it until the allow and deny rules were repeated there. Access control that covers the page but not the stream isn’t access control.