openvibers/openrestream .env.example
.env.example
| 1 | # ═══════════════════════════════════════════════════════════════ |
| 2 | # OpenRestream — Environment Configuration |
| 3 | # Copy to .env for development. In production this is /etc/openvibe/openre.env (0600), read by |
| 4 | # every unit (openre-api, openre-session-coordinator, openre-rtmp-ingest@, openre-restream-worker@); |
| 5 | # the units set NODE_ENV, PORT and OPENRE_RELEASE themselves. |
| 6 | # Names only here: never commit a value. |
| 7 | # ═══════════════════════════════════════════════════════════════ |
| 8 | |
| 9 | # ── openre-api ───────────────────────────────────────────────── |
| 10 | PORT=4500 |
| 11 | HOST=127.0.0.1 |
| 12 | NODE_ENV=development |
| 13 | #BASE_URL=https://openre.stream |
| 14 | # Hops in front of Node that set X-Forwarded-For (Cloudflare → nginx → Node). |
| 15 | #TRUST_PROXY=2 |
| 16 | #COOKIE_SECURE=true |
| 17 | |
| 18 | # ── Identity: OpenVibe.Network ──────────────────────────────── |
| 19 | OV_NETWORK_URL=https://openvibe.network |
| 20 | OV_NETWORK_INTERNAL_URL=http://127.0.0.1:4000 |
| 21 | #OV_NETWORK_ISSUER=https://openvibe.network |
| 22 | # Pin the Network public key instead of fetching /api/.well-known/jwks (PEM, \n escapes allowed). |
| 23 | #OV_NETWORK_PUBLIC_KEY= |
| 24 | # OAuth client `openre`: browser sign-in for the UI (redirect https://openre.stream/auth/callback) |
| 25 | # and OpenRestream's own client-credentials tokens (Events, Media). |
| 26 | OV_OAUTH_CLIENT_ID=openre |
| 27 | OV_OAUTH_CLIENT_SECRET= |
| 28 | #OV_OAUTH_REDIRECT_URI=https://openre.stream/auth/callback |
| 29 | # A browser's Network JWT is accepted when its aud contains one of these. |
| 30 | #OPENRE_USER_AUDIENCES=openvibe.openre,openvibe.network |
| 31 | |
| 32 | # ── Store (PostgreSQL, shared by every OpenRestream process) ──────── |
| 33 | # PostgreSQL (ADR-035): DATABASE_URL serves through PgBouncer, DATABASE_DIRECT_URL (the owner) runs migrations/ at boot; |
| 34 | # OpenVibe.Host `roles/data/add-service.sh openre` writes both. Every OpenRestream process shares the database. Without |
| 35 | # DATABASE_URL, development runs on an embedded PGlite database in data/pglite (OPENRE_PGLITE_DIR): one process only. |
| 36 | DATABASE_URL= |
| 37 | DATABASE_DIRECT_URL= |
| 38 | VALKEY_URL= |
| 39 | |
| 40 | # ── Secrets ─────────────────────────────────────────────────── |
| 41 | # 32 bytes (64 hex chars or base64): encrypts restream destination keys and SRT passphrases at rest. |
| 42 | # Required for destinations; generate with `openssl rand -hex 32`. |
| 43 | OPENRE_SECRETS_KEY= |
| 44 | # The previous key while rotating OPENRE_SECRETS_KEY (decryption only). |
| 45 | #OPENRE_SECRETS_KEY_PREVIOUS= |
| 46 | |
| 47 | # ── RTMP ingest (openre-rtmp-ingest) ────────────────────────── |
| 48 | # Public port. Live's own ingest keeps 1935 until its RTMP is retired (README "Port plan"). |
| 49 | OPENRE_RTMP_PORT=1936 |
| 50 | # More public ports every worker also serves, e.g. 1935 after Live's RTMP is retired. |
| 51 | #OPENRE_RTMP_EXTRA_PORTS=1935 |
| 52 | # Public listener address (default 0.0.0.0). 127.0.0.1 keeps ingest host-local (production until the |
| 53 | # cutover, docs/cutover.md step 5). A new value takes effect with the next worker generation |
| 54 | # (deploy.sh workers, which runs deploy/scripts/workers.sh), never by restarting a worker. |
| 55 | #OPENRE_RTMP_BIND=0.0.0.0 |
| 56 | # What encoders are told: rtmp://<host>[:<port>]/live |
| 57 | #OPENRE_RTMP_PUBLIC_HOST=ingest.openre.stream |
| 58 | #OPENRE_RTMP_PUBLIC_PORT=1936 |
| 59 | # Loopback ports each worker generation takes for its RTMP play + HTTP-FLV endpoints. |
| 60 | #OPENRE_RTMP_INTERNAL_PORT_MIN=19360 |
| 61 | #OPENRE_RTMP_INTERNAL_PORT_MAX=19399 |
| 62 | #OPENRE_RTMP_CHUNK_SIZE=60000 |
| 63 | #OPENRE_RTMP_MAX_PUBLISHERS=64 |
| 64 | |
| 65 | # ── Ingest (JSMPEG, openre-jsmpeg@) ─────────────────────────── |
| 66 | # Public port: the broadcaster's MPEG-TS HTTP POST and the WebSocket viewers on it. Live's relay |
| 67 | # keeps 9710/9711 until the JSMPEG cutover (README "Port plan"). |
| 68 | #OPENRE_JSMPEG_PORT=9736 |
| 69 | # Public listener address (default 0.0.0.0). |
| 70 | #OPENRE_JSMPEG_BIND=0.0.0.0 |
| 71 | # What broadcasters/viewers are told (production default ingest.openre.stream, else 127.0.0.1). |
| 72 | #OPENRE_JSMPEG_PUBLIC_HOST=ingest.openre.stream |
| 73 | #OPENRE_JSMPEG_PUBLIC_PORT=9736 |
| 74 | # Loopback ports a worker generation serves its raw MPEG-TS data tap from (the restream worker |
| 75 | # reads it); first free port in the range, so two generations can run during a drain. |
| 76 | #OPENRE_JSMPEG_INTERNAL_PORT_MIN=19710 |
| 77 | #OPENRE_JSMPEG_INTERNAL_PORT_MAX=19749 |
| 78 | #OPENRE_JSMPEG_MAX_PUBLISHERS=64 |
| 79 | |
| 80 | # ── Ingest (WebRTC: WHIP + mediasoup SFU + viewers, openre-webrtc@) ── |
| 81 | # Public port: WHIP (POST/PATCH/DELETE /whip/…) and the /b/<key>, /w/<id> signaling WebSockets. |
| 82 | # Live's own WHIP lives on its app port until the WebRTC cutover. |
| 83 | #OPENRE_WEBRTC_PORT=9936 |
| 84 | # Public listener address (default 0.0.0.0). |
| 85 | #OPENRE_WEBRTC_BIND=0.0.0.0 |
| 86 | # What broadcasters/viewers are told (production default ingest.openre.stream, else 127.0.0.1). |
| 87 | #OPENRE_WEBRTC_PUBLIC_HOST=ingest.openre.stream |
| 88 | #OPENRE_WEBRTC_PUBLIC_PORT=9936 |
| 89 | # Loopback ports a generation serves RTP descriptors from (restream worker, Media's RTP recorder |
| 90 | # and the thumbnail grabber); first free port in the range. |
| 91 | #OPENRE_WEBRTC_INTERNAL_PORT_MIN=19810 |
| 92 | #OPENRE_WEBRTC_INTERNAL_PORT_MAX=19849 |
| 93 | #OPENRE_WEBRTC_MAX_PUBLISHERS=64 |
| 94 | # STUN/TURN servers handed to browsers, comma-separated. |
| 95 | #OPENRE_WEBRTC_STUN=stun:stun.l.google.com:19302 |
| 96 | # Live thumbnails: a frame grabbed from the worker's own source every interval, uploaded to Media |
| 97 | # (OPENRE_THUMBNAIL_NS, grant media.object.upload ns live) and carried on the session. |
| 98 | #OPENRE_THUMBNAILS=on |
| 99 | #OPENRE_THUMBNAIL_INTERVAL_MS=30000 |
| 100 | #OPENRE_THUMBNAIL_WIDTH=640 |
| 101 | #OPENRE_THUMBNAIL_NS=live |
| 102 | |
| 103 | # ── mediasoup (inside openre-webrtc) ────────────────────────── |
| 104 | # Public address RTC candidates are advertised with. REQUIRED in production: without it remote |
| 105 | # WebRTC clients cannot reach the worker's transports. |
| 106 | #MEDIASOUP_ANNOUNCED_IP= |
| 107 | # Interface RTC transports bind to (either name; MEDIASOUP_LISTEN_IP wins). |
| 108 | #MEDIASOUP_LISTEN_IP=0.0.0.0 |
| 109 | #OPENRE_MEDIASOUP_LISTEN_IP=0.0.0.0 |
| 110 | # Announced address under the OPENRE_ prefix (MEDIASOUP_ANNOUNCED_IP wins when both are set). |
| 111 | #OPENRE_MEDIASOUP_ANNOUNCED_IP= |
| 112 | # UDP port range for RTC (never Live's 10000–10100) and how many mediasoup workers per process. |
| 113 | #OPENRE_MEDIASOUP_MIN_PORT=10200 |
| 114 | #OPENRE_MEDIASOUP_MAX_PORT=10300 |
| 115 | #OPENRE_MEDIASOUP_WORKERS=1 |
| 116 | |
| 117 | # ── Workers, leases, drain ──────────────────────────────────── |
| 118 | #OPENRE_WORKER_HEARTBEAT_MS=2000 |
| 119 | # A worker silent this long is lost: its sessions fail and its outputs move to another worker. |
| 120 | #OPENRE_WORKER_LEASE_MS=15000 |
| 121 | # A draining generation keeps its sessions at most this long (default 24 h), then ends them. |
| 122 | #OPENRE_DRAIN_MAX_MS=86400000 |
| 123 | #OPENRE_COORDINATOR_INTERVAL_MS=1000 |
| 124 | #OPENRE_RESTREAM_POLL_MS=1000 |
| 125 | |
| 126 | # ── Restream outputs (openre-restream-worker) ───────────────── |
| 127 | #OPENRE_FFMPEG_PATH=ffmpeg |
| 128 | # Static OpenSSL ffmpeg used for rtmps:// destinations (as Live's bin/ffmpeg). |
| 129 | #OPENRE_FFMPEG_OPENSSL_PATH= |
| 130 | #OPENRE_MAX_DESTINATIONS=10 |
| 131 | # Allow destinations on loopback/private/link-local hosts (off: SSRF rule). |
| 132 | #OPENRE_DEST_ALLOW_PRIVATE=false |
| 133 | #OPENRE_OUTPUT_LOG_LIMIT=200 |
| 134 | #OPENRE_RESTART_BASE_MS=5000 |
| 135 | #OPENRE_RESTART_MAX_MS=120000 |
| 136 | #OPENRE_MAX_RESTARTS=30 |
| 137 | #OPENRE_RAPID_CRASH_MS=5000 |
| 138 | #OPENRE_RAPID_CRASH_GIVEUP=4 |
| 139 | #OPENRE_LIVE_ACK_TIMEOUT_MS=20000 |
| 140 | #OPENRE_STABLE_MS=30000 |
| 141 | #OPENRE_OUTPUT_START_DELAY_MS=3000 |
| 142 | |
| 143 | # ── Events (OpenVibe.Events; relay runs in the coordinator) ─── |
| 144 | # Unset = relay off (rows still commit and wait). Grant: [openre, events.event.publish, openvibe.events]. |
| 145 | #EVENTS_URL=http://127.0.0.1:4300 |
| 146 | #EVENTS_PUBLISH=on |
| 147 | #EVENTS_RELAY_INTERVAL_MS=1000 |
| 148 | |
| 149 | # ── Recording requests (OpenVibe.Media) ─────────────────────── |
| 150 | MEDIA_URL=http://127.0.0.1:4100 |
| 151 | # The Media tenant recordings are filed under ('live' keeps them in the Live channel's gallery). |
| 152 | MEDIA_APP_ID=live |
| 153 | # Requests carry OpenRestream's Network service token (OV_OAUTH_CLIENT_SECRET; grant |
| 154 | # [openre, media.object.upload, openvibe.media] with namespace live). |
| 155 | # OPENRE_RECORDING=off disables recording requests. |
| 156 | #OPENRE_RECORDING=on |
| 157 | #OPENRE_RECORDING_START_DELAY_MS=2000 |
| 158 | |
| 159 | # ── Restore drills ──────────────────────────────────────────── |
| 160 | # OPENRE_DRILL=1 only in an `ovhost drill openre` instance (OpenVibe.Host sets it in the drill's |
| 161 | # override file): openre-api serves reads from the restored copy and refuses writes, /play/ and |
| 162 | # sign-in; the coordinator and every worker refuse to start; no events, no Media calls. |
| 163 | # NEVER set it here in production (scripts/cutover-preflight.js --only env fails if it is). |
| 164 | #OPENRE_DRILL= |
| 165 | |
| 166 | # ── Links ───────────────────────────────────────────────────── |
| 167 | #OV_LIVE_URL=https://openvibe.live |
| 168 | # OpenVibe Live on by default (server/live-link.js): a person's new stream also gets a slot on their Live channel, |
| 169 | # through Live's loopback POST /internal/openre/slots. OPENRE_LIVE_LINK=off turns it off. |
| 170 | #OV_LIVE_INTERNAL_URL=http://127.0.0.1:3000 |
| 171 | #OPENRE_LIVE_LINK=on |
| 172 | |
| 173 | # Per-actor limits on a signed-in person's API writes (server/api/actor-limits.js, roadmap WS-R task 4), per minute |
| 174 | # and per hour; key rotations, destination tests and new streams have tighter numbers. Services are not counted. |
| 175 | #OPENRE_LIMITS_MINUTE=120 |
| 176 | #OPENRE_LIMITS_HOUR=3000 |
| 177 |