Repository navigation
fix(gateway): treat a blank GATEWAY_HOST/GATEWAY_PORT as unset - #5801
Merged
WillemJiang merged 1 commit intoSep 24, 2026
Merged
Conversation
os.getenv's default only covers an unset variable, so `docker run -e
GATEWAY_PORT=` — or `GATEWAY_PORT=${PORT}` with PORT unset — reached
int("") and aborted the create_app() import that both entry points run.
Blank now falls back to the declared default, while "0" stays a real port.
WillemJiang
marked this pull request as ready for review
September 24, 2026 07:39
WillemJiang
approved these changes
Sep 24, 2026
2 of 9 tasks
WillemJiang
pushed a commit
that referenced
this pull request
Sep 25, 2026
…out as unset (#5840) Follows #5801 for the remaining numeric env reads that break on an empty value (`-e VAR=`, or `${VAR}` with VAR unset): - The WeChat QR worker guard read a blank GATEWAY_WORKERS as an invalid count and refused QR login, although the compose command starts one worker for it (`--workers ${GATEWAY_WORKERS:-1}`) and the other worker checks treat it as 1. A blank value now falls through to WEB_CONCURRENCY and then 1, so the guard still fails closed for real multi-worker setups. - The Lark broker aborted startup on int("") for a blank DEERFLOW_LARK_BROKER_PORT or DEERFLOW_LARK_BROKER_TIMEOUT; it now uses the defaults. Co-authored-by: Claude Opus 5.5 <[email protected]>
hawkli-1994
pushed a commit
to rongxinzy/deer-flow
that referenced
this pull request
Sep 27, 2026
…ance#5801) os.getenv's default only covers an unset variable, so `docker run -e GATEWAY_PORT=` — or `GATEWAY_PORT=${PORT}` with PORT unset — reached int("") and aborted the create_app() import that both entry points run. Blank now falls back to the declared default, while "0" stays a real port.
hawkli-1994
pushed a commit
to rongxinzy/deer-flow
that referenced
this pull request
Sep 27, 2026
…out as unset (bytedance#5840) Follows bytedance#5801 for the remaining numeric env reads that break on an empty value (`-e VAR=`, or `${VAR}` with VAR unset): - The WeChat QR worker guard read a blank GATEWAY_WORKERS as an invalid count and refused QR login, although the compose command starts one worker for it (`--workers ${GATEWAY_WORKERS:-1}`) and the other worker checks treat it as 1. A blank value now falls through to WEB_CONCURRENCY and then 1, so the guard still fails closed for real multi-worker setups. - The Lark broker aborted startup on int("") for a blank DEERFLOW_LARK_BROKER_PORT or DEERFLOW_LARK_BROKER_TIMEOUT; it now uses the defaults. Co-authored-by: Claude Opus 5.5 <[email protected]>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes #5800
Why
Trigger: while reading the gateway startup path for another change I noticed that
get_gateway_config()passes its fallbacks asos.getenvdefaults, which only apply when thevariable is absent — and this function is called at import time (
app.py:1074→create_app()→app.py:711).Pain:
docker run -e GATEWAY_PORT=, orGATEWAY_PORT=${PORT}withPORTunset, hands us"", andint("")raisesValueError: invalid literal for int() with base 10: ''. The whole gateway processdies before uvicorn binds, even though uvicorn is what actually picks the listening port and this
config only feeds the startup log line at
app.py:348plus the bind addresscreate_app()uses. Avariable that is set-but-empty means "not configured" everywhere else in this app
(
app/channels/dedupe_store.py:204doesint(os.environ.get("GATEWAY_WORKERS", "1") or 1), andapp/gateway/deps.py:83-86catches the sameValueError), so the failure is also inconsistent withthe repo's own convention.
What changed
GATEWAY_HOSTorGATEWAY_PORTnow falls back to the declared default (0.0.0.0/8001) instead of crashing the import, so an empty env var in a compose file or a shellexpansion is treated the same as an absent one.
GATEWAY_PORT=0still means port0(ask the OS for a free port) — the fallback is applied tothe string before
int(), not to the parsed number.GATEWAY_ENABLE_DOCSis deliberately untouched: for that flag""is a value a caller canreasonably mean as "off", and it fails closed today rather than crashing, so there is no bug to
fix there.
Surface area
backend/appOnly the empty-value case changes: for
hostit goes from""(an unusable bind address) to0.0.0.0, and forportfrom a hardValueErrorto8001. Every non-empty value parses exactly asbefore.
Bug fix verification
backend/tests/test_gateway_docs_toggle.py::test_blank_host_and_port_fall_back_to_defaultsmainand green on this branch? yestest_zero_port_is_not_treated_as_unsetis the control that keeps theorfallback honest about"0"; it passes in both columns, which is the point — it pins the case a naiveint(x or 8001)would get wrong.
Validation
makeis not available on this machine, so I ran the commands behindmake lint/make testdirectly from
backend/, withPYTHONPATH=.;packages/harness;packages/extension-apiagainst aPython 3.12 venv:
The full
make testsuite was not run locally; CI is the first full pass.Notes for the reviewer
app/gateway/__init__.pyre-exportsget_gateway_config, so the module import inuvicorn app.gateway.app:appis the first thing that touches this — hence "at import time" rather than "atfirst request".
AI assistance
Tool(s) used: Qoder agent (Claude), operating this account autonomously.
How you used it: the agent located the asymmetry, wrote the failing tests, the fix and this
description, and measured the red/green numbers above. The checkbox below is left unticked on
purpose: no human has read the diff yet, so nobody can claim that responsibility for it at the
moment of opening. The agent will amend or close the PR on request.