fix(agent): make free Codex usable end-to-end (ENG-4785)#265
Conversation
Three bugs found on the staging dogfood:
1. wire_api: Codex rejects "chat" (removed Feb 2026) -> config now writes
wire_api = "responses"; Codex hits {base_url}/responses, which the CP proxy
forwards to OpenRouter's drop-in Responses API.
2. Terminal opened claude, not codex: bux-ttyd hardcoded /usr/bin/claude.
New bux-agent-shell launcher picks codex (free-DeepSeek profile active, or
signed in) vs claude, and ttyd now runs it. Symlinked in bootstrap.
3. TG showed 'Not signed in': both signed-in checks (_is_agent_authed and
_login_status_cached) shelled out to 'codex login status', which the free
path never passes (no codex login). Added _codex_free_profile_active() so an
active browser-use-free profile counts as codex-authed in both checks.
|
Retest gotcha: the existing staging box already has the old |
There was a problem hiding this comment.
2 issues found across 4 files
Reply with feedback, questions, or to request a fix.
Fix all with cubic | Re-trigger cubic
…ell (Cubic, ENG-4785) Cubic P2s on the launcher's free-profile detection: - profile*=* matched non-profile keys (profile_dir, profiles); now extract the key before '=', trim it, and require an EXACT 'profile' match. - table-header detection missed indented headers; now trim leading whitespace before matching so ' [profiles.x]' is correctly seen as a table and its in-table 'profile' isn't read as the top-level default. Tested: top-level free, no-space, decoy keys, in-table-only, indented table.
pr-reviewer (automated)Reviewed Blocking
The new ExecStart is
The old Fix: add the symlink to ln -sfn "$REPO_DIR/agent/bux-agent-shell" /usr/local/bin/bux-agent-shell(bootstrap re-asserting it is still correct for the already-provisioned case; install.sh needs it for first boot.) Nice-to-have1. Path source inconsistency across the 3 mirrored helpers. (
All three resolve to the same file when run as 2. Triplicated free-profile detection logic is a real maintenance liability. ( 3. codex login status 2>&1 | grep -qi "logged in" && \
! (codex login status 2>&1 | grep -qi "not logged in")Two subprocess invocations to dodge the "not logged in" substring matching "logged in". Capturing once into a var is cheaper and avoids a TOCTOU window: out="$(codex login status 2>&1)"
printf '%s' "$out" | grep -qi "not logged in" && return 1
printf '%s' "$out" | grep -qi "logged in"Minor — this path only runs when the free profile is inactive. 4. "codex picked but not actually usable" gap — pre-existing, not introduced here. All three helpers treat Confirmed correct
|
|
Fixed the blocking issue in dfe1808 — added the On the nice-to-haves: agreed the free-profile detection is now triplicated (2 Python + 1 bash) — they're in parity and tested, but I'll note deduping the two Python copies (box_agent + telegram_bot) as a follow-up. The others (config-path naming, double shell-out in codex_signed_in, proxy-down gap) are cosmetic/pre-existing; leaving for now to keep this PR scoped to the staging bugs. |
Why
Staging dogfood of the free DeepSeek Codex path hit three bugs. Fixes all three.
Fixes
1.
wire_api = "chat"rejected by Codex (codex#7782, removed Feb 2026). The config now writeswire_api = "responses"; Codex hits{base_url}/responses, which the CP proxy (cloud #4578) forwards to OpenRouter's drop-in Responses API.2. Web terminal opened
claude, notcodex.bux-ttyd.servicehardcoded/usr/bin/claude, so a codex-only (free) box launched Claude and hit "Not logged in". Newbux-agent-shelllauncher picks codex (free-DeepSeek profile active, or codex signed in) vs claude; ttyd runs it; symlinked in bootstrap.3. Telegram showed "Not signed in. Pick an agent." Both signed-in checks (
_is_agent_authedand_login_status_cached) shelled out tocodex login status, which the free path never passes (nocodex login— auth is the profile +bu-cp-token). Added_codex_free_profile_active()so an activebrowser-use-freeprofile counts as codex-authed in both checks.Pairs with
cloud #4578 (
/v1/responsesproxy route).Gates
ruff check agent/clean;bash -non bootstrap + launcher valid; free-profile detection unit-tested (top-level vs in-tableprofile).Summary by cubic
Makes the free DeepSeek Codex path usable end-to-end (ENG-4785). Fixes API routing, terminal agent selection, and Telegram auth detection so free Codex works without a login.
wire_api = "responses"so Codex hits/responses; CP proxy forwards to the OpenRouter Responses API (cloud #4578).bux-agent-shell(prefers Codex when top-levelprofile = "browser-use-free"is active or Codex is signed in);bux-ttyd.serviceupdated to use it. Profile detection is exact and ignoresprofile_dir/profilesand indented table headers.browser-use-freeprofile as “signed in” for Codex; added_codex_free_profile_active()and updated both auth checks to use it.Written for commit c1816b8. Summary will update on new commits. Review in cubic