Skip to content

cmux NEXT: Use an API key on a chat whose Claude Code or Codex is not signed in - #31517

Merged
teamleaderleo merged 1 commit into
feat-cmux-nextfrom
lane/byok-builtin-harness-key
Nov 2, 2026
Merged

teamleaderleo merged 1 commit into
feat-cmux-nextfrom
lane/byok-builtin-harness-key

Conversation

@teamleaderleo

@teamleaderleo teamleaderleo commented Nov 2, 2026 •

Copy link
Copy Markdown
Collaborator

Leo-ask: ask-f74602af08

Leo, 2026-10-26: "if user picks a model they don't have api key, we offer them to add credits or add their own api key"

#27058 shipped the Add Credits half, on the cmux model router's plan and credit refusals. The add their own API key half waited on key plumbing (manaflow-ai/cmuxterm-hq#5411): a key the app saved never reached a built-in harness. #30188 has since given acpmux _acpmux/agent_login/api_key. It saves a key where the agent's own CLI reads it (Claude's settings.json env.ANTHROPIC_API_KEY, or codex login --with-api-key with the key on stdin) and restarts the chat on it. Until now only Cloud chats offered it, through the Cloud sign-in card.

With this PR, a chat on this Mac whose built-in claude or codex fails a turn because it isn't signed in offers Use an API key after Sign in again, as an outlined button. It uses the same key field as the Cloud card: a password input, then Save. Send again resends the failed prompt, and only on the person's click.

  • cloudAgentLogin.ts: the shared builder is now agentLogin. cloudAgentLogin covers Cloud chats, as before. The new localApiKeyLogin covers chats on this Mac, and only the built-in claude and codex harnesses. Routes (claude-cr, claude-sr) set their own key and endpoint, so a saved key would never reach them and they get no key field.
  • TurnRows.tsx: a sign-in failure with no Cloud card renders <CloudSignIn keyOnly> after Sign in again.
  • No Rust or Swift changes. The host already allows _acpmux/agent_login/api_key on a click (AcpmuxPaneMethods.swift), and every acpmux advertises agent_login.

Once this lands, cmuxterm-hq#5411's key half is covered for local Claude Code and Codex chats. Two things stay open there: a router BYOK path, and Gemini.

Tests

bun test test/cloud-signin-card.test.tsx test/access-offer.test.tsx test/signed-out-rail.test.tsx: 30 pass. New tests cover:

  • the gating: built-in claude/codex only, never a route, a Cloud chat, a disconnected chat or an acpmux without agent_login;
  • a local signed-out card reading [Sign in again, Use an API key, …], with Save calling agent_login/api_key and Send again resending under a gesture ticket;
  • no key field on a failure that isn't a sign-in.

Observed / Not run

  • Ran: the bun tests above and scripts/web-lint.sh (fmt passed; the type-aware lint and the type check are left to CI on this host).
  • Not run: a DEV build. The card is unchanged CloudSignIn UI, and the gallery covers its states.

Changelog

  • Added: a chat whose Claude Code or Codex isn't signed in offers Use an API key next to Sign in again.

Agent session: agent session

🤖 Generated with Claude Code


View with [code]smith Autofix with [code]smith
Need help on this PR? Tag @codesmith-bot with what you need.


Summary by cubic

Lets a chat on this Mac whose built-in Claude Code or Codex isn't signed in offer Use an API key next to Sign in again. Previously only Cloud chats offered API key sign-in; this extends it to local built-in agents through the existing _acpmux/agent_login/api_key path, saving the key where the agent's own CLI reads it and restarting the chat on it.

  • The key field matches the Cloud card's (password input, Save, then Send again resends the failed prompt on click).
  • Routes (claude-cr, claude-sr) and Cloud chats get no key field: routes set their own key and endpoint, and a Cloud chat has its own card.

Written for commit 1fdc977. Summary will update on new commits.

View guided diff Turn on auto-fix

…r Codex is not signed in

Leo, 2026-10-26: "if user picks a model they don't have api key, we offer them to add credits or add their own api key"

#27058 shipped the Add Credits half (the router's plan and credit refusals). The key half waited
on key plumbing (manaflow-ai/cmuxterm-hq#5411); #30188 has since given acpmux
`_acpmux/agent_login/api_key`, which saves a key where the agent's own CLI reads it (Claude's
settings.json env.ANTHROPIC_API_KEY, `codex login --with-api-key`) and restarts the chat on it.
Only Cloud chats offered it. A chat on this Mac whose built-in `claude` or `codex` fails a turn
for want of a sign-in now shows Use an API key after Sign in again; Save stores the key and Send
again resends the failed prompt on the person's click. Routes (claude-cr, claude-sr) set their
own key and endpoint, so they get no key field.

Tests: bun test test/cloud-signin-card.test.tsx test/access-offer.test.tsx test/signed-out-rail.test.tsx -> 30 pass.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Agent-Session: https://cmux.com/deeplink/agent?id=aid-60c63e855fe3c933a547
@github-actions

github-actions Bot commented Nov 2, 2026 •

Copy link
Copy Markdown
Contributor

cmux status (one comment, edited in place; each line is updated by the job that owns it)

Review 1fdc977: HQ feed card · gallery before/after runs · checks

App of this head (app.zip, kept 1 day)

gh workflow run reload-build.yml -R manaflow-ai/cmux --ref feat-cmux-next -f tag=pr31517 -f ref=lane/byok-builtin-harness-key -f platform=macos -f backend_mode=local

Gallery before/after for 1fdc977: 16 states rendered, 0 images differ, 1724 more touched states not rendered. Images are in the run's artifact, not on this public PR; the independent review of this head reads them on its own, so the PR needs no hand-made screenshots of these states.

gh run download 41369346053 -R manaflow-ai/cmux -n gallery-advisory-31517-1fdc977d427c9f1fc84ded6e70dd1904bef7ac11 (then read gallery-review.json)

States
State Theme Status Diff Picked by
agent-pane.access-offer/turn-no-credits Apple System Colors Light unchanged 0% own TurnRows.tsx
agent-pane.access-offer/turn-no-credits Apple System Colors unchanged 0% own TurnRows.tsx
agent-pane.access-offer/turn-low-credits Apple System Colors Light unchanged 0% own TurnRows.tsx
agent-pane.access-offer/turn-low-credits Apple System Colors unchanged 0% own TurnRows.tsx
agent-pane.access-offer/turn-no-offer Apple System Colors Light unchanged 0% own TurnRows.tsx
agent-pane.access-offer/turn-no-offer Apple System Colors unchanged 0% own TurnRows.tsx
agent-pane.chat-width/standard Apple System Colors Light unchanged 0% own App.tsx
agent-pane.chat-width/standard Apple System Colors unchanged 0% own App.tsx
agent-pane.chat-width/wide Apple System Colors Light unchanged 0% own App.tsx
agent-pane.chat-width/wide Apple System Colors unchanged 0% own App.tsx
agent-pane.chat-width/wide-blocks Apple System Colors Light unchanged 0% own App.tsx
agent-pane.chat-width/wide-blocks Apple System Colors unchanged 0% own App.tsx
agent-pane.coderouter-offer/claude-key Apple System Colors Light unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/claude-key Apple System Colors unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/deepseek-key Apple System Colors Light unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/deepseek-key Apple System Colors unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/sign-in Apple System Colors Light unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/sign-in Apple System Colors unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/rate-limited Apple System Colors Light unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/rate-limited Apple System Colors unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/on-coderouter Apple System Colors Light unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/on-coderouter Apple System Colors unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/moving Apple System Colors Light unchanged 0% own TurnRows.tsx
agent-pane.coderouter-offer/moving Apple System Colors unchanged 0% own TurnRows.tsx
agent-pane.composer-edge/short-edge Apple System Colors Light unchanged 0% own App.tsx
agent-pane.composer-edge/short-edge Apple System Colors unchanged 0% own App.tsx
agent-pane.composer-edge/wide-edge Apple System Colors Light unchanged 0% own App.tsx
agent-pane.composer-edge/wide-edge Apple System Colors unchanged 0% own App.tsx
agent-pane.composer-edge/no-edge Apple System Colors Light unchanged 0% own App.tsx
agent-pane.composer-edge/no-edge Apple System Colors unchanged 0% own App.tsx
agent-pane.composer-floats/scrolled-to-end Apple System Colors Light unchanged 0% own App.tsx
agent-pane.composer-floats/scrolled-to-end Apple System Colors unchanged 0% own App.tsx

Pick other states with a Gallery: entry.id, entry.id/variant line in the PR body.

red: cmux-next checks (god files, concurrency, crash safety, l10n); NEW: red check: Web bundle key inputs (+4 more) is not red on the base fc32735; do not merge until green; see lane-rules

Shipped in:

@github-actions github-actions Bot added the risk:normal Risk tier (docs/ci/risk-tiers.md) label Nov 2, 2026
@teamleaderleo

Copy link
Copy Markdown
Collaborator Author

Review (subagent claude-opus-5-5 medium): SHIP at 1fdc977

The reviewer checked the real code. A local caller gets past acpmux's origin and shared-machine checks. The pane host allows _acpmux/agent_login/api_key on a click for a chat in the pane's scope. The gating never shows two cards. The useMemo deps are already complete. test/cloud-signin-card.test.tsx gives 20 pass.

Follow-ups (none blocking):

  • Gate localApiKeyLogin on summary.hostKind !== "cloud" too, the way Sign in again's reauthenticate is gated. It does no harm today: the key still lands on the chat's own machine.
  • Claude's key goes to ~/.claude/settings.json, so it applies to all of Claude Code on the Mac and takes precedence over a later /login. The card copy should say where the key goes, or the key should be scoped to the agent cmux starts.
  • The settings merge re-sorts a hand-edited settings.json (serde_json without preserve_order).
  • The comment in AcpmuxPaneMethods.swift (around lines 154-158) still says "Never this Mac's login".
  • No test covers the wiring in App.tsx.

@teamleaderleo
teamleaderleo merged commit 86e714c into feat-cmux-next Nov 2, 2026
190 of 205 checks passed
@teamleaderleo
teamleaderleo deleted the lane/byok-builtin-harness-key branch November 2, 2026 01:41

This branch was previously deployed

1 inactive deployment
ci-routing-agent — 1fdc977d Deployed Nov 2, 2026 by teamleaderleo via wait for same-key tree publisher #98060
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

risk:normal Risk tier (docs/ci/risk-tiers.md)

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant