- Created README.md in docs folder outlining project structure and documentation links. - Added SECURITY.md detailing the security model, threat model, authentication, transport security, network isolation, and incident response procedures. - Introduced SETUP.md providing a detailed setup guide for local and production environments, including prerequisites, environment setup, and Gitea integration. - Added STREAMING.md outlining the streaming pipeline, including production flow, source-media contract, playout and HLS packaging, cache contract, player behavior, and monitoring. - Updated architecture documentation to include links to new SETUP.md and STREAMING.md files for better navigation.
94 lines
4.0 KiB
Markdown
94 lines
4.0 KiB
Markdown
# Security Guide
|
|
|
|
Layered security model for Linear Void.
|
|
|
|
## Threat Model
|
|
|
|
```
|
|
┌──────────┐ ┌──────────┐ ┌──────────┐ ┌──────────┐
|
|
│ Client │───▶│Cloudflare│───▶│ nginx │───▶│ Backend │
|
|
│ (public) │ │ WAF+CDN │ │ proxy │ │ chat │
|
|
└──────────┘ └──────────┘ └────┬─────┘ └────┬─────┘
|
|
│ │
|
|
┌──────┴──────┐ ┌─────┴──────┐
|
|
│ /health │ │ /api/admin │
|
|
│ /metrics │ │ /ws (chat) │
|
|
│ /hls/* │ │ /api/chat/* │
|
|
│ (public) │ │ (auth req) │
|
|
└─────────────┘ └────────────┘
|
|
```
|
|
|
|
## Authentication & Sessions
|
|
|
|
- Login: `POST /api/admin/login` → cookie `linearvoid_admin_session`
|
|
- Cookie flags: `HttpOnly`, `SameSite=Strict`, `Secure` (over HTTPS)
|
|
- Server-side expiry via `ADMIN_SESSION_TTL_HOURS`
|
|
- Rate limit: 5 attempts/IP/5min via Redis
|
|
|
|
## Transport Security (TLS/HSTS)
|
|
|
|
- Cloudflare TLS mode: **Full (strict)** — valid origin cert required
|
|
- nginx listens on 80 internally; Cloudflare handles TLS termination
|
|
- HSTS header set by Cloudflare: `max-age=31536000; includeSubDomains; preload`
|
|
- WSS upgrade path: `/ws` through nginx → chat:3000
|
|
|
|
## Network Isolation
|
|
|
|
- All backend services on internal Docker network (`linearvoid-net`)
|
|
- Only nginx port exposed to host (443/80)
|
|
- Database, Redis, exporters inaccessible from outside
|
|
- `docker-compose.prod.yml` keeps ports internal via `expose:` not `ports:`
|
|
|
|
## Reverse Proxy Controls
|
|
|
|
- `auth_request /api/admin/auth` gate on all `/admin` and `/api/admin` paths
|
|
- Explicit `client_max_body_size 64m` for resumable upload chunks
|
|
- WebSocket upgrade headers: `Upgrade`, `Connection` preserved
|
|
- CORS headers on HLS: `Access-Control-Allow-Origin *`
|
|
- XSS protection: CSP headers served by Cloudflare
|
|
|
|
## Rate Limiting
|
|
|
|
| Resource | Limit | Window |
|
|
| ----------------- | ----- | ------ |
|
|
| WebSocket connect | 5/IP | 60s |
|
|
| Chat messages | 10/IP | 10s |
|
|
| Admin login | 5/IP | 5min |
|
|
|
|
Implemented via Redis `INCR` + `EXPIRE`.
|
|
|
|
## Secrets Management
|
|
|
|
- `.env` — local dev only, **gitignored**
|
|
- Gitea Actions secrets (`CI_*` prefix) for CI/CD
|
|
- Never commit: passwords, tokens, API keys, R2 credentials
|
|
- Production `.env` provisioned manually on host, never checked in
|
|
- Rotate admin password quarterly
|
|
|
|
## Data Protection
|
|
|
|
- PostgreSQL: chat history, moderation logs, media metadata
|
|
- Redis: append-only persistence for presence, rate limits, sessions
|
|
- HLS segments: ephemeral, regenerated by playout
|
|
- Backups: `scripts/backup-db.sh` (daily), `scripts/backup-weekly.sh`, `scripts/verify-backups.sh`
|
|
|
|
## Hardening Checklist
|
|
|
|
- [ ] HTTPS/WSS enforced end-to-end (Cloudflare Full strict)
|
|
- [ ] Strong admin credentials configured
|
|
- [ ] Secrets only in env/secrets stores (never committed)
|
|
- [ ] Proxy auth and websocket headers validated
|
|
- [ ] Upload limits and MIME validation active
|
|
- [ ] Rate limiting active (WS, messages, login)
|
|
- [ ] Cloudflare WAF/rate-limit rules active
|
|
- [ ] Backup/restore drills completed
|
|
- [ ] Security alerts routed (Prometheus alertmanager)
|
|
|
|
## Incident Response
|
|
|
|
1. Detect — alerts (ChatDown, RedisDown, HighChatLatency) or user reports
|
|
2. Triage — edge (Cloudflare), proxy (nginx), app (chat/playout), data (Redis/Postgres)
|
|
3. Contain — rate limit, credential rotate, service restart, slate mode activation
|
|
4. Recover — verify health endpoints, check Prometheus targets, validate HLS output
|
|
5. Record — timeline + corrective actions in `docs/incident-runbook.md`
|