Skip to main content
ValarCode routes the OpenAI Codex CLI through Valar by editing its config.toml. Codex keeps speaking the OpenAI Responses API and you keep picking your model; the gateway maps whatever it sends to the target your routing resolves to. See Set up ValarCode for the shared setup and the client-id model.

Prerequisites

  • The OpenAI Codex CLI installed, with a ~/.codex config directory. Run Codex once so the directory exists.
  • A Valar coding key (vlrcode_…) and the valar CLI (install).

Enable routing

Run once per machine:
The routing lives entirely in config.toml, with no env var, shell-rc edit, or new-terminal step. Then restart Codex (or the ChatGPT app, if that is where you run Codex) and start a new conversation. Check the state any time:

What gets written

valar codex on edits ~/.codex/config.toml. It sets the root provider to Valar and adds a provider block that points at the gateway and carries your credentials in request headers:
In detail, enabling:
  • Sets the root model_provider to valar so Codex uses the Valar provider block.
  • Writes base_url with the /v1 surface. Codex speaks the OpenAI Responses API (wire_api = "responses") and appends /responses, so requests land on https://api.valarhq.ai/v1/responses.
  • Puts the coding key on experimental_bearer_token, which Codex renders as Authorization: Bearer on the wire. It must not be an Authorization entry in http_headers. Codex treats that name as reserved and drops it (confirmed from codex-cli 0.145), which sends requests with no credential at all.
  • Adds the X-Valar-Client-Id, X-Valar-Harness and X-Valar-Cli-Version request headers. The client-id header is omitted entirely when there is no client id, rather than written blank.
Your comments, layout, and any other tables pass through byte-for-byte. The file is written user-only (0600), since it now holds a bearer token, and the original config.toml is snapshotted under ~/.valar/codex/ before the first change so off restores it exactly.
The client id defaults to your OS username, so the header reads X-Valar-Client-Id: jdoe. Use --user-id RANDOM for an opaque vc_… id instead. See per-engineer attribution.

Route a single session

To try Valar without changing anything in your Codex setup, or to run one routed session beside it, open a single Valar-routed session instead of enabling globally:
This starts one codex pinned to its own data dir (~/.valar/codex/session-home), routed through Valar. Your real ~/.codex config, and every other Codex session, stay untouched, and valar codex status stays off. Session history persists in that data dir across single-session runs.

Turn off routing

This restores the pre-enable config.toml byte-for-byte. Restart Codex and start a new conversation.

Known limitations

Existing conversations require a fork between valar on and off

Moving a conversation across a valar codex on or off boundary is not supported. Start a new conversation, or /fork. Conversations opened before valar codex on stay with OpenAI. Run /fork in one and the fork carries the context through Valar. Running valar codex off under a conversation that is still open breaks that conversation. Routing reverts with the file, but the model stays the one you had selected, and OpenAI does not serve it:
Finish or close a routed conversation before you turn routing off. Resuming across a switch is the quieter trap. codex resume reads whatever config.toml says at that moment and drops both the provider and the model the session recorded. The only hint is about the model:
Nothing mentions the endpoint. Because off restores the file without the Valar block, a session recorded on Valar resumes straight against OpenAI on OpenAI’s default model. Forcing the provider back does not rescue it, since the block it needs is the thing off removed:

Voice is off while routing is on

Codex voice, realtime sessions and in-app dictation both, terminates at OpenAI. The audio leg runs against OpenAI’s Realtime API under your ChatGPT sign-in, and model_provider does not redirect it. Valar routing authenticates with your coding key instead, so the voice path is unavailable and Codex stays text-only. Turn routing off, or keep an unrouted Codex beside it, if you need voice.

Next steps

Model routing

How cohorts and the split decide which model serves each request.

Models

The open-weight targets and the frontier Claude tiers.