Browser plugin bootstrap fails in Codex App: browser-client is not trusted
Open 💬 15 comments Opened May 30, 2026 by workpodsjun
💡 Likely answer: A maintainer (github-actions[bot], contributor)
responded on this thread — see the highlighted reply below.
Summary
Browser plugin / in-app browser automation fails during bootstrap in the Codex desktop app.
Environment
- Codex App version: 26.527.31326
- Thread id: 019e7814-b976-73a0-aaa2-36cc02b620be
- This thread is being used from the Codex desktop app, not only from CLI/cmux.
Error
privileged native pipe bridge is not available; browser-client is not trusted
Minimal checks
- The in-app browser itself is visible in the Codex App UI.
- Browser skill bootstrap uses an absolute path import for
browser-client.mjs. - No localhost navigation, URL transition, tab creation, or real UI inspection was attempted.
nodeReplexists.nodeRepl.nativePipeis false / missing.requestMetakeys are onlyprogressToken,threadId, andx-codex-turn-metadata.- Browser backend metadata is not visible in request metadata.
- Computer Use has worked separately in a Codex App session with
list_apps.
Current diagnosis
The trusted native bridge / browser backend metadata for the Browser plugin appears not to be injected into this thread's Node REPL runtime, even though the thread is being used from the Codex desktop app and the in-app browser is visible.
15 Comments
Potential duplicates detected. Please review them and close your issue if it is a duplicate.
Powered by Codex Action
Additional recovery attempt:
codex plugin remove browser@openai-bundled.codex plugin add browser@openai-bundled.browser@openai-bundledis installed and enabled again.nodeRepl.nativePipeis still false / missing.progressToken,threadId, andx-codex-turn-metadata.js_resetbefore running bootstrap again. Same result.Current interpretation: plugin reinstall succeeds, but the existing thread's Node REPL runtime still does not receive the Browser plugin trusted native bridge / backend metadata.
Follow-up after reviewing the duplicate candidates suggested by the bot.
I checked the suggested issues:
browser-client is not trusted/ native pipe bridge unavailable error, but reported on Windows / Chrome plugin.What is similar:
What is different in this report:
iab), not only the external Chrome plugin.browser-client.mjshashes match the trusted hash configured locally.nodeRepl.nativePipe.@Browseralso failed at bootstrap before any tab creation, URL navigation, localhost access, or UI inspection.Current narrowed failure point:
nodeRepl.nativePipeis missing.So this may be related to the duplicate candidates, especially #23831, but I do not think it is an exact duplicate unless the same fix is expected to cover macOS Browser plugin / in-app browser automation as well.
Additional Windows recovery datapoint from another affected machine. This is not an official fix, but it may help narrow down the failure mode.
Environment:
26.527.3686.0codex-cli 0.135.0-alpha.1browser,chrome, andcomputer-useplugins at26.527.31326Symptoms observed:
browser-client is not trustedprivileged native pipe bridge is not availablecodex plugin list --marketplace openai-bundledcould show plugins as enabled, while runtime bootstrap still failednot installedbecause local plugin cache directories/manifests were missingWhat recovered this machine:
browser,chrome, andcomputer-useplugin cache directories/manifests from the bundled marketplace source. Avoided overwriting already-loaded native files while Codex was running.node_replMCP server:The important part was not hard-coding someone else's values. The SHA-256 list was computed from the installed plugin client files on that machine, and the Computer Use pipe was discovered from the current live
\\.\pipe\codex-computer-use-*pipe.SKY_CUA_NATIVE_PIPE_DIRECTORYto the current live pipeconfig.tomlVerification after repair:
config.tomlparsed successfullycodex mcp get node_replshowed the expected env entriescodex plugin list --marketplace openai-bundledshowed Browser, Chrome, and Computer Use asinstalled, enabledagent.browsers.list()sky.list_apps()andsky.list_windows()My interpretation:
config.tomlrepair scripts.Sanitized write-up of the local repair is here:
https://gist.github.com/dingjianhui123-create/9c3c2b83c2a45c2ef32f9991e712edba
Same here
The first thing I would separate here is trust/bootstrap failure from normal browser availability.
A useful repro matrix is just four checks in order: extension installed, extension enabled, native host present, then a lightweight tab-list/bootstrap call. If the first three are true and the bootstrap still says the browser client is not trusted, that points to the trust handshake itself rather than Chrome not being there.
The most helpful receipt is usually the first failing primitive plus the exact profile/browser context it ran under. Once you have that, this class of bug gets much easier to pin down than a generic "browser failed" report.
Follow-up from the same macOS/Codex App environment on 2026-06-05.
The issue is still reproducible in the current CLI-backed session.
Minimal smoke results:
list_appscall timed out after 120 seconds.Current interpretation:
No secrets or local file contents are included here.
Same root cause as #21719 — full evidence posted there. tl;dr: the trust gate isn't the failure. On app build
26.611.62324(engine0.140.0-alpha.19, macOS arm64),browser-client.mjshashes to exactlyNODE_REPL_TRUSTED_BROWSER_CLIENT_SHA256Sand sits underNODE_REPL_TRUSTED_CODE_PATHS, yethasNativePipe: false. The reasonnativePipeis missing: the desktop app-server and the Chromeextension-hosteach open their own/tmp/codex-browser-use/<uuid>.sockand never connect, so no privileged pipe is ever handed tonode_repl. A full clean-slate restart (wipingchrome-native-hosts*.json+ all sockets) does not fix it — the mismatch reproduces immediately. Detailedlsof/registry evidence in #21719.I am seeing the same issue on macOS arm64 after today's migration/update to the new ChatGPT desktop app.
Environment:
Error:
privileged native pipe bridge is not available; browser-client is not trustedWhat I verified:
latestsymlink are correctextension-host-config.jsonwas initially missing and was regenerated using the bundled installerbrowser-client is not trustedbefore any tab or page data can be readAdditional context:
Earlier today, the previous Codex desktop app crashed during an update and became
ChatGPT Classic.app. I then installed the newChatGPT.app, which contains ChatGPT, Work, and Codex. The two apps have separate bundle identifiers and separate application-support directories, and ChatGPT Classic is not using the active~/.codexconfiguration.There appears to be a mismatch between the UI state and the runtime trust state:
The in-app feedback submission also failed with “Unable to submit your feedback. Please try again later.”
I have redacted diagnostic reports available if maintainers need them.
I can reproduce the same failure on ChatGPT desktop 26.707.51957 (5175), macOS 26.5.1 arm64:
privileged native pipe bridge is not available; browser-client is not trustedAs in the original report,
nodeReplexists butnodeRepl.nativePipeis missing, and the failure occurs before any browser connection or tab operation.I found two additional lifecycle clues:
browser@openai-bundled. A few seconds later it writes a seven-plugin marketplace including Browser, reinstalls it, and shortly afterward installs it again with reasonoutdated.The app, Browser plugin, and Chrome plugin versions all match 26.707.51957, and the installed
browser-client.mjshashes are identical, so this does not appear to be corrupted plugin files.This suggests that stale per-task kernels and/or the bundled-plugin startup reconciliation race can leave an existing task without Browser trust registration. Full app restart, reinstall, or bundled-plugin reload should probably invalidate affected kernels and create a fresh trusted runtime.
Feedback ID:
019f5909-bc40-7fc2-9447-1690c7511f04I cloned and traced the current public
openai/codexsource, compared it withrust-v0.144.1, inspected the packaged ChatGPT Desktop runtime, and correlated that with the local startup logs/process lifecycle.Source boundary
The exact failing implementation is not in the public repository. Current
main(2f7d89b141) and the release-era tags have no implementation ofnodeRepl.nativePipe,browser-client.mjs, or this trust error. Those pieces are supplied by the packaged Desktopnode_repl/Browser bridge.The packaged Desktop code constructs the
node_replMCP configuration from the available Browser backends and suppliesNODE_REPL_TRUSTED_BROWSER_CLIENT_SHA256S. In this reproduction the packaged Browser/Chrome client hashes match, so the messagebrowser-client is not trustedis misleading: the immediate condition is that the privileged bridge was not injected into the active kernel.The public source does explain why reinstalling the UI may not repair that runtime state:
app-server/src/lib.rs#L676-L679,#L954-L974);OnceCell, with shutdown but no reset/rebind operation (core/src/tools/code_mode/mod.rs#L66-L80,#L109-L123,#L157-L177);app-server/src/effective_plugin_change.rs#L22-L45).The public code-mode runtime is not the closed
node_replkernel itself, but it demonstrates the same persistent per-thread lifecycle boundary that Desktop needs to handle.Proposed fix
I suggest treating every privileged Browser kernel as belonging to a versioned capability generation:
On Desktop initialize/reconnect, app update, bundled-plugin install/update/remove/reload, or trust-manifest change:
nodeRepl.nativePipebefore evaluating plugin code.nativePipe:v1capability/health handshake before advertising Browser availability.native bridge missingerror instead ofbrowser-client is not trusted.The bundled-plugin reconciliation should also be transactional. The observed startup sequence first published a six-plugin set without Browser and uninstalled
browser@openai-bundled, then a few seconds later published seven plugins and reinstalled it. A provisional feature-gated plugin list should never drive destructive uninstall. Wait for authoritative feature availability, compute one final set, atomically publish it, then refresh/rebind affected runtimes.Finally, task kernels should be owned by the app/app-server lifecycle and killed/reaped on full quit, update handoff, thread unload, or generation mismatch. A detached kernel from the previous installation was still alive in this reproduction, which explains why reinstalling the app alone had no effect.
Regression tests
nodeRepl.nativePipe.createConnectionexists.I found no public PR or commit on current
mainthat addressesnativePipe, this exact error, or #25247, so the direct patch likely belongs to the closed Desktop/node_replowner rather thancodex-rs.The additional reproductions are useful because they point to a packaging/trust mismatch, not a generic browser startup failure.
It may help to make startup emit a small machine-readable boundary check before launching:
package_mismatch,bridge_unavailable, orpolicy_deniedRight now several distinct failures collapse into the same user-facing retry path. Preserving that boundary result would prevent repeated bootstrap attempts and give maintainers comparable evidence across app builds.
Reproduced on a newer release after a full Mac restart:
26.715.21425(build5488)26.5.2019f7130-bf27-7913-8146-1983c831ca0aCurrent diagnostics:
browser@openai-bundledandchrome@openai-bundledare installed and enabledDespite this, Browser/Chrome bootstrap still fails immediately with:
The failure occurs before opening or inspecting any tab. Restarting the Mac and ChatGPT did not restore the trusted native bridge.
This confirms the issue persists in desktop build 26.715.21425 and is not limited to the older builds reported above. The in-app feedback submission above contains the corresponding desktop diagnostic context.
Follow-up: I found a working macOS-only local workaround for this failure. I am sharing the architecture rather than the implementation so other affected users and maintainers have a concrete path forward.
Basic workaround
nodeRepl.nativePipe.createConnectioninterface using a normal Unix-domain socket connection adapter, together with the minimal configuration and task metadata expected by the bundled client.browser-client.mjsunchanged from the app bundle.agent.browsersAPI. Keep its security/elicitation policy active: deny external origins by default and exact-allow-list only the origin needed for the current task.Why this works
The failing task runtime has the official Browser client but never receives
nodeRepl.nativePipe. ChatGPT's own signed Node executable passes the app's native peer authorization and can reach the existing Browser rendezvous socket. The helper therefore supplies only the missing connection adapter in an authorized signed process while continuing to use OpenAI's bundled client, protocol, APIs, and origin policy.Validation
On ChatGPT Desktop
26.715.21425:A fresh task still reproduces
privileged native pipe bridge is not available; browser-client is not trustedthrough the normal built-in path, so this is a workaround, not a repair.Important limits
Related in-app feedback
019f71ba-c90e-73b0-b8c7-83caa1c7f5b9Additional macOS reproduction with read-only local diagnostics.
Environment
26.715.3192526.5.2(arm64)019f74c8-162e-7800-a94d-7554c9fb7a09a1344c11-7b80-498d-9a5d-f1bf91c96f93browser@openai-bundledversion26.715.31925Failure
The bundled Browser bootstrap fails immediately, before any tab inspection or navigation:
Direct runtime checks:
There is no
x-codex-browser-use-available-backendsmetadata on the actual Node REPL request.What is healthy
browser-client.mjsfiles are identical.461c4ba94b821ec805da79c8e8138fe510b1b3358609fc93da47387a2cf3fbf3NODE_REPL_TRUSTED_BROWSER_CLIENT_SHA256S.node_replMCP server process received the expected Browser-related environment keys, includingBROWSER_USE_AVAILABLE_BACKENDS,NODE_REPL_TRUSTED_BROWSER_CLIENT_SHA256S, andNODE_REPL_TRUSTED_CODE_PATHS.However,
lsofshowed only ChatGPT listening on the per-thread socket; the task'snode_replprocess never connected. The Desktop log likewise contains listener-start events but no peer connection/authorization event for this thread.Startup reconciliation race observed
On this launch, Desktop performed the following sequence:
The current task's Node REPL process was created several minutes after the final reconciliation, so this specific reproduction is not only an old pre-reconciliation kernel. The final failure point is the capability handoff: Desktop has a live per-thread socket and the trusted client configuration, but the active task kernel is not given
nodeRepl.nativePipeor the Browser backend request metadata.This appears to confirm both the bundled-plugin reconciliation race and a separate Desktop/app-server → per-thread Node REPL native-pipe injection/rebinding failure.