refactor(renderer)!: prefix every renderer env var with RENDERER_

The renderer's settings now read RENDERER_HOST, RENDERER_PORT,
RENDERER_MAX_CONCURRENT_RENDERS, RENDERER_RENDER_TIMEOUT_MS,
RENDERER_MAX_OPTIONS, and RENDERER_MAX_OPTION_CHARS, so they read as
renderer settings and cannot clash with the bot's variables, which
Coolify injects into every service. NODE_ENV keeps its standard name.

BREAKING CHANGE: the unprefixed HOST, PORT, MAX_CONCURRENT_RENDERS,
RENDER_TIMEOUT_MS, MAX_OPTIONS, and MAX_OPTION_CHARS are no longer read
by the renderer.
This commit is contained in:
tiennm99 committed 2026-10-03 12:05:56 +07:00
1 parent 11ed121af9
commit 83321fa330
7 files changed
+35 -32

No files matched your search

+8 -6
View File
@@ -57,12 +57,14 @@ services:
restart: unless-stopped
environment:
NODE_ENV: production
HOST: 0.0.0.0
PORT: "3000"
MAX_CONCURRENT_RENDERS: ${MAX_CONCURRENT_RENDERS:-1}
RENDER_TIMEOUT_MS: ${RENDER_TIMEOUT_MS:-15000}
MAX_OPTIONS: ${MAX_OPTIONS:-32}
MAX_OPTION_CHARS: ${MAX_OPTION_CHARS:-40}
# Every renderer setting carries the RENDERER_ prefix so it cannot clash
# with the bot's variables, which Coolify also injects into this service.
RENDERER_HOST: 0.0.0.0
RENDERER_PORT: "3000" # keep in sync with the bot's RENDERER_URL and the healthcheck
RENDERER_MAX_CONCURRENT_RENDERS: ${RENDERER_MAX_CONCURRENT_RENDERS:-1}
RENDERER_RENDER_TIMEOUT_MS: ${RENDERER_RENDER_TIMEOUT_MS:-15000}
RENDERER_MAX_OPTIONS: ${RENDERER_MAX_OPTIONS:-32}
RENDERER_MAX_OPTION_CHARS: ${RENDERER_MAX_OPTION_CHARS:-40}
expose:
- "3000"
healthcheck:
+3 -2
View File
@@ -60,8 +60,9 @@ compose network, so it needs no domain, publishes no port, and takes no auth
token. Its API is unauthenticated, so never publish a port or attach a domain
to it.
Renderer tuning (`MAX_CONCURRENT_RENDERS`, `RENDER_TIMEOUT_MS`, `MAX_OPTIONS`,
`MAX_OPTION_CHARS`) can be set in Coolify too; the defaults are in
Renderer tuning (`RENDERER_MAX_CONCURRENT_RENDERS`,
`RENDERER_RENDER_TIMEOUT_MS`, `RENDERER_MAX_OPTIONS`,
`RENDERER_MAX_OPTION_CHARS`) can be set in Coolify too; the defaults are in
[`renderer/docs/deployment.md`](../renderer/docs/deployment.md). Give the host
1-2 GB of headroom for the renderer's Chrome.
+6 -6
View File
@@ -1,8 +1,8 @@
PORT=3000
HOST=0.0.0.0
RENDERER_PORT=3000
RENDERER_HOST=0.0.0.0
NODE_ENV=production
MAX_CONCURRENT_RENDERS=1
RENDERER_MAX_CONCURRENT_RENDERS=1
# Remotion browser timeout floor is 7000ms; lower values are raised to 7000.
RENDER_TIMEOUT_MS=15000
MAX_OPTIONS=32
MAX_OPTION_CHARS=40
RENDERER_RENDER_TIMEOUT_MS=15000
RENDERER_MAX_OPTIONS=32
RENDERER_MAX_OPTION_CHARS=40
+3 -3
View File
@@ -67,7 +67,7 @@ result and its rarity — the service only draws it.
Response is a silent H.264 `video/mp4` (Telegram plays it as an animation)
with `X-Gacha-Rarity` and `X-Render-Duration-Ms` headers. All routes share the
`MAX_CONCURRENT_RENDERS` slots. No game assets are used.
`RENDERER_MAX_CONCURRENT_RENDERS` slots. No game assets are used.
pack-cards animates on the browser clock, so the wish does not use Remotion
compositions. `src/render/render-gacha.js` keeps one headless Chrome per
@@ -182,6 +182,6 @@ docker run --rm -p 3000:3000 miti99bot-renderer
```
Recommended starting resources: 1-2 vCPU and 1-2 GB RAM, with
`MAX_CONCURRENT_RENDERS=1`. `RENDER_TIMEOUT_MS` defaults to `15000` and is
raised to Remotion's `7000ms` browser timeout floor when configured lower.
`RENDERER_MAX_CONCURRENT_RENDERS=1`. `RENDERER_RENDER_TIMEOUT_MS` defaults to
`15000` and is raised to Remotion's `7000ms` browser timeout floor when configured lower.
The API has no authentication; publish its port only on a trusted network.
+8 -8
View File
@@ -28,15 +28,15 @@ Avoid for v1:
## Runtime
Required env vars:
Env vars, all optional (defaults shown):
```sh
PORT=3000
HOST=0.0.0.0
MAX_CONCURRENT_RENDERS=1
RENDER_TIMEOUT_MS=15000
MAX_OPTIONS=32
MAX_OPTION_CHARS=40
RENDERER_PORT=3000
RENDERER_HOST=0.0.0.0
RENDERER_MAX_CONCURRENT_RENDERS=1
RENDERER_RENDER_TIMEOUT_MS=15000
RENDERER_MAX_OPTIONS=32
RENDERER_MAX_OPTION_CHARS=40
```
The root `compose.yml` forwards the tuning values with `${VAR:-default}`
@@ -50,7 +50,7 @@ including `libnspr4` and `libnss3`. Prefer Docker for consistent verification.
The Docker image runs `npm run browser:ensure` during build so production requests
do not need to download Chrome Headless Shell on first render.
`RENDER_TIMEOUT_MS` is a total render timeout. Values below `7000` are raised to
`RENDERER_RENDER_TIMEOUT_MS` is a total render timeout. Values below `7000` are raised to
`7000` because Remotion's browser timeout has that minimum.
## Health
+6 -6
View File
@@ -30,14 +30,14 @@ const parsePositiveInt = (value, fallback) => {
*/
export const loadConfig = (env = process.env) => {
return {
host: env.HOST || '0.0.0.0',
port: parsePositiveInt(env.PORT, 3000),
maxConcurrentRenders: parsePositiveInt(env.MAX_CONCURRENT_RENDERS, 1),
host: env.RENDERER_HOST || '0.0.0.0',
port: parsePositiveInt(env.RENDERER_PORT, 3000),
maxConcurrentRenders: parsePositiveInt(env.RENDERER_MAX_CONCURRENT_RENDERS, 1),
renderTimeoutMs: Math.max(
minRenderTimeoutMs,
parsePositiveInt(env.RENDER_TIMEOUT_MS, 15000),
parsePositiveInt(env.RENDERER_RENDER_TIMEOUT_MS, 15000),
),
maxOptions: parsePositiveInt(env.MAX_OPTIONS, 32),
maxOptionChars: parsePositiveInt(env.MAX_OPTION_CHARS, 40),
maxOptions: parsePositiveInt(env.RENDERER_MAX_OPTIONS, 32),
maxOptionChars: parsePositiveInt(env.RENDERER_MAX_OPTION_CHARS, 40),
};
};
+1 -1
View File
@@ -3,7 +3,7 @@ import {loadConfig, minRenderTimeoutMs} from '../src/config.js';
describe('loadConfig', () => {
test('keeps render timeout compatible with Remotion browser timeout limits', () => {
const config = loadConfig({RENDER_TIMEOUT_MS: '500'});
const config = loadConfig({RENDERER_RENDER_TIMEOUT_MS: '500'});
expect(config.renderTimeoutMs).toBe(minRenderTimeoutMs);
});