Skip to content
Router One
Back to Blog

OpenCode vs Claude Code vs Codex CLI: One Key for All Three

PublishedByRouter One TeamHow we measure

OpenCode, Claude Code, and Codex CLI are the three terminal coding agents most engineers shortlist in 2026, and the honest one-line answer is: pick Claude Code for maximum autonomy on the Claude family, Codex CLI for a sandbox-first agent on the GPT family, and OpenCode when you want an open-source agent tied to neither vendor.

OpenCode drives any OpenAI-compatible endpoint, which on Router One means the whole 40+ model catalog from one config file. All three bill through one Router One key: Claude Code calls the Anthropic-compatible endpoint, Codex CLI the Responses endpoint, OpenCode the OpenAI-compatible endpoint, and every request lands in the same wallet with the same per-request cost trace. Below: the properties you can verify — license, model families, config surface, billing path, China access — and the exact setup for running all three on one account.

If you have already narrowed it to the two vendor CLIs, Claude Code vs Codex CLI covers autonomy versus sandboxing in depth; if the question is terminal versus editor, start with Cline vs Cursor vs Claude Code. This post adds the corner both skip: the provider-agnostic open-source agent, and what changes once all three share one key.

Side by side

OpenCodeClaude CodeCodex CLI
LicenseOpen source (MIT)Anthropic's vendor CLI, not open sourceOpenAI's vendor CLI, open source (Apache-2.0)
Model families through Router OneAny chat model in the catalog: Claude, GPT, Gemini, DeepSeek, Grok, GLM, MiniMax, DoubaoClaude family + DeepSeek V4GPT family + DeepSeek V4
Endpoint family/v1/chat/completions (OpenAI-compatible)/v1/messages (Anthropic-compatible)/v1/responses
Config surfaceOne provider block in opencode.jsonTwo environment variables, or the env block of ~/.claude/settings.json~/.codex/config.toml with env_key
Billing through Router OneWallet, pay per token, per-key spend capSame wallet, same tracesSame wallet, same traces

The protocol row decides the rest: each vendor CLI reaches only the models Router One serves in its wire format, while /v1/chat/completions — the endpoint OpenCode speaks — is the one every Router One model serves, so OpenCode is the only tool of the three that reaches Claude, GPT, Gemini, and DeepSeek from a single config.

OpenCode: open source and tied to no vendor

OpenCode is an open-source (MIT) coding agent for the terminal: a TUI on a client/server core that treats model providers as configuration. You declare a provider in opencode.json, list the models it serves, and pick one as provider/model-id. Because it talks the OpenAI-compatible protocol to whatever base URL you give it, one provider block reaches every model on Router One, Claude included:

{
  "$schema": "https://opencode.ai/config.json",
  "provider": {
    "router-one": {
      "npm": "@ai-sdk/openai-compatible",
      "name": "Router One",
      "options": {
        "baseURL": "https://api.router.one/v1",
        "apiKey": "{env:ROUTER_ONE_API_KEY}"
      },
      "models": {
        "anthropic/claude-sonnet-5": { "name": "Claude Sonnet 5" },
        "openai/gpt-5.6-sol": { "name": "GPT-5.6 Sol" },
        "deepseek-v4-pro": { "name": "DeepSeek V4 Pro" }
      }
    }
  },
  "model": "router-one/anthropic/claude-sonnet-5"
}

Export the key in the shell that runs opencode (export ROUTER_ONE_API_KEY=sk-your-api-key); OpenCode fills in the {env:…} reference when it loads the file, or you can store the key through its /connect command. The file lives in your project root or globally at ~/.config/opencode/opencode.json, and opencode models router-one prints what you declared. Step by step: OpenCode + Router One.

The gotcha: a custom provider brings no model list of its own — a model you have not declared under models does not exist as far as OpenCode is concerned, and each key should be the exact catalog ID from /models, prefix included (anthropic/claude-sonnet-5) — the gateway accepts most official bare names as aliases, but the catalog ID is the form guaranteed to match. Add a limit object with context and output per model if you want the remaining-context display to work. Keep npm on @ai-sdk/openai-compatible, which OpenCode's docs pair with /v1/chat/completions; the docs also allow @ai-sdk/openai (Responses) and a base-URL override on the built-in Anthropic provider, but each reaches only the models its protocol serves natively, and we have not verified OpenCode's Anthropic-provider override end to end (the gateway does accept the x-api-key header that package sends).

Claude Code: maximum autonomy on the Anthropic protocol

Claude Code is Anthropic's terminal agent: run claude in a repo, describe the task, and it reads, edits, runs the tests, and iterates on its own, with hooks, skills, and CLAUDE.md for teams that want their conventions encoded. It speaks the Anthropic Messages protocol, so on Router One it uses the Anthropic-compatible endpoint and reaches the Claude family — Claude Opus 5, Claude Sonnet 5, Claude Haiku 4.5 — plus DeepSeek V4 (deepseek-v4-pro / deepseek-v4-flash) on the same endpoint. The setup is two environment variables:

export ANTHROPIC_BASE_URL=https://api.router.one
export ANTHROPIC_AUTH_TOKEN=sk-your-api-key

Or let the one-click script install Claude Code if it is missing, write the same two values into the env block of ~/.claude/settings.json, and verify the key with a one-token request:

curl -fsSL https://router.one/install/claude-code.sh | bash -s -- sk-your-api-key

The base URL carries no /v1 — Claude Code appends its own path. The Windows command is in the CLI setup guide.

The gotcha: two variables, not three. ANTHROPIC_API_KEY is not required — leave it unset, because a leftover export triggers an extra approval prompt on current builds. And precedence runs the other way from what most people expect: the env block in ~/.claude/settings.json overrides a shell export, so if a request trace shows a base URL you did not expect, check the file before the shell.

Codex CLI: sandbox-first on the Responses protocol

Codex CLI is OpenAI's open-source terminal agent (Apache-2.0). It is sandbox-first — commands run under explicit approval modes — and it speaks the Responses API wire format rather than classic Chat Completions, which is why generic relays 404 on it while a gateway that implements wire_api = "responses" natively does not (Codex and the Responses API). Through Router One it reaches the GPT family — GPT-5.6 Sol, GPT-5.5, GPT-5.4, GPT-5.3 Codex Spark — plus DeepSeek V4. The provider lives in ~/.codex/config.toml:

model = "gpt-5.6-sol"
model_provider = "router"

[model_providers.router]
name = "Router One"
base_url = "https://api.router.one/v1"
wire_api = "responses"
env_key = "ROUTER_ONE_API_KEY"

env_key is the mechanism: the file names an environment variable, and Codex reads your key from it and sends it as a Bearer token without touching your ChatGPT login state. Export ROUTER_ONE_API_KEY in your shell profile, or let the one-click script write the file, persist the variable, and verify the key:

curl -fsSL https://router.one/install/codex.sh | bash -s -- sk-your-api-key

The gotcha: the model line must name a model served on /v1/responses. A Claude-family ID in config.toml gets a 400 before any model runs — Claude is served on the Anthropic-compatible endpoint and on /v1/chat/completions, never on Responses, and each model page lists its endpoints. One relay-only failure worth knowing: Codex's review line sends the model ID codex-auto-review, which Router One lists in its catalog, so /review works without a review_model override.

Running all three on one key

The literal answer to "can one key run all three?" is yes — the same sk- key is accepted on all three endpoints. The better setup is one key per tool, all funded by the same wallet, because per-key attribution is what turns the ledger into answers:

  • A hard cap per tool. Set maxSpend on each key — say $10 for a one-week trial of an unfamiliar agent — and a runaway session stops at the cap while the wallet and the other two keys are untouched. rateLimit and tokenLimitTpm throttle a retry loop mid-flight.
  • A cost trace per request. Every call records the model, tokens, cost, latency, and status (Dashboard → Logs), so "was that expensive afternoon OpenCode or Claude Code?" is a filter by key, not a guess. The cost tracking page lists what the ledger records; per-key cost attribution shows the pattern in practice.
  • Same-model failover for all three. When an upstream returns a retryable 5xx or a timeout, Router One may retry the request on another healthy route serving the same requested model. It never swaps in a different model, and it is not a zero-downtime guarantee — long agent sessions should still tolerate the occasional failed call.
  • Switching models without switching tools. Claude Code moves to DeepSeek V4 with /model deepseek-v4-pro; Codex changes its model = line; OpenCode adds one entry under models. None needs a new account, key, or billing relationship. The models page is the live rate sheet — pricing starts as low as 10% of official provider list prices (up to 90% off) on select models (cheap Claude API, cheap GPT API) — and Pro/Max/Ultra plans sit alongside the wallet on pricing if you prefer a flat monthly number.

From mainland China

All three default to vendor endpoints that are unreliable from Chinese ISPs without a VPN, and vendor billing assumes a foreign card — OpenCode has no billing of its own and inherits whichever provider you configure. Router One's endpoints are directly reachable from the mainland with no VPN, and the wallet tops up with a card or Alipay through one hosted checkout, or with USDT/USDC on six chains (Tron, BSC, Ethereum, Polygon, Base, Arbitrum) — no US credit card required. If a tool still answers 403 or "unsupported country, region, or territory" after the switch, the endpoint has not actually changed: see the Claude Code 403 checklist and the region-block fix. Dedicated setup pages: Claude Code in China, Codex CLI in China, OpenCode + Router One.

FAQ

Can OpenCode use Claude models through Router One? Yes. OpenCode speaks the OpenAI-compatible protocol, and Router One serves the Claude family on /v1/chat/completions alongside every other model. Declare the exact catalog ID (for example anthropic/claude-sonnet-5) under models and select it as router-one/anthropic/claude-sonnet-5.

Can Claude Code use GPT models, or Codex CLI use Claude models? No. Claude Code speaks the Anthropic protocol and reaches the Claude family plus DeepSeek V4; Codex CLI speaks the Responses protocol and reaches the GPT family plus DeepSeek V4. A Claude ID sent to /v1/responses returns a 400 before any model runs. DeepSeek V4 is the one family all three tools can drive.

Do I need three API keys? One key works for all three tools. One key per tool, funded by the same wallet, is the recommended setup: each key carries its own maxSpend cap, and the per-request trace filters by key, so per-tool spend is a fact rather than an estimate.

Do I need Claude Pro, Claude Max, or ChatGPT Plus for these CLIs? No. Through Router One all three bill per token from a prepaid wallet at posted per-model rates, and OpenCode never had a vendor subscription to begin with. Router One's own Pro/Max/Ultra plans exist as an optional flat-rate alternative — see pricing.

Which of the three is cheapest to run? The model decides the bill, not the tool: the same model at the same posted rate costs the same from any of the three. What differs is how much context each agent sends per turn and how long its sessions run, which is why Claude Code token costs explained focuses on model mix, session hygiene, and per-key caps — advice that transfers to OpenCode and Codex unchanged.

Next steps

Create a key at router.one, cap it, and let a week of real work through each tool make the call.

Related canonical pages

This article belongs to the Claude Code China cluster. These pages are the commercial page, setup docs, evidence source, and trust references.

Related reads