Repository navigation
ocx stop/restore leave unmarked openai_base_url + proxy models_cache behind when Codex app rewrote config after injection #1798
Description
Client or integration
Codex App (and Codex CLI)
Version
2.21.0 (npm, @bitkyc08/opencodex)
Operating system
macOS 15.7.9 (build 24G830), Apple Silicon (arm64); Codex desktop app 151.0.7922.137
Area
Service lifecycle (ocx stop / ocx restore), Catalog / models
Summary
ocx stop (and ocx restore) leave the injected routing in place when the Codex app rewrote ~/.codex/config.toml after injection: the root key openai_base_url = "http://127.0.0.1:10100/v1" and [features] fast_mode = true stay in the config, and the proxy-routed models_cache.json is not restored. Result: plain Codex keeps sending every request to a dead 127.0.0.1:10100 and all messages fail with connection refused, while the model picker still lists proxy-routed models (e.g. opencode-go/deepseek-v4-flash, qwen-cloud/...) and gpt-5.3-codex is replaced by gpt-5.3-codex-spark.
Expected: ocx stop / ocx restore remove all injected routing (including an unmarked root openai_base_url) and restore the native models_cache.json from the catalog backup, so plain Codex works with no manual cleanup.
Reproduction
Environment: macOS (darwin arm64), opencodex 2.21.0 (npm), Codex desktop app 151.0.7922.137. Loopback routing (Design B: built-in openai_base_url override).
ocx start→~/.codex/config.tomlgetsopenai_base_url = "http://127.0.0.1:10100/v1"(root) and[features] fast_mode = true.~/.codex/opencodex-journal.jsonrecordsoriginalConfig+injectedConfigHash.- Open the Codex desktop app and change the model (or any setting). The app rewrites
~/.codex/config.toml, sosha256(config.toml)no longer equalsinjectedConfigHashand themodelvalue differs from the injected snapshot. - Run
ocx stop. The service/proxy stop cleanly, but the config and cache are left injected:restoreJournalState()skips the journal restore because the config changed since injection (configUnchangedis false).- The fallback
removeCodexConfig()reports "opencodex not present in Codex config." and removes nothing, becausehasInjectedOpenaiBaseUrl()(injected-marker.ts) only detectsopenai_base_urlwhen the line directly above it contains the# Auto-injected by opencodexmarker — in this state the key is unmarked.
ocx restorebehaves identically: prints✅ opencodex not present in Codex config./Codex integration is OFF..., but neither removes the routing line nor restoresmodels_cache.json.- Result:
curl http://127.0.0.1:10100/v1/models→ connection refused; every Codex message fails.
Logs or error output
$ ocx restore
✅ opencodex not present in Codex config.
Codex integration is OFF and plain `codex` now runs natively. Switch back with: ocx restore back
$ curl -s -m 3 -o /dev/null -w "HTTP %{http_code}\n" http://127.0.0.1:10100/v1/models
HTTP 000
# models_cache.json after restore (still proxy-written; metadata untouched):
client_version: 0.0.0 fetched_at: 2000-01-01T00:00:00Z
models: gpt-5.6-sol, gpt-5.6-terra, gpt-5.6-luna, gpt-5.5, gpt-5.4, gpt-5.4-mini,
gpt-5.3-codex-spark, alibaba-token-plan-intl/deepseek-v4-flash-0731,
alibaba-token-plan-intl/qwen3.8-max, nous-portal/qwen-qwen3.8-27b,
opencode-free/deepseek-v4-flash-free, opencode-go/deepseek-v4-flash,
opencode-go/glm-5.3, opencode-go/grok-4.6, qwen-cloud/deepseek-v4-flash-0731,
qwen-cloud/deepseek-v4-pro-0813Observations / possible causes
- The journal restore only fires when the config is byte-identical to the injected snapshot; a normal app rewrite defeats it. Consider stripping known injected root keys (
openai_base_url,model_catalog_json, andfast_modeunder[features]) even without the marker comment, or always writing the marker line on inject. - The catalog restore (
restoreCodexCatalogArtifact→restoreCodexCatalogWithPermit→readCatalogBackup) was a no-op here: the hash-named backup formodels_cache.json(~/.opencodex/catalog-backup-<sha256(path)>.json) does not exist, and the legacy~/.opencodex/catalog-backup.jsonwas not applied. Observed behavior:models_cache.jsonuntouched afterocx restore. I could not determine from outside whether the catalog step resolved a different path or was skipped;models_cache.jsonwas restored manually from the legacy backup. - Related:
ocx stopleaves the Codex CLI autostart shim installed; the nextcodexCLI invocation runsocx ensure, which restarts the proxy and re-injects. If that is intended, a warning would help, sinceocx stop's contract is "plain codex works again".
Workaround applied
Manually removed openai_base_url and [features] fast_mode from ~/.codex/config.toml, restored ~/.codex/models_cache.json from ~/.opencodex/catalog-backup.json, ran ocx codex-shim uninstall, and restarted the Codex app. Verified working afterward.
Checks
- I searched existing issues and documentation.
- I removed secrets, tokens, account details, request credentials, and personal data.
Activity
coderabbitai commentedon Aug 15, 2026
🔗 Related PRs
#333 - fix(codex): preserve external model providers [merged]
#576 - fix(codex): warn about stale Codex app-servers after a catalog write [merged]
#832 - fix(codex): preserve auto-compaction limit on inject [merged]
#1106 - feat(toggles): Codex restore truth, Claude Desktop switch, composed acceptance (WP13 resume) [merged]
#1461 - fix(codex): preflight sync injection before catalog writes [merged]
📝 Issue Planner
Check the box below or use the
@coderabbitai plancommand to generate an implementation plan and prompts that you can use with your favorite coding assistant.🧪 Issue enrichment is currently in open beta.
To disable automatic issue enrichment, add the following to your
.coderabbit.yaml:💬 Have feedback or questions? Drop into our discord!
github-actions commentedon Aug 15, 2026
Issue reopened
The report now contains the information required by the automated check. Thanks for updating it.
fix(codex): restore the catalog we actually wrote, not the one the co…
lidge-jun commentedon Aug 16, 2026
fix(codex): remove injected routing after the Codex app rewrites conf…
docs(devlog): record the Wave 3/4 second pass, audit corrections and …
fix(codex): decode TOML string escapes when reading injected routing …
fix(codex): decode TOML string escapes when reading injected routing …
fix(codex): remove injected routing after the Codex app rewrites conf…
fix(codex): restore the catalog we actually wrote, not the one the co…
docs(devlog): record the Wave 3/4 second pass, audit corrections and …
fix(codex): decode TOML string escapes when reading injected routing …
fix(codex): journal the web-search switch's ownership both ways
fix(codex): journal the web-search switch's ownership both ways
fix(codex): journal the web-search switch's ownership both ways
fix(codex): journal the web-search switch's ownership both ways
fix(desktop,gui): bundle L5 — macOS reopen, hidden-window polling, He…