mrkeyoor.com_
Fri 16 Oct 18:52 UTC
Tech6 min read

Codex's Shared Daemon Keeps Its Startup Environment Across Sessions

Codex terminals can share a backend with an earlier session's environment. Release code confirms the behavior and provides controls for daemon startup and updates.

Changing a proxy variable before opening a second Codex terminal may leave the agent using the first terminal's proxy. OpenAI's daemon documentation says shared clients inherit the server's startup environment. Clearing variables in a later terminal doesn't clear that copy. A fresh window can connect to an old process with old settings.

The behavior is drawing renewed attention through issue #48195, filed on September 25 by Yihua-Liu-1997 after installing Codex 0.157.0 through npm on Linux under WSL2. The report asks OpenAI to make automatic daemon startup opt-in. Its central complaint is that opening an interactive coding tool now also starts infrastructure whose lifetime extends beyond the window.

OpenAI's 0.157.0 release notes confirm that automatic background-server startup became enabled for eligible interactive sessions. The release shipped on September 25. The distinction matters for developers who use terminal wrappers to select network routes or load project credentials: launching the CLI and launching its backend are now separate events.

OpenAI's app-server protocol separates a client connection from a conversation. A client initializes its connection, then starts or resumes a thread and sends turns to that thread. That design lets interfaces talk to the same execution service. It also means a new connection isn't equivalent to a new operating-system process, which is where the environment in this dispute lives.

A new terminal doesn't reset the backend

On October 12, commenter alexklibisz added a related observation to the issue: after starting Codex in one directory with environment variables supplied through direnv, a later session in another directory used the earlier values. The commenter named GH_TOKEN as an example of a variable reused across projects. This is a user report, rather than a reproduction performed for this article.

The repository's daemon README independently documents the limitation: shared clients don't get separate inherited environments. A developer can change what the next shell sees while leaving the server's settings untouched. Switching project credentials therefore requires attention to when the backend started.

Codex's daemon launch code constructs a child process, disconnects its standard input and output, and calls setsid() on Unix to create a separate session. This gives the backend a process lifetime separate from the interactive terminal. Closing the interface doesn't, by itself, establish that the backend has stopped.

The launcher uses Tokio's process builder. Its documented default is to inherit the parent's environment, unless the caller changes it. Environment inheritance is ordinary process behavior. The surprising part for this workflow is reuse: a later client can attach to a process created before that client's shell settings existed.

For a local check, a harmless environment label can stand in for a credential. Compare a session launched before changing that label with one launched afterward, and record which backend serves each. Tokio's process documentation makes the relevant distinction clear: the environment is copied when a child process is created. Inspecting a later shell alone can't establish the earlier child's values.

These sources establish a shared-environment limitation. The credential-switching example in #48195 doesn't establish that a credential reached an unauthorized destination. A useful investigation would check which backend handled the command and which identity the command actually used, without printing the credential itself.

The installed CLI and running server can differ

Codex's managed-install code resolves a dedicated package beneath CODEX_HOME/packages/app-server-daemon, while retaining support for older standalone daemon installations. The backend has its own selected executable. Updating the foreground CLI through a package manager therefore doesn't, on its own, prove that an already running server has changed.

The daemon's lifecycle interface reports the local CLI and running app-server versions when applicable. For diagnosis after an upgrade, inspect both:

codex app-server daemon version

The updater is also conditional. The managed-install checks require a stable release selected for the latest channel, with a matching update-selection marker. A pinned release and an eligible automatically updated release have different behavior. The installed CLI's update policy alone won't tell you which case you're in.

For package managers, this has already produced concrete failures. In issue #48050, galiandan reported that the Arch Linux package stopped opening a usable session after the move from 0.156.1 to 0.157.0. The report describes a complete official package starting the daemon successfully, while the same executable copied out of that package failed. Running with --no-daemon restored the interactive prompt. Those are the reporter's tests, and the package layout was part of the failure.

Automatic updates have controls

An older August 26 report describes automatic updates interrupting work on a managed installation moving from 0.149.0 to 0.150.0. Its author ran 13 long-lived threads, with build and test turns lasting between three and 30 minutes. The report also said automatic updates couldn't be disabled. Later releases have added settings the report said were missing.

The 0.162.1 settings implementation has an autoUpdateEnabled preference, a configurable update interval, and a shutdown-grace setting. Automatic updates default to enabled, the interval defaults to 60 minutes, and shutdown grace defaults to 60 seconds. The allowed grace period tops out at 300 seconds. Operators have controls, although the maximum grace remains shorter than some workloads in the older report.

The preference belongs to the daemon settings file, under CODEX_HOME/app-server-daemon/settings.json. The settings parser reads autoUpdateEnabled inside an updater object, rather than as a top-level CLI setting. Existing values should be preserved when changing it. The same parser rejects a zero update interval, so turning updates off and choosing how often to check are separate controls.

The updater loop waits five minutes before its initial check and reads the stored update preference. It exits the scheduled path when automatic updates are disabled. This is a separate mechanism from checking for a newer CLI when the user opens it, so an operator needs to identify which updater a setting governs.

Shutdown still has a deadline. The PID backend escalates to forced termination after the configured grace expires, using SIGKILL for the Unix app-server process. A graceful request gives work time to finish, but it doesn't promise to wait indefinitely. Scheduling a backend restart outside a lengthy build remains relevant even when automatic updating is turned off.

Opting out changes future launches

For an invocation that should avoid implicit daemon use, the interactive startup code recognizes --no-daemon as an exclusion:

codex --no-daemon

The CLI also has a persistent feature-setting command. Its command dispatcher sends features disable to the configuration-writing path:

codex features disable daemon_auto_start

Disabling startup and stopping a process are different operations. The daemon shutdown implementation handles an existing process through its own stop path. Changing a future-launch preference shouldn't be treated as evidence that a server already serving other clients has exited. Check ongoing work before stopping a shared backend.

Documentation could make those choices easier to discover. The official configuration reference, checked for this article, lists check_for_update_on_startup but contains no daemon_auto_start entry. Meanwhile, the 0.162.1 feature registry classifies daemon auto-start as stable and enables it by default. Readers following the configuration reference alone can miss the setting that determines the backend's lifetime.

OpenAI has addressed some surrounding startup problems. The 0.162.1 release notes, published October 9, say compatibility checks now apply only to explicit command-line feature overrides, fixing failures caused by differences between server settings and CLI defaults. That fix has a defined scope. It doesn't announce a change to environment inheritance.

Watch for per-client environment handling or a notice explaining the shared environment when a terminal attaches. The daemon documentation still specifies shared startup variables. Until that changes, verify which server a new terminal joins before relying on a different project's credentials.

We reviewed this

  1. codex — our honest review

Sources

  1. Codex app-server daemon documentation, 0.162.1
  2. Issue #48195: Make daemon_auto_start opt-in
  3. Codex 0.157.0 release notes
  4. OpenAI Codex App Server documentation
  5. Codex 0.162.1 daemon process launch implementation
  6. Tokio process Command documentation
  7. Codex 0.162.1 managed daemon installation and update eligibility
  8. Issue #48050: Arch Linux package startup failure in Codex 0.157.0