Files
live/DEPLOYMENT.md
T
adminandClaude Opus 4.8 996e3fea39 feat: consolidate on the shadcn frontend and harden playback
Frontend
- Replace the Ant Design app with the shadcn/ui app as the single frontend,
  keeping the portfolio side-by-side revertible in this commit.
- Drop the abandoned mdui experiment and the AntD tree so there is one app,
  one router and one design system to maintain.

Live playback
- Stop racing the encoder. lowLatencyMode + liveSyncDurationCount:1 targeted a
  single 4s segment, so playback ran at up to 1.10x and the forward buffer
  bottomed out at 0.1s, re-buffering every segment. Measured over 40s:
  buffer min 0.1s -> 8.9s, rate 1.00 constant, 0 stalls.
- Remove the 落后 labels and the page-level edge-snapping timer that fought
  hls.js over two different definitions of "latency".
- Live can no longer be paused: the control is not rendered while it plays, so
  the icon can never misreport state.
- Fix autoplay: muted autoplay started silently and never unmuted, and the
  gesture that restored sound also toggled playback off. One owner now.

Source ("原画") rendition
- Publish the publisher's stream remuxed losslessly via -c:v copy alongside the
  transcoded ones, so a source option exists even when every ladder entry
  downsizes.
- Give renditions an ASCII path slug: the HLS path is part of the URL and
  MediaMTX rejects non-alphanumeric paths, so 原画 could never be served.

Backend
- Supervise MediaMTX from the backend: start it at boot and restart it on exit,
  never killing an origin it did not start.
- Clear stale HLS output before restarting an encoder; an ENDLIST-less playlist
  left by a dead encoder hangs hls.js forever.
- Mark JSON timestamps as UTC. utcnow().isoformat() emitted a naive string that
  JS read as local time, so every viewer heartbeat looked 8 hours old in UTC+8
  and the live board's active-viewer count was permanently zero.
- Rebind a viewer session when it arrives on another stream instead of failing,
  and survive the StrictMode double-heartbeat race on first insert.
- Replace the Linux-only /proc and os.getloadavg metrics with psutil.
- Complete MediaMTX's cookieCheck redirect inside /hls proxying, and hold the
  httpx client open for the streamed body.

Housekeeping
- Ignore RainOSS (it stores accessKeySecret), runtime output, TLS keys and
  .venv; remove generated screenshots, load test scripts and stray files.

Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
2026-09-22 18:07:56 +08:00

87 lines
3.6 KiB
Markdown

# Deployment
The maintained deployment target for this project is Windows first. Linux and macOS can still run services manually, but real end-to-end deployment testing should use the PowerShell flow below.
Runtime paths are resolved relative to the repository by default and can be overridden with environment variables.
- LS_DATABASE_URL: SQLAlchemy database URL.
- LS_REPLAY_MEDIA_DIR: server-local directory containing replay files. When started by start.ps1, the default is runtime\replay under the repository.
- LS_HLS_RUNTIME_DIR: backend and FFmpeg HLS output directory. When started by start.ps1, the default is runtime\hls under the repository.
## Windows deployment
Run these commands from PowerShell on the Windows node.
### 1. Install prerequisites
Required on PATH: Python 3.11+, FFmpeg, and MediaMTX. MediaMTX may instead be left in the repository's `mediamtx\` directory, which is where the backend looks second. Node.js is only needed to build the frontend for deployment.
### 2. Install application dependencies
```powershell
powershell -ExecutionPolicy Bypass -File .\start.ps1 -InstallDeps
```
### 3. Start the stack
```powershell
powershell -ExecutionPolicy Bypass -File .\start.ps1
```
This starts the FastAPI backend on 0.0.0.0:8080. The backend owns everything else:
- **MediaMTX** is started at boot if nothing is already answering its API on :9997, and restarted by the supervisor if it dies. Set `LS_MEDIA_ORIGIN_AUTOSTART=false` to manage it externally; the backend then only supervises transcoders.
- **Transcoders** are started for every live stream whose MediaMTX path is publishing, and restarted within ~10s of an ffmpeg process exiting.
- **HLS** is written under `runtime\hls` and served through `GET /hls/...`, which falls back to proxying MediaMTX's own HLS when the local files are absent.
Publish RTMP to rtmp://127.0.0.1:1935/live/<stream_key>. Backend docs are at http://127.0.0.1:8080/docs.
### 4. Useful variants
```powershell
powershell -ExecutionPolicy Bypass -File .\start.ps1 -HostAddress 0.0.0.0 -BackendPort 8080
```
### 5. Smoke test commands
```powershell
curl.exe http://127.0.0.1:8080/api/health
curl.exe http://127.0.0.1:9997/v3/paths/list
ffmpeg -version
mediamtx --version
nvidia-smi
```
If browser or network tests run from another machine, open the Windows firewall for ports 8080, 1935, and 8888.
## Windows edge node launcher
Build and start an edge node from a Windows edge machine:
```powershell
powershell -ExecutionPolicy Bypass -File .\edge-agent\start-edge.ps1 -Build -OriginUrl http://<origin-host>:8080 -NodeId edge-win-01 -Region default -HlsPort 8889 -ApiPort 9997
```
For normal subsequent starts, omit `-Build`:
```powershell
powershell -ExecutionPolicy Bypass -File .\edge-agent\start-edge.ps1 -OriginUrl http://<origin-host>:8080 -NodeId edge-win-01 -Region default -HlsPort 8889 -ApiPort 9997
```
The launcher sets the StreamCore edge environment variables, starts the Windows edge-agent executable, stores runtime data under `ProgramData\StreamCore\edge\<node-id>` by default, and writes logs to that node data directory. The edge agent then manages its embedded MediaMTX edge process.
## Edge node scripts
```cmd
mediamtx\scripts\start_origin.bat
mediamtx\scripts\start_edge.bat 1 127.0.0.1
mediamtx\scripts\check_multicast.bat
```
## Replay file safety
Replay records store paths relative to LS_REPLAY_MEDIA_DIR. Absolute paths and parent-directory traversal are rejected.
## Linux and macOS
Linux and macOS are not the primary deployment path. For local development, run the backend with uvicorn from `backend`, run the frontend with `npm run dev` from `frontend`, and set `LS_HLS_RUNTIME_DIR` to a writable directory.