Stream forwarding
ARGUS can relay any live TACLINK track to an external destination as either RTMP (push) or RTSP (pull). The backend (argus-api) spawns an FFmpeg relay per forward, persists status + stats to Firestore, and surfaces the active list inside the streams tile.
Opening the forward dialog
From a stream card in the TACLINK grid, hover to reveal
the overflow menu (⋯) and pick Forward. The forward dialog opens with
the stream pre-selected. The fwdDialog signal stores
{ peerId, trackId, streamName } so the dialog knows which track it’s forwarding.
The protocol picker
Two toggle buttons at the top of the dialog — RTMP or RTSP.
RTMP — push
You provide the destination URL. Typical shape:
rtmp://live.example.com/app/stream-keyThe FFmpeg relay will push the track there. Most streaming services (YouTube Live, Twitch, broadcast-grade CDNs, Wowza, Ant Media, OvenMediaEngine) accept RTMP ingest.
The URL can include a stream key or auth — whatever the destination expects. The URL is treated as sensitive and encrypted at rest with the operation’s E2E key before writing to Firestore.
RTSP — pull
No URL input. ARGUS’s backend exposes an RTSP endpoint; you pull from it. On
successful start, the forward record is populated with rtspPullUrl which the
dialog displays — copy it and paste into your player / recorder.
Useful for:
- Feeding a local NVR that speaks RTSP.
- Feeding an on-premise VMS that ingests RTSP.
- Partner agencies that want to pull with
ffmpeg/vlc/go2rtcwithout exposing their own push endpoint.
Fields common to both
- Name — required. Short label used in the active-forwards panel.
Click Start. The dialog closes and the forward appears in the active panel (usually within a second — “starting” state) then transitions to “active” once FFmpeg is producing bytes.
The active-forwards panel
A list at the bottom of the streams tile shows every active forward for this mission. Rows:
- Status dot — green for
active, amber forstarting, red forerror, grey forstopping. - Name (as you entered in the dialog).
- Protocol badge — RTMP or RTSP.
- Bitrate (kbps) — updated server-side every few seconds.
- Frames forwarded / dropped — hover the row for the detail tooltip.
- Stop button — terminates the forward.
The list is filtered to forwards whose status is starting or active — stopped
and errored forwards fall out of the list but remain in Firestore for history.
What’s stored in Firestore
Each forward writes a stream_forwards doc with:
id— UUID.operationId— which mission this belongs to.name— user-entered label.protocol—rtmp/rtsp.peerId+trackId— what track is being forwarded.destinationUrl— RTMP only. Encrypted with E2E key.rtspPullUrl— RTSP only. The generated pull URL (not sensitive — it’s not directly encrypted, but your argus-api TLS stops unauthorised access).status—starting/active/stopping/stopped/error.bitrateKbps,framesForwarded,droppedFrames— updated by the server.createdOn,createdBy— audit trail.
The service queries are filtered to the current mission and ordered by
createdOn descending.
Stopping a forward
Click Stop on the row. The service posts to
/api/stream-forwards/{forwardId}/stop. The forward transitions to stopping,
FFmpeg is killed cleanly, status flips to stopped, and the row falls out of
the active list.
If your browser crashed between starting and stopping, the forward keeps running — just come back to the console, sign in, and click Stop. Forwards aren’t bound to your session.
Failures
If the destination refuses the connection (wrong URL, auth failure, destination
down), the forward transitions to error with the reason captured in the
record. A toast in the UI surfaces the server error string.
Typical causes:
- RTMP auth wrong — your stream key is wrong or has expired.
- RTMP ingest down — the destination’s ingest endpoint is unreachable.
- Codec mismatch — ARGUS sends H.264 + AAC. If your destination only accepts H.265 or Opus, the forward will error.
- Network blocked — corporate firewalls on your server may block outbound RTMP (port 1935) — use RTMPS or RTSP instead.
Security considerations
- Destination URLs (RTMP push keys) are encrypted at rest with the operation’s E2E key. They never appear in logs.
- Operator UID is attached to every forward record for audit.
- Forwards persist beyond mission-end for compliance — see data retention for cleanup rules.
Known limitations
- No multi-destination — one forward = one destination. Use multiple forwards on the same track if you need several outputs.
- No transcoding options — you get the source codec as-is. If you need re-encoding, run a transcoder (Node-Media-Server, Ant Media) at the destination.
- No scheduled start — forwards start immediately when you click Start; there’s no “start at 14:00” option.
- Client-triggered only — there’s no workflow automation that starts a forward on an event (e.g. “start RTMP forward when mission activates”). Planned.
Related
- Streams overview
- Recordings — similar pipeline, but writes to mission storage instead of an external URL.
- E2E encryption — how the destination URL is protected.