Router One

Codex CLI and the Responses API: why most relays 404

OpenAI's Codex CLI doesn't call the classic Chat Completions API — it speaks the newer Responses API wire format. Most OpenAI-compatible relays only implement Chat Completions, so Codex pointed at them fails with 404s or malformed-request errors even though the same key works in curl. Router One implements the Responses wire format natively (wire_api = "responses"), so Codex works with a two-minute config change.

The one-line root cause

Codex sends requests to /responses-style routes with a request schema that Chat Completions servers don't recognize. A relay that only speaks Chat Completions answers with 404 (unknown path) or 400 (unknown fields). No amount of key or model fiddling fixes a wire-format mismatch — the gateway itself has to support it.

The working configuration

Point Codex at Router One in ~/.codex/config.toml and export your key in the same shell that runs codex:

config.toml
# ~/.codex/config.toml
model_provider = "router"

[model_providers.router]
name = "router"
base_url = "https://api.router.one/v1"
requires_openai_auth = true
wire_api = "responses"

# in your shell:
# export OPENAI_API_KEY=sk-your-router-one-key

Error checklist

If Codex still fails after the config change:

SymptomCauseFix
404 on every requestbase_url points at a relay without Responses API support, or has a typoSet base_url to https://api.router.one/v1 exactly and keep wire_api = "responses".
401 unauthorizedOPENAI_API_KEY isn't visible in the shell running codexExport the key in the same session (or your shell profile), then restart the terminal and re-run codex.
Model not foundModel ID doesn't match the catalogCopy the exact ID from the /models page — IDs are case-sensitive.
402 insufficient balanceWallet or key spend cap exhaustedTop up or raise the key's maxSpend in Dashboard → API Keys.
Config seems ignoredCodex reads a different config file than the one you editedConfirm the file lives at ~/.codex/config.toml (Windows: %USERPROFILE%\.codex\config.toml).

Verify from the trace

Once requests reach the gateway, every Codex call shows up in Dashboard → Logs with model, tokens, cost, and status. If the log stays empty while Codex errors, the failure is still local — config path or env var. If entries appear with 4xx, the trace names the exact limit.

FAQ

Why does my key work in curl but not in Codex?
curl exercises the Chat Completions surface; Codex uses the Responses API wire format. A relay can pass the curl test and still 404 for Codex. The gateway must implement the Responses wire format — Router One does.
What does wire_api = "responses" actually do?
It tells Codex which protocol shape to speak with the provider block. With "responses", Codex sends Responses-API-formatted requests; the endpoint on the other side has to understand them natively.
Does the base URL need /v1?
Yes — for Codex the OpenAI-compatible base URL is https://api.router.one/v1 including /v1. That's the opposite of Claude Code, whose Anthropic-compatible base URL has no /v1 suffix.
Which models can Codex use through the gateway?
Any chat-capable model in the catalog with its exact model ID — the /models page lists IDs, prices, and context windows. You're not locked to a single family.
Does this work from Mainland China?
Yes. The gateway is reachable from Mainland China without a VPN; the config.toml above is identical everywhere.