Skip to content

Latest commit

 

History

History
41 lines (34 loc) · 2.01 KB

File metadata and controls

41 lines (34 loc) · 2.01 KB

Architecture

LiteDVR uses one persistent ingest pipeline per enabled camera. The RTSP connection is opened once and remains owned by that camera's recorder. FFmpeg packet-copies the native video stream into independent three-hour fragmented MP4 files and simultaneously emits a low-rate MJPEG preview stream. The recorded video is never decoded or transcoded.

RTSP camera
    | one persistent connection
    v
Camera recorder (supervised FFmpeg)
    +-- segment muxer --> 3-hour MP4 files --> SQLite metadata/timeline
    +-- MJPEG publisher --> isolated WebSocket subscribers (live view)

Browser playback --HTTP Range--> backend MP4 streamer --> stored MP4

The segment muxer owns rotation at fixed UTC three-hour boundaries (00:00, 03:00, 06:00, and so on), so rotating from one file to the next does not reconnect to the camera. A lightweight indexer watches the segment directory and keeps SQLite start/end times, size, and status current. Active segments are marked RECORDING; completed or interrupted files remain individually addressable for timeline seeking and download.

Each camera has its own live subscriber set. Opening or closing a live WebSocket only adds or removes that browser from the camera's publisher; it does not start another RTSP connection and does not stop recording. Playback never contacts the camera: it uses the backend's range-capable MP4 streamer.

FFmpeg runs in its own process group. On backend shutdown the entire group is terminated (escalating to a forced kill after five seconds if needed), and the supervisor restarts the ingest after an unexpected exit. Corrupt RTSP packets are discarded where possible; a genuine RTSP disconnect marks the active file interrupted and retries the same camera with bounded backoff.

SQLite contains metadata only. Video remains beneath the configured recordings directory (<group>/<camera>/segments for new segmented ingest), which is bind-mounted by Docker. The aiohttp backend is independent of the frontend and can run under Docker Compose or systemd.