Skip to content

chore(release): merge upstream rust-v0.140.0#74

Open
richardgetz wants to merge 195 commits into
stablefrom
stable-refresh/rust-v0.140.0-from-stable
Open

chore(release): merge upstream rust-v0.140.0#74
richardgetz wants to merge 195 commits into
stablefrom
stable-refresh/rust-v0.140.0-from-stable

Conversation

@richardgetz

Copy link
Copy Markdown
Owner

Summary

  • Merge upstream rust-v0.140.0 into the fork stable branch.
  • Preserve fork-only account alias, scratchpad/continuous, memory, MCP recovery/visibility, app-server, TUI, conventional commit, git intent note, enablement, and CI/release behavior.
  • Regenerate app-server protocol schemas, config schema, Cargo/Bazel lock artifacts, and accept intentional TUI snapshots for the v0.140.0 UI surface.

Fork-contract conflict notes

  • Kept fork action-policy/scratchpad guardrails and attached an intent note for this release merge.
  • Preserved account alias/keyring behavior while adapting upstream Bedrock/API auth additions.
  • Preserved MCP visibility/recovery behavior while adapting upstream catalog/plugin config changes.
  • Preserved app-server/TUI realtime routing and restored fork slash command visibility after upstream TUI restructuring.
  • Preserved executor-selected skill precedence over host skill name collisions and added regression coverage.
  • Renumbered incoming upstream state migrations to avoid colliding with existing fork migrations.

Local verification

  • just write-app-server-schema
  • just write-config-schema
  • just bazel-lock-update
  • just bazel-lock-check
  • just fmt
  • just test -p codex-app-server-protocol passed 243/243
  • just test -p codex-core-skills passed 102/102
  • just test -p codex-skills-extension passed 8/8
  • just test -p codex-mcp passed 83/83
  • just test -p codex-login passed 140/140
  • just test -p codex-state passed 148/148
  • just test -p codex-tools passed 86/86
  • just test -p codex-tui passed 2930/2930, with 1 leaky and 4 skipped
  • Focused codex-core merge-drift tests passed for state migration numbering, thread-spawn lineage metadata, token-count payloads, token-budget context windows, and skill injection.
  • just fix -p codex-tools
  • just fix -p codex-core -p codex-app-server -p codex-tui -p codex-mcp -p codex-login -p codex-state -p codex-core-skills -p codex-skills-extension

Local environment caveats

  • Full just test -p codex-core still has local harness failures dominated by nested Seatbelt (sandbox-exec: sandbox_apply: Operation not permitted), missing local test_stdio_server, and sandbox/network hook expectations. Focused merge-drift failures were resolved.
  • Full just test -p codex-app-server improved to 875 passed, 3 failed, 1 timed out, 3 skipped. Remaining failures are local nested sandbox/network/image file access issues.
  • Per repo guidance, tests were not rerun after the final just fix/just fmt pass.

tamird and others added 30 commits June 8, 2026 21:32
Codex forces `core.fsmonitor=false` on internal Git commands so a
repository cannot select an executable fsmonitor helper. This also
disables Git's built-in daemon for `status`, `diff`, and `ls-files`,
turning those worktree reads into full scans in large repositories.

Read the raw effective `core.fsmonitor` value and preserve it only when
Git interprets it as true and advertises built-in daemon support through
`git version --build-options`. Query uncommon boolean spellings back
through Git using the exact effective value. Unset, false, helper paths,
malformed values, probe failures, and unsupported Git builds continue to
force `core.fsmonitor=false`.

Centralize this policy in `git-utils` while keeping process execution in
the existing local and workspace-command adapters. Probe once per
worktree workflow and reuse the result for its Git commands, including
the TUI `/diff` path. Metadata-only commands and repository discovery
remain disabled without probing. Each probe and requested Git process
keeps its own existing timeout, and the decision is not cached because
layered and conditional Git configuration can change while Codex runs.

---------

Co-authored-by: Chris Bookholt <bookholt@openai.com>
)

## Summary
- request `includeAppsNeedingAuth=true` when installing remote plugins
- return backend-provided `app_ids_needing_auth` from the remote install
client
- use those app IDs to populate `appsNeedingAuth` without refetching
accessible apps, with fallback for older responses

## Testing
- `just fmt`
- `just test -p codex-app-server`
- `just test -p codex-core-plugins`
- real app-server install/uninstall check with Notion remote plugin
- subagent review found no blocking issues
## Summary

- return installed `workspace-directory` remote plugins by default in
`plugin/installed`
- keep shared-with-me installed plugins gated behind `plugin_sharing`
- filter remote installed plugin marketplaces by canonical marketplace
name instead of coarse workspace scope

## Validation

- `just fmt`
- `just test -p codex-core-plugins`
- `just test -p codex-app-server`
- `just fix -p codex-core-plugins`
- `just fix -p codex-app-server`
- `$xin-build` targeted verification:
- `just test -p codex-core-plugins
build_remote_installed_plugin_marketplaces_from_cache_filters_by_marketplace_name`
- `just test -p codex-app-server
plugin_installed_includes_workspace_directory_without_plugin_sharing`
- `just test -p codex-app-server
plugin_installed_includes_remote_shared_with_me_plugins`
- `just test -p codex-app-server
plugin_list_omits_shared_with_me_kind_when_plugin_sharing_disabled`
## Why

Multi-agent v2 identifies agents by canonical paths, but its tool
handlers still emitted the larger legacy collaboration begin/end events
built around nickname and role metadata. App-server, rollout-trace,
analytics, and TUI consumers therefore lacked one compact path-based
completion signal that behaved consistently across live events and
replay.

The TUI also needs a bounded `/agent` status surface for v2 agents. It
should use recent local activity for previews, refresh liveness without
loading full histories, and keep the legacy picker available when no
path-backed v2 agent is known.

## What changed

- Replace the v2 `spawn_agent`, `send_message`, `followup_task`, and
`interrupt_agent` legacy lifecycle emissions with a success-only
`SubAgentActivity` event. The event records the tool call ID, occurrence
time, affected thread, canonical agent path, and `started`,
`interacted`, or `interrupted` kind.
- Expose the activity as a completion-only app-server v2
`subAgentActivity` thread item in live notifications and reconstructed
history, regenerate the protocol schemas, and count it in sub-agent tool
analytics.
- Track canonical paths from live activity and loaded-thread metadata in
the TUI, and render the activity in live and replayed transcripts.
- Make `/agent` list running path-backed agents with summaries from
bounded local event buffers. Each summary is capped at 240 graphemes,
the scan is capped at six recent items, only the last three wrapped
lines are shown, and command output is omitted. Liveness falls back to
metadata-only `thread/read` when local turn state is unavailable.
- Persist the activity as a terminal rollout-trace runtime payload and
reduce it to the corresponding spawn, send, follow-up, or close
interaction edge. `interrupt_agent` is classified as a close-edge
operation.
- Preserve the legacy picker when no path-backed v2 agent is known.

## Compatibility

App-server v2 clients that consumed `collabAgentToolCall` begin/end
pairs for these tools must handle the new completion-only
`subAgentActivity` item. Legacy v1 collaboration behavior is unchanged.

## Screenshot

<img width="684" height="288" alt="Screenshot 2026-06-08 at 15 40 47"
src="https://github.com/user-attachments/assets/194b3cd0-619d-45fb-b587-cf3e2b1b8a1d"
/>

## Testing

- `just test -p codex-app-server-protocol`
- `just test -p codex-rollout-trace`
- Added focused coverage for activity analytics, terminal trace
serialization, spawn-edge reduction, `interrupt_agent` classification,
TUI status rendering without aggregated command output, and clearing
stale running state after a completed turn.
…penai#27166)

## Why

PR openai#27007 moved MultiAgentV2 interruption reporting from the legacy
collaboration close event to `SubAgentActivity::Interrupted`.
App-server's missing-thread cleanup still ran only for the legacy event,
so an interrupted child that had already been unloaded could remain
marked as loaded and running in `ThreadWatchManager`. That leaves thread
status and running-turn accounting stale, including the count used
during graceful shutdown.

## What changed

- Handle `SubAgentActivity::Interrupted` separately in app-server event
processing.
- Remove the child's thread watch when `ThreadManager` no longer has
that thread.
- Continue forwarding the same completed sub-agent activity notification
to clients.

## Testing

- Added a regression test that starts with a running watch for an
unloaded child, applies the interrupted activity event, and verifies the
watch is removed, the running count returns to zero, and the client
notification is still emitted.
## Why

The PR babysitter could surface inline comments from a GitHub review
that was still in the `PENDING` state. That allowed Codex to start
acting on feedback before the reviewer submitted it.

## What changed

- Correlate inline comments with their parent review and ignore pending
reviews and their comments.
- Remove pending review IDs from saved watcher state so the feedback
surfaces normally after publication.
- Update the skill instructions and add regression coverage for the
draft-to-published transition.

## Validation

- `python3 -m pytest
.codex/skills/babysit-pr/scripts/test_gh_pr_watch.py`
- Skill package validation with `quick_validate.py`
- Live verification on openai#26835: the draft comment stayed hidden and
surfaced after the review was submitted.
## Summary

- avoid acquiring SQLite's writer slot when the singleton backfill row
already exists
- preserve race-safe repair when the row is missing
- add regressions for writer contention and missing-row repair

## Why

State runtime initialization and backfill-state reads previously
executed
`INSERT ... ON CONFLICT DO NOTHING` even in the steady state. SQLite
still
enters the writer path for that statement, so TUI and app-server startup
could
wait behind another writer for up to the configured five-second busy
timeout.

## Validation

- `just test -p codex-state` (134 tests passed)
- `just fix -p codex-state`
- `just fmt`
## Summary

- reuse the history-bearing `StoredThread` loaded while probing for a
running thread
- avoid rereading and reparsing the rollout when that probe finds no
active process
- reload after shutting down a loaded thread because shutdown may flush
newer rollout items
- add a regression test that verifies cold resume performs one
history-bearing store read

## Problem

`thread/resume` first reads the persisted thread with history while
checking whether the thread is
already running. When no running process exists, cold resume currently
falls through to
`resume_thread_from_rollout`, which reads and parses the same history
again.

That duplicate work grows with rollout size and remains on the
synchronous resume path even when
the caller requests `excludeTurns`.

## Background

The duplicate read was introduced by openai#24528, which fixed resume
overrides for idle cached
threads. To support resumes specified by rollout path,
`resume_running_thread` began loading the
stored thread with history so it could resolve the canonical thread ID
and determine whether a
cached `CodexThread` was already loaded.

That history is needed when the loaded-thread path handles the request.
On a cold miss, however,
the function's boolean result could only report that no loaded thread
handled the request. It
discarded the history-bearing `StoredThread`, and the normal cold-resume
path immediately loaded
and parsed the same rollout again.

This change preserves the idle cached-thread behavior from openai#24528 while
allowing the cold-resume
path to reuse the probe result.

## Performance

I benchmarked real retained rollouts using isolated `CODEX_HOME`
directories, explicit rollout
paths, debug builds of the commit and its exact parent, and alternating
parent/patch order. The
table below uses `thread/resume` with `excludeTurns: true`; response
payload sizes were identical.

| Rollout size | Records | Parent median | Patch median | Median paired
saving |
| ---: | ---: | ---: | ---: | ---: |
| 6 MB | 3,574 | 541 ms | 441 ms | 132 ms |
| 30 MB | 15,220 | 1.505 s | 1.041 s | 701 ms |
| 60 MB | 31,453 | 2.644 s | 1.742 s | 970 ms |
| 149 MB | 100,874 | 10.506 s | 7.156 s | 3.350 s |
| 559 MB | 259,734 | 27.759 s | 16.725 s | 9.836 s |

The absolute saving increases with thread size, as expected when
removing one complete JSONL
history read and parse. Total resume time is also content-dependent, so
the relationship is not
perfectly linear.

I also tested full-history resume with `excludeTurns: false`. The
response payload was
byte-identical between variants, and the same size-dependent improvement
remained visible:

| Rollout size | Parent median | Patch median | Median paired saving |
| ---: | ---: | ---: | ---: |
| 6 MB | 1.052 s | 904 ms | 270 ms |
| 30 MB | 2.667 s | 1.762 s | 924 ms |
| 60 MB | 8.464 s | 6.272 s | 3.680 s |
| 149 MB | 26.719 s | 12.118 s | 14.601 s |
| 559 MB | 40.359 s | 25.475 s | 16.590 s |

## Validation

- `just test -p codex-app-server
cold_thread_resume_reuses_non_local_history_probe`
- `just fix -p codex-app-server -p codex-thread-store`
- `just fmt`
…#22879)

This changes the `/review` escape path so `Esc` no longer behaves like
the normal queued-follow-up interrupt flow while a review is running.
Steering is not currently supported in `/review` mode, without this
change users are able to attempt a steer but it leads to a crash (see
openai#22815). If the user has already tried to send additional guidance
during `/review`, the TUI now keeps the review running and shows a
warning that steer messages are not supported in that mode, while still
pointing users to `Ctrl+C` if they actually want to cancel. It also adds
regression coverage for the review-specific warning behavior. When users
do cancel with Ctrl+C during /review, the TUI now tolerates the
active-turn race that can happen during review handoff, and any queued
steer messages are restored to the composer instead of being discarded.

- Special-case `Esc` during an active `/review` when follow-up steer
input is pending or has already been deferred.
- Show a clear warning instead of interrupting the running review.
- Make the Ctrl+C cancel path during /review resilient to active-turn
races, while preserving any queued steer text by restoring it to the
composer.
- Add review-mode test coverage for the warning path.

## Testing

1. Start a `/review` with a diff large enough that the review stays
active for more than a few seconds.

2. While the review is still running, type a follow-up / steer message,
submit it, and then press `Esc`.
   Before: `Esc` causes the TUI to close abruptly.  
After: the review keeps running and the transcript shows a warning that
steer messages are not supported during `/review`, with guidance to use
`Ctrl+C` if you want to cancel.

3. Press `Ctrl+C` if you actually want to stop the review.  
Before: (after restarting the test since Pt. 2 crashed) this is the
intentional cancellation path.
After: this remains the intentional cancellation path, and any queued
follow-up steer text is restored to the composer instead of being lost.
   
## Note:
`/review` mode explicitly does not support steering at this time (as
noted in `turn_processer.rs`, if we want to explore that in the future
this code will need to be modified). This change keeps unsupported steer
attempts from crashing the TUI and preserves queued follow-up text if
the user cancels with Ctrl+C.
…27173)

## Why

Multi-agent v2 sub-agents are owned and coordinated by their parent
agent. Allowing an app-server client to start or steer turns on a
spawned child bypasses the multi-agent messaging path and creates a
second, conflicting source of work for that sub-agent.

## What changed

- Reject direct `turn/start` and `turn/steer` requests targeting
multi-agent v2 thread-spawn sub-agents.
- Identify these targets using both the thread's resolved multi-agent
version and its `SubAgentSource::ThreadSpawn` session source, leaving
root threads, v1 agents, and other sub-agent types unchanged.
- Return a consistent invalid-request error before validating or
applying the submitted input.

## Testing

- Added an app-server integration test that spawns a real multi-agent v2
child and verifies that direct `turn/start` and `turn/steer` requests
are rejected.
## Why

CCA is moving toward a split runtime where the orchestrator may not have
a filesystem, while executors can expose preinstalled plugins and
skills. A thread therefore needs to select capabilities without asking
app-server or core to interpret executor-owned paths through the
orchestrator's filesystem.

The longer-term model is broader than executor skills:

- A plugin is a bundle of skills, MCP servers, connectors/apps, and
hooks.
- A plugin root can be local, executor-owned, or hosted by a backend.
- Components inside one plugin can use different access and execution
mechanisms. A skill may be read from a filesystem or through backend
tools; an HTTP MCP server can run without an executor; a stdio MCP
server or hook needs an execution environment.
- Core should carry generic extension initialization data. The extension
that owns a component should discover it, expose it to the model, and
invoke it through the appropriate runtime.

This PR establishes that architecture through one complete vertical:
selecting a root on an executor, discovering the skills beneath it,
exposing those skills to the model, and reading an explicitly invoked
`SKILL.md` through the same executor.

## Contract

`thread/start` gains an experimental `selectedCapabilityRoots` field:

```json
{
  "selectedCapabilityRoots": [
    {
      "id": "deploy-plugin@1",
      "location": {
        "type": "environment",
        "environmentId": "workspace",
        "path": "/opt/codex/plugins/deploy"
      }
    }
  ]
}
```

The root is intentionally not classified as a "plugin" or "skill" in the
API. It can point at a standalone skill, a directory containing several
skills, or a plugin containing skills and other components. This PR only
teaches the skills extension how to consume it; later extensions can
resolve MCP, connector, and hook components from the same selection.

The platform-supplied `id` is stable selection identity. The location
says which runtime owns the root and gives that runtime an opaque path.
App-server does not inspect or canonicalize the path.

## What changed

### Generic thread extension initialization

App-server converts selected roots into `ExtensionDataInit`. Core
carries that generic initialization value until the final thread ID is
known, then creates thread-scoped `ExtensionData` before lifecycle
contributors run.

This keeps `Session` and core independent of the capability-selection
contract. The initialization value is consumed during construction; it
is not retained as another long-lived `Session` field.

### Executor-backed skills

The skills extension now owns an `ExecutorSkillProvider` that:

- resolves the selected environment through `EnvironmentManager`
- discovers, canonicalizes, and reads skills through that environment's
`ExecutorFileSystem`
- contributes the bounded selected-skill catalog as stable developer
context
- reads an explicitly invoked skill body through the authority that
listed it
- warns when an environment or root is unavailable
- never falls back to the orchestrator filesystem for an executor-owned
root

Skill catalog and instruction fragments have hard byte bounds, which
also bound them below the 10K-token per-item context limit. If a
selected executor skill has the same name as a legacy local skill, the
executor selection owns that invocation and the local body is not
injected a second time.

Existing local and bundled skill loading remains in place. Omitting
`selectedCapabilityRoots` therefore preserves current local-only
behavior.

## Current semantics

- Only environment-owned locations are represented in this first
contract.
- Roots are resolved by the destination extension, not by app-server or
core.
- An unavailable executor or invalid root produces a warning and no
capabilities from that root; it does not trigger a local-filesystem
fallback.
- Selection applies to a newly started active thread.
- MCP servers, connectors, and hooks beneath a selected plugin root are
not activated yet.
- Selection is not yet persisted or inherited across resume, fork, or
subagent creation. Existing local capabilities continue to behave as
they do today in those flows.

## Planned vertical follow-ups

1. **Hosted HTTP MCP:** add an extension-backed HTTP MCP source that
works without an executor, then replace the special-purpose MCP plugins
loader with that implementation.
2. **Executor MCP:** register and execute stdio MCP servers through the
environment that owns the selected plugin root.
3. **Backend skills:** add a hosted skill source whose catalog and
bodies are accessed through extension tools rather than a filesystem.
4. **Connectors and hooks:** activate those components through their
owning extensions, using the same selected-root boundary and
component-specific runtime.
5. **Durable selection:** define the desired-selection lifecycle,
persist it, and make resume, fork, and subagent inheritance explicit
rather than accidental.
6. **Local convergence:** incrementally route existing local plugin,
skill, and MCP loading through the same extension model while preserving
current local behavior.

Each follow-up remains reviewable as an end-to-end capability. The
platform selects roots, generic thread extension data carries the
selection, and the owning extension resolves and operates its component.

## Verification

Coverage added for:

- app-server end-to-end discovery and explicit invocation of a skill
inside an executor-selected plugin root
- exclusive invocation when a selected executor skill collides with a
local skill name
- executor filesystem authority for discovery, canonicalization, and
reads
- thread extension initialization before lifecycle contributors run
- stable executor catalog context, explicit invocation, context
rebuilding, hidden skills, and preserved host/remote catalog behavior

Targeted protocol, core-skills, skills-extension, core lifecycle, and
app-server executor-skill tests were run during development.
## Why

`codex-extension-api` defines contracts shared by extension crates and
their hosts, but it had no direct test suite. Host and feature tests
cover downstream behavior, while regressions in the API crate's own
typed state, registry ordering, and capability adapters could go
unnoticed.

## What

- Add public-surface integration tests for `ExtensionData`, including
concurrent initialization and poison recovery.
- Cover contributor registration order, approval short-circuiting, event
sink retention, no-op response injection, and closure-based agent
spawning.
- Add the test-only dependencies used by the suite.

## Validation

- `just test -p codex-extension-api`
- `just argument-comment-lint -p codex-extension-api`
- `just bazel-lock-check`
## Why
- `ThreadSource` currently defines a closed set of core-owned values
- Product features also create threads for background or scheduled work
- Adding every product-specific value to the core enum would require
repeated `codex-rs` protocol changes
- Feature-backed values let product callers provide precise attribution
while preserving the existing core classifications

## What Changed
- Adds `ThreadSource::Feature(String)` for app-owned thread source
values
- Represents all app-server v2 thread sources as scalar strings, so a
feature source is supplied as `"automation"`
- Persists and emits the feature's plain string label, so `"automation"`
produces `thread_source="automation"` in analytics
- Keeps `user`, `subagent`, and `memory_consolidation` as explicit
core-owned values and regenerates the app-server schemas and TypeScript
bindings

## Verification
- `just write-app-server-schema`
- `cargo check --workspace`
- `just test -p codex-protocol
feature_thread_source_serializes_as_its_app_owned_label`
- `just test -p codex-app-server-protocol
thread_sources_round_trip_as_scalar_labels`
- `cargo test -p codex-analytics
thread_initialized_event_serializes_expected_shape`
- `just fmt`
## Why

`just test` currently uses the CI-oriented nextest profile, which
serializes app-server integration tests even on developer machines that
can run several safely. Bounded local parallelism substantially shortens
this common iteration loop without changing CI behavior.

Eight-worker experiments were faster, but keeping them reliable required
relaxing several test deadlines. Four workers for integration tests is a
solid tradeoff that speeds up local testing without needing to change
test logic.

## What changed

- Add a `local` nextest profile that inherits the existing defaults.
- Allow up to four app-server integration tests to run concurrently
under that profile.
- Make `just test` select the local profile on Unix and Windows.
- Keep the default CI profile serialized and leave all test deadlines
unchanged.

The tests use separate processes, randomized temporary `CODEX_HOME`
directories, and ephemeral ports. The remaining shared constraints are
system resources; each app-server also uses a multi-thread Tokio
runtime, and fuzzy-search tests can create additional worker threads, so
the local cap remains intentionally conservative.

## Performance and validation

All measurements below are warm, execution-only app-server runs with
nextest retries disabled.

On the current rebased branch, an AMD EPYC 7763 machine with 16 logical
CPUs and 62 GiB RAM completed three consecutive runs:

| Run | Nextest time | Wall time | Result |
| --- | ---: | ---: | --- |
| 1 | 142.941s | 145.17s | 836/836 passed |
| 2 | 143.402s | 145.59s | 836/836 passed |
| 3 | 142.870s | 145.08s | 836/836 passed |

The mean wall time was 145.28s. The slow-inventory, approval replay, and
zsh-fork tests all passed with their original deadlines.

Earlier measurements on the same Linux machine, before the suite grew,
showed the scaling that motivated the change:

| App-server concurrency | Nextest time | Result |
| --- | ---: | --- |
| 1 | 369.5s | 572/572 passed |
| 2 | 194.5s | 572/572 passed |
| 4 | 111.0s mean over 3 runs | 3/3 clean |

Four workers reduced that execution time by about 70%, a roughly 3.3x
speedup over serialization.
## Summary
- reuse the MITM HTTPS serving path for raw SOCKS5 TCP streams
- route limited-mode and hooked SOCKS5 TCP requests through MITM before
dialing upstream
- keep SOCKS5 UDP limited-mode behavior unchanged

## Validation
- `just fmt`
- `just test -p codex-network-proxy`
- `just fix -p codex-network-proxy`
- `git diff --check`
## Why

Users have indicated that they want an agent to be able to create a new
goal for itself after completing the previous goal. Currently, that's
not possible because agents cannot overwrite an existing goal even if
it's complete. This PR removes this limitation and allows `create_goal`
to overwrite an existing goal if it is in the `complete` state.

## What changed

`create_goal` now replaces the existing goal only when its status is
`complete`. The replacement is performed atomically in the goal store,
creates a fresh active goal with reset usage, and continues to reject
creation while any unfinished goal exists. App server clients see a
single `thread/goal/updated` event when the previous goal is replaced
with the new one.

The tool description and error message now reflect these semantics.

## What didn't change

Agents are not allowed to create a new goal (overwrite their existing
goal) if an existing goal is still active, blocked, paused, or in any
other state other than "completed".
## Why

The TUI still reached through `app-server-client::legacy_core` for
thread-name normalization and project-instruction filename details. In
particular, checking the TUI's local filesystem for `/init` is incorrect
for remote app-server sessions, where the server owns the working
directory and instruction discovery.

## What changed

- use the instruction source paths supplied by the app server to decide
whether `/init` should avoid overwriting project instructions
- keep the small thread-name normalization helper local to the TUI
- remove the now-unused instruction filename constants, utility module,
and other unused `legacy_core` re-exports
- make status helper tests independent of concrete instruction filenames

## Verification

- `just test -p codex-app-server-client`
- `just test -p codex-tui
slash_init_skips_when_project_instructions_are_loaded`
- `just test -p codex-tui` ran 2,799 tests; 2,797 passed and two
unrelated guardian feature-flag tests failed reproducibly in untouched
code

### Manual test

Started an app server over WebSocket with a remote workspace containing
`AGENTS.md`, then connected the TUI using `--remote`. After confirming
`thread/start` returned the file in `instructionSources`, deleted
`AGENTS.md` and ran `/init` in the existing session.

The TUI still reported that project instructions already existed and
skipped `/init`. The trace contained no `turn/start` request, confirming
the decision came from app-server session state rather than a new
client-local filesystem check.
## Why

Goal continuation turns are emitted by the existing runtime as separate
physical turns. The Python SDK needs private thread-scoped routing
before it can present those notifications as one logical operation,
without changing ordinary turn routing or the app-server protocol.

## What

- add private goal operation state and thread-scoped notification
routing
- add internal wrappers for the existing `thread/goal/clear` and
`thread/goal/set` RPCs
- include existing goal notifications in the SDK notification union
- preserve ordinary turn-ID routing unchanged
- add focused routing coverage

This PR does not expose a public goal API. It is the first PR in the
Python goal operations stack.

## Test plan

- online CI, including the Python SDK suite
- focused typed-notification routing coverage
## Stack

- Base: openai#27184
- This PR is the second vertical and should be reviewed against
`jif/external-plugins-1`, not `main`.

## Why

CCA is moving toward a split runtime where the orchestrator may have no
filesystem or executor, but it still needs to activate remotely hosted
plugin components. HTTP MCP servers are the simplest complete example:
they need configuration and host authentication, but they do not need an
executor process.

The Apps MCP endpoint is currently synthesized by a special-purpose
loader inside the MCP runtime. That works locally, but it leaves hosted
MCP activation outside the extension model being established in openai#27184.
It also makes the Apps path a poor foundation for plugins whose skills,
MCP servers, connectors, and hooks may come from different sources or
execute in different places.

This PR moves that one behavior behind an extension-owned contribution
while preserving the existing local fallback. It deliberately does not
introduce a generic plugin activation framework.

## What changed

### MCP extension contribution

`codex-extension-api` gains an ordered `McpServerContributor` contract.
A contributor returns typed `Set` or `Remove` overlays for MCP server
configuration; later contributors win for the names they own.

The contract stays at the existing MCP configuration boundary.
Extensions do not create a second connection manager or transport
abstraction.

### Hosted Apps MCP extension

A new `codex-mcp-extension` contributes the reserved `codex_apps` server
from the existing Apps feature, ChatGPT base URL, path override, and
product SKU configuration.

When `apps_mcp_path_override` is enabled for `https://chatgpt.com`, the
resulting streamable HTTP endpoint is
`https://chatgpt.com/backend-api/ps/mcp`. The existing ChatGPT-auth gate
remains authoritative, so this server can run in an orchestrator-only
process without being exposed for API-key sessions.

### One resolved runtime view

`McpManager` now distinguishes three views:

- **configured:** config- and plugin-backed servers before extension
overlays;
- **runtime:** configured servers plus host-installed extension
contributions;
- **effective:** runtime servers after auth gating and compatibility
built-ins.

App-server installs the hosted MCP extension and uses the runtime view
for thread startup, refresh, status, threadless resource reads,
connector discovery, and MCP OAuth lookup. This keeps
`mcpServer/oauth/login` consistent with the servers exposed by the other
MCP APIs. The hosted Apps server itself continues to use existing
ChatGPT host authentication rather than MCP OAuth.

## Compatibility

Hosts that do not install the MCP extension retain the existing Apps MCP
synthesis path. This preserves current local-only, CLI, and
standalone-host behavior while app-server exercises the extension path.

Disabling Apps removes the reserved `codex_apps` entry, and losing
ChatGPT auth removes it from the effective runtime view. Executor
availability is not consulted for this HTTP transport.

## Follow-ups

The next vertical will resolve a manifest-declared stdio MCP server from
an executor-selected plugin root and execute it in the environment that
owns that root. Later verticals can add backend-owned skills, connector
metadata, hooks, durable selection semantics, and incremental local
convergence without changing the component-specific runtime boundaries
introduced here.

## Verification

Focused coverage was added for:

- contributing the hosted Apps MCP at `/backend-api/ps/mcp` without an
executor;
- requiring ChatGPT auth in the effective runtime view;
- removing a reserved configured Apps server when the Apps feature is
disabled.

`cargo check -p codex-app-server -p codex-mcp-extension -p
codex-extension-api -p codex-mcp` passed. Tests and Clippy were not run
locally under the current development instruction; CI provides the full
validation pass.
## Why

Global instruction behavior spans thread creation, resume, forks,
subagents, and compaction. Characterization coverage is needed before
changing those semantics so preserved history can be distinguished from
newly loaded configuration.

## What changed

- Extends the existing `agents_md` suite with fresh-thread, warning,
resume, fork, and subagent lifecycle coverage.
- Extends the existing `compact` suite with manual, mid-turn, and
remote-v2 compaction coverage.
- Asserts rendered instruction fragments, reported source paths, and
structured request history before and after instruction-file mutations.
…6713)

## Why

Persisted MCP OAuth credentials were reported as authenticated whenever
a credential record existed. An expired token without a usable refresh
token could therefore appear as `OAuth` even though startup could not
authenticate with it, leaving users with a misleading status instead of
a login prompt.

## What changed

- Classify stored OAuth credentials as missing, usable, or requiring
authorization.
- Reuse the existing refresh window so near-expiry credentials without a
refresh path are also treated as logged out.
- Validate required credential fields before reporting OAuth
authentication.
- Add unit coverage for credential usability and integration coverage
for expired, unexpired, and refreshable persisted credentials.

## Validation

- `just test -p codex-rmcp-client`
## Why

A long-running unified exec process started with `tty: false` could not
be interrupted via `write_stdin`: ordinary non-TTY stdin writes are
rejected once stdin is closed, but an exact U+0003 payload should still
map to a process interrupt. The interrupt should flow through the same
process lifecycle path as a real signal so Codex preserves
process-reported output and exit metadata instead of fabricating a
Ctrl-C exit code or tearing down the session early.

## What Changed

- Add `process/signal` to exec-server with `ProcessSignal::Interrupt`
and an empty response.
- Add a non-consuming `ProcessHandle::signal` path for spawned
processes; on Unix it sends SIGINT to the process group and leaves
terminate/hard-kill unchanged.
- Route non-TTY U+0003 `write_stdin` through `process.signal(...)`
instead of `terminate`, then let the normal post-write collection path
drain output and observe exit.
- Add exec-server coverage where a shell `trap INT` handler prints the
signal and exits with its own code.
- Add unified exec coverage where a `tty: false` process traps SIGINT,
emits output, and exits with its own code.

## Validation

- `just test -p codex-exec-server
exec_process_signal_interrupts_process`
- `just test -p codex-exec-server`
- `just test -p codex-core
write_stdin_ctrl_c_interrupts_non_tty_session`
## Why

The realtime frontend model and the backing Codex thread should present
one coherent assistant. Raw typed messages, steers, and worker reports
belong to the orchestrator; the frontend model should receive the
orchestrator's user-facing result rather than a second copy of those
inputs.

Today normal `turn/start` input is automatically inserted into the
realtime conversation, while `turn/steer` is not. Besides creating
inconsistent context, this can make the frontend model react
independently before Codex has produced the response it should speak.

## What changed

- Remove automatic accepted-user-input mirroring into realtime
- Remove the mirror-only echo-suppression flag and dead V2 prefix helper
- Preserve explicit app-to-realtime text injection and FEM-to-Codex
delegation
- Replace the positive mirror tests and obsolete snapshots with a
negative routing regression test

## Test plan

- `cargo test -p codex-core
conversation_user_text_turn_is_not_sent_to_realtime`
- `cargo test -p codex-core
conversation_startup_context_is_truncated_and_sent_once_per_start`
- `cargo test -p codex-core inbound_handoff_request_starts_turn`
## Why

The Python SDK must treat the runtime's initial goal turn and its
continuations as one logical operation. That requires a private
lifecycle engine before the public API can return the existing turn
handle and result types.

## What

- start goals by composing the existing clear/set goal RPCs
- enforce persisted, idle threads and a bounded startup handshake
- coalesce continuation notifications under a stable logical turn ID
- aggregate items, usage, timing, and terminal status
- support rollover-aware steering, interruption, cancellation, and
cleanup
- provide equivalent sync and async internals

This is the second PR in the stack and intentionally adds no public API.

## Test plan

- online CI, including the Python SDK suite
- behavioral coverage is added in the following two stack PRs
## Summary
- Retry transient streamable HTTP failures during RMCP startup when the
failure happens while sending the initialize request.
- Retry transient streamable HTTP failures for tools/list, which is
read-only and safe to replay.
- Cover both retryable HTTP statuses and request-layer failures where no
HTTP status is returned.
- Surface retryable HTTP statuses from the streamable HTTP adapter as
typed client errors.
- Add integration coverage for initialize retry, tools/list retry,
no-status request failure retry, and non-retryable initialize status.

## Root cause
The observed codex_apps failures can happen before normal tool
execution: RMCP startup fails while sending initialize, or the first
read-only tools/list fails after startup. Retrying hosted_apps_bridge
tools/call would not cover initialize and would risk replaying
side-effecting tool calls. This change retries the streamable HTTP
handshake itself, recreates the transport between initialize attempts,
and retries only tools/list among post-initialize service operations.

## Validation
- cargo fmt --package codex-rmcp-client
- cargo test -p codex-rmcp-client --test streamable_http_recovery
…ai#27257)

## Summary

- order `McpConnectionManager` methods by visibility, with the primary
constructor and public API first
- restrict `list_available_server_infos` to `codex-mcp`
- make `new_uninitialized` a private test-only helper

## Why

The manager exposed methods that are only used inside `codex-mcp` or its
unit tests. Tightening those methods keeps the exported API intentional,
while the new ordering makes the supported surface easier to scan.

## Validation

- `just fmt`
- `git diff --check`
- local tests not run; relying on CI
## Why

Memory startup used hardcoded OpenAI model slugs for extraction and
consolidation. That works for the default OpenAI-compatible path, but
provider-specific backends can require different model identifiers. In
particular, Amazon Bedrock should use its Bedrock model ID for these
background memory requests instead of the OpenAI `gpt-5.4-mini` /
`gpt-5.4` slugs.

## What Changed

- Added provider-owned preferred memory model methods alongside
`approval_review_preferred_model`.
- Updated memory extraction and consolidation to resolve their default
model through the active `ModelProvider`.
- Added Amazon Bedrock overrides so both memory stages use
`openai.gpt-5.4` through Bedrock’s provider-specific model ID.
- Kept explicit `memories.extract_model` and
`memories.consolidation_model` config overrides taking precedence.
- Added startup coverage for default OpenAI and Bedrock memory model
selection.

#closes openai#26288
## Why
- Local profiling shows `append_tool_search_executor` averages ~113ms
per call. Adding a span lets us track this cost as we optimize in
follow-up PRs, either by reducing the work or avoiding repeated rebuilds
when inputs have not changed.
- While we're here, we can add spans to `build_tool_router` and other
sub-calls which code analysis shows may have additional opportunities
for improvement.

## What changed
Add function-level trace spans around `build_tool_router`,
`build_tool_specs_and_registry`, `add_tool_sources`,
`append_tool_search_executor`, and
`build_model_visible_specs_and_registry`

## Verification
Trigger Codex rollout and observe new spans are included
dylan-hurd-oai and others added 30 commits June 12, 2026 13:31
## Summary
Removes Plugin descriptions from the dev message, since descriptions of
skills and MCPs cover the capabilities offered by the plugin.

## Testing
- [x] Updates unit tests
## Why

Multi-agent v2 `send_message` deliveries already reach the receiving
model as typed `agent_message` items with encrypted content.
Child-completion notifications are generated by Codex itself, so their
content is plaintext and previously fell back to a serialized JSON
envelope inside an assistant message.

With plaintext `input_text` supported for `agent_message`, both delivery
paths can use the same model-visible type while preserving explicit
author and recipient metadata.

## What changed

- add plaintext `input_text` support to `AgentMessageInputContent` and
regenerate the affected app-server schemas
- preserve `InterAgentCommunication` as structured mailbox input instead
of converting it to assistant text
- record delivered communications as typed `agent_message` history items
- persist a dedicated rollout item so local delivery metadata such as
`trigger_turn` remains available without leaking into the Responses
request
- reconstruct typed agent messages on resume and preserve fork-turn
truncation behavior
- remove request-time assistant-content parsing
- preserve plaintext and encrypted inter-agent deliveries in stage-one
memory inputs
- normalize and link plaintext and encrypted agent messages in rollout
traces without treating inbound messages as child results
- cover the real MultiAgent V2 child-completion path end to end with
deterministic mailbox synchronization

## Verification

- `just test -p codex-core
plaintext_multi_agent_v2_completion_sends_agent_message`
- `just test -p codex-core input_queue_drains_mailbox_in_delivery_order
record_initial_history_reconstructs_typed_inter_agent_message
fork_turn_positions_use_inter_agent_delivery_metadata`
- `just test -p codex-memories-write
serializes_inter_agent_communications_for_memory`
- `just test -p codex-rollout-trace
agent_messages_preserve_routing_and_content
sub_agent_started_activity_creates_spawn_edge`
- `just test -p codex-rollout-trace
agent_result_edge_falls_back_to_child_thread_without_result_message`
- `just test -p codex-protocol -p codex-rollout -p
codex-app-server-protocol`
## Why

Removes the realtime audio support from TUI.

## What Changed

- Removed the TUI `/realtime` and realtime `/settings` command paths.
- Deleted TUI voice capture/playback, WebRTC session handling,
audio-device selection UI, and recording-meter code.
- Removed TUI realtime tests and snapshots that covered the deleted
surfaces.
- Dropped the TUI-only `cpal` and `codex-realtime-webrtc` dependencies
and refreshed the Rust/Bazel locks.
## Why

Windows Credential Manager limits generic credential blobs to 2,560
bytes. Large serialized ChatGPT auth payloads can exceed that limit, so
keyring-mode CLI auth needs a backend that keeps only the encryption key
in the OS keyring and stores the payload in Codex's encrypted
local-secrets file.

This is the third PR in the encrypted-auth stack:

1. openai#27504 — feature and config selection
2. openai#27535 — auth-specific local-secrets namespaces
3. This PR — CLI auth implementation and activation
4. MCP OAuth implementation and activation

## What Changed

- Added encrypted CLI-auth storage using the `CliAuth` secrets
namespace.
- Preserved direct keyring storage for platforms/configurations where it
remains selected.
- Selected the backend consistently for login, logout, refresh,
device-code login, auth loading, and login restrictions.
- Threaded resolved bootstrap/full config through CLI, exec, TUI,
app-server account handling, cloud config, and cloud tasks.
- Removed stale `auth.json` fallback data after successful encrypted
saves and removed encrypted, direct-keyring, and fallback data during
logout.
- Added storage and integration coverage for both direct and encrypted
keyring modes.

MCP OAuth persistence is intentionally left to the next PR.

## Validation

- `just test -p codex-login` — 131 passed
- `just test -p codex-cli` — 280 passed
- `just test -p codex-app-server v2::account` — 25 passed
- `just test -p codex-cloud-config service` — 21 passed, 7 skipped
- `just fix -p codex-login`
- `just fix -p codex-cli`
- `just fmt`
## Summary
Startup warnings for under-development features only recognized bare
boolean toggles like `features.foo = true`. An upcoming feature will use
table-format config, so `features.foo = { enabled = true, ... }` needs
to count as an explicit opt-in too.

This updates the warning predicate to recognize structured tables with
`enabled = true`, while leaving tables without that field unwarned.

## Testing
- `just fmt`
- `just test -p codex-features
unstable_warning_event_mentions_enabled_structured_under_development_feature`
## Summary

- store MCP OAuth credentials in the configured auth credential backend
- support encrypted-local OAuth storage, including legacy keyring
migration
- propagate the credential backend through MCP refresh, session, CLI,
and app-server paths

## Stack

1. openai#27504 — config and feature flag
2. openai#27535 — auth-specific secret namespaces
3. openai#27539 — encrypted CLI auth storage
4. this PR — encrypted MCP OAuth storage

This is a parallel review stack; the original openai#17931 remains unchanged.

## Tests

- `just test -p codex-rmcp-client` (the transport round-trip test passed
after building the required `codex` binary and retrying)
- `just test -p codex-mcp`
- `just test -p codex-app-server
refresh_config_uses_latest_auth_keyring_backend`
- `just test -p codex-core
refresh_mcp_servers_is_deferred_until_next_turn`
- `just test -p codex-cli mcp`
- `just fix -p codex-rmcp-client -p codex-mcp -p codex-core -p codex-cli
-p codex-app-server -p codex-protocol`
- `just bazel-lock-check`
## Summary

Add an explicit `user` or `developer` role to
`thread/realtime/appendText` and propagate it through the realtime input
queue into `conversation.item.create`. Older JSON clients that omit the
field continue to default to `user`.

This lets app-provided context such as memory retain developer authority
without bypassing app-server through a renderer-owned data channel. The
app-server schemas, API documentation, and focused protocol and
websocket coverage are updated with the new contract.

The Codex Apps consumer is tracked in
[openai/openai#1025261](openai/openai#1025261).
## Stack

1. [1 of 3] Support long raw TUI goal objectives - openai#27508
2. **[2 of 3] Support long pasted text in TUI goals** - this PR
3. [3 of 3] Support images in TUI goals - openai#27510

## Why

Large text pasted into the TUI composer is represented as a paste
placeholder plus pending paste metadata. For `/goal`, preserving only
the visible placeholder is not enough: the agent would see a short
placeholder string instead of the actual pasted text, and the long-text
support from the first PR would never see the payload.

The TUI also needs to avoid writing stale sidecar files when a user
pastes a large block and then deletes its placeholder before submitting
the goal.

## What Changed

- Introduces a TUI `GoalDraft` for goal submissions so `/goal`, `/goal
edit`, and queued goal commands can carry objective text plus text
elements and pending paste payloads.
- Materializes active pasted-text placeholders to `pasted-text-N.txt`
files through the app-server filesystem path introduced in openai#27508.
- Rewrites active paste placeholders in the persisted objective to file
references, while leaving literal placeholder-looking text alone.
- Filters out deleted paste placeholders so otherwise-small goals do not
require `$CODEX_HOME` or remote filesystem writes.
- Preserves pending paste metadata when a `/goal` command is queued
before a thread exists.

## Verification

- Added goal materialization tests for active paste placeholders,
deleted paste placeholders, and whitespace-only paste payloads.
- Added/updated TUI slash-command tests for large pasted text, queued
`/goal` commands before thread start, and queued oversized goal
behavior.

## Manual Testing

- Used real terminal bracketed-paste sequences through a remote TUI
session. A 1,228-byte multiline paste became `pasted-text-1.txt`; its
first/last lines and byte count matched exactly, and the persisted
objective referenced the server-host path.
- Pasted a large block, deleted its placeholder, and submitted a small
replacement objective. No new directory or sidecar file was created.
- Added two same-length large pastes to one goal. The composer
disambiguated their visible placeholders, and materialization preserved
order and contents in `pasted-text-1.txt` and `pasted-text-2.txt`.
- Submitted a whitespace-only large paste and verified the goal was
rejected as empty without writing a file.
- Submitted a pasted-text replacement while another goal was active,
verified no file was written before confirmation, then canceled and
confirmed the original goal remained unchanged.
- Combined a large paste with enough raw text to exceed 4,000 characters
after placeholder rewriting. The paste sidecar and `goal-objective.md`
were created in the same remote attachment directory, and `/goal edit`
restored the rewritten objective with its sidecar reference.
## Why

We need request-level evidence for Guardian cases where
`codex-auto-review` is missing from the client-side model catalog and
the review falls back to the parent model.

## What changed

- Add `guardian_catalog_contains_auto_review` to Guardian Responses API
client metadata.
- Add `guardian_model_provider_id` to Guardian Responses API client
metadata.
- Keep review-session metadata optional so callers without metadata
preserve the existing `None` path.
- Add tests for override, normal preferred-model, and
missing-auto-review-catalog behavior.

## Validation

- `just test -p codex-core
guardian_review_records_missing_auto_review_model_in_request_metadata`
- `just test -p codex-core
guardian_review_uses_model_catalog_override_when_preferred_review_model_exists`
- `just test -p codex-core
guardian_review_uses_preferred_review_model_without_model_catalog_override`
- `git diff --check origin/main`
Codex seems to do interesting things with `cfg`'s sometimes and it seems
it would be good to give it guidance about how broadly our Rust needs to
work.

This adds a very brief section to AGENTS.md explaining that we target
the major desktop OSes and that we want the vast majority of our logic
to be portable across them.
Each Windows packaging job creates three compressed forms of five
binaries in sequence. This takes roughly two minutes and is on the
release critical path.

Use two xargs workers to compress independent binaries concurrently.
The workers only read the raw executables and write per-binary archive
names. The Codex zip can safely read the helper executables while their
own archives are generated.

On a 16-vCPU AMD EPYC 9V74 Windows x64 release runner, alternating
trials against artifacts from release run 27391514823 measured:

  serial:   121 s, 123 s, 121 s
  parallel:  73 s,  73 s,  74 s

This saves 47 to 50 seconds in the x64 packaging lane, reducing the
observed release critical path by about 48 seconds when x64 remains the
limiting lane.

https://github.com/openai/codex/actions/runs/27401905938
…penai#27499)

## Summary

This PR promotes Mentions 2.0 (unified TUI mention popup) to stable and
enables it by default.

- Keep `mentions_v2` as a temporary rollback path to the legacy split
popups (`--disable mentions_v2`).
- Add feature-default and snapshot coverage for the default experience.

## Prior work

- [openai#19068 — Unified mentions in
TUI](openai#19068)
- [openai#22375 — Use plugin/list to get plugins for
mentions](openai#22375)
- [openai#23363 — Unified mentions tweaks and rendering
polish](openai#23363)

## Test plan

- Launch Codex without any feature overrides.
- Type `@` in the TUI composer.
- Confirm the unified mentions menu opens and displays filesystem,
plugin, and skill results.
## Why

The paired thread-environment migration changed several generic test
turn helpers from supplying a fallback cwd to explicitly selecting the
local environment. That changes their meaning under
`build_with_remote_env()`: remote-only fixtures cannot resolve the
forced local selection, so the tests fail before exercising apply-patch,
RMCP, unified-exec, or view-image behavior.

Generic helpers should inherit the environment selected by their
fixture. Tests that intentionally exercise local routing continue to
select the local environment explicitly.

## What changed

- Remove forced `local_selections(...)` overrides from the generic
apply-patch, RMCP, unified-exec, and view-image turn helpers.
- Remove the imports made unused by those deletions.

## Testing

- Not run locally; this is a test-fixture-only change and the `full-ci`
branch will exercise the affected remote shards.
In the x64 packaging job from

https://github.com/openai/codex/actions/runs/27391514823

archiving and uploading PDBs took 65 seconds after signing. Release
packaging could not start until that work completed.

Windows code signing changes executables but not their PDBs. Package
the PDBs in a sibling Ubuntu job as soon as all binary artifacts are
available. Signing and release packaging can then proceed without
waiting for the symbols archive, reducing the critical path by about
one minute.
## Why

`PathUri::from_abs_path` can fail for absolute paths that do not have a
normal `file:` URI representation, forcing filesystem call sites to
handle a conversion error even though the original path can be preserved
losslessly.

## What

Make `from_abs_path` infallible and migrate its callers. Unrepresentable
paths use `file:///%00/bad/path/<base64>`, encoding Unix bytes or
Windows UTF-16LE; `to_abs_path` validates and decodes that fallback. The
leading encoded null reserves a namespace that cannot collide with a
real Unix or Windows path, and fallback URIs remain opaque to lexical
path operations.

## Validation

Added path-URI coverage for Unix null and non-UTF-8 paths, Windows
device/verbatim and non-Unicode paths, serialization, malformed
fallbacks, opaque lexical operations, invalid native payloads, and
literal `/bad/path` collision resistance.
In the Windows x64 packaging job from

https://github.com/openai/codex/actions/runs/27391514823

building the primary and app-server package archives serially took 116
seconds.

Both archives read the same signed-binary directory but write separate
package trees and output files. Run them concurrently with xargs -P2.

The package helper rewrites DotSlash executables under the process temp
directory. A naive concurrent run failed when one process tried to
replace an executable used by the other. Give each bundle separate TMP
and TEMP roots to keep those caches independent.

On Windows x64 in

https://github.com/openai/codex/actions/runs/27397197944

three serial trials took 127, 128, and 126 seconds. Concurrent trials
took 76, 74, and 74 seconds, saving 52 to 54 seconds. This removes about
50 seconds from the release critical path without changing the packaging
commands or output set.
In the release job from

https://github.com/openai/codex/actions/runs/27391514823

staging the nine npm release tarballs serially took 104 seconds.

Each package build writes to a separate staging directory, output path,
and npm cache. Run them through the script's existing thread pool,
bounded by the available CPU count. Delete each staging tree as its
build finishes so concurrency does not retain all copies until the end.

On ubuntu-24.04 in

https://github.com/openai/codex/actions/runs/27397232050

two serial trials took 103 and 101 seconds, while concurrent trials
both took 41 seconds. Comparing every extracted file from the first
serial and concurrent sets found no differences. This removes about one
minute from every release.
## Why

We have some large gaps in our thread start, resume, and pre-sampling
traces that make it hard to tell where latency is coming from.

## What Changed

- Added coarse spans around thread start/resume, turn context
construction, rollout reconstruction, skill/plugin loading, and tool
preparation.
- Added a breakdown of discoverable-tool preparation across connector
loading, plugin discovery, and local plugin details.

## Testing

- `cargo check -p codex-app-server -p codex-core -p codex-core-skills -p
codex-core-plugins`
- Built the app-server locally and exercised thread start, first turn,
follow-up turn, server restart, thread resume, and a resumed turn.
## Stack

1. [1 of 3] Support long raw TUI goal objectives - openai#27508
2. [2 of 3] Support long pasted text in TUI goals - openai#27509
3. **[3 of 3] Support images in TUI goals** - this PR

## Why

The first two PRs make goal definitions resilient to long text, but
`/goal` still dropped image inputs from the composer. That meant a user
could attach images while defining a goal and the resulting goal
continuation would not have any useful reference to those images.

Goal state still persists only objective text, so image inputs need to
become paths or URLs that the agent can read later.

## What Changed

- Extends TUI `GoalDraft` with local image attachments and remote image
URLs.
- Copies local goal images through the app-server filesystem layer into
the managed goal attachment directory, then rewrites active image
placeholders to file references.
- Appends unplaced local images and remote image URLs to the objective
as referenced image files or URLs.
- Preserves goal image metadata through live `/goal` submission and
queued `/goal` dispatch.

## Verification

- Added goal materialization coverage for local image files and remote
image URLs.
- Added/updated TUI slash-command coverage showing `/goal` drafts
include attached images instead of dropping them.

## Manual Testing

- Attached an image by bracketed-pasting its local path into a live
`/goal` composer. The `[Image #1]` placeholder became a server-host
`image-1.png` reference, copied bytes matched exactly, and no attachment
was written under the TUI's local home.
- Deleted an image placeholder before submitting a small goal and
verified no image was copied.
- Attached PNG and JPEG files to the same goal. Placeholder order was
preserved as `image-1.png` and `image-2.jpg`, and both remote copies
matched their source bytes.
- Tried extensionless, malformed-extension, and
extension/content-mismatched paths; the composer rejected them as image
attachments before goal dispatch rather than creating misleading managed
image files.
- Combined a local image, a large pasted block, and enough raw text to
exceed 4,000 characters. The remote attachment directory contained the
image, paste sidecar, and `goal-objective.md`; all embedded references
used server-host paths and both payloads matched their sources.
- Submitted an image replacement while a goal was active, verified no
image was copied before confirmation, then canceled and confirmed the
attachment count was unchanged.
## Why

[openai#25345](openai#25345) was approved,
green, and squash-merged into its stacked base branch,
`fcoury/tokenmaxxing-api`. Four minutes later, that base branch was
force-pushed back to an API-only rebased head while preparing
[openai#25344](openai#25344) for `main`. As a
result, the squash commit from openai#25345 was orphaned and the TUI command
never reached `main` or a release.

This PR relands the orphaned TUI change from
[`411410b8`](openai@411410b)
on current `main`.

## What changed

- Add `/usage`, `/usage daily`, `/usage weekly`, and `/usage cumulative`
for account token activity.
- Fetch account usage asynchronously through the existing
`account/usage/read` app-server RPC.
- Render daily, weekly, and cumulative activity with theme-aware
terminal palettes and bounded transient cards.
- Preserve transcript ordering while assistant streams, history
consolidations, active cells, and hooks complete.
- Hide `/usage` from completion when backend auth is unavailable while
keeping typed-command guidance.
- Carry current-main behavior forward for cwd-aware Markdown parsing,
Windows Terminal color detection, and personal access token auth.
- Clear pending usage cards on thread rollback and delay completed cards
until live hook output is committed.
- Add focused regression and snapshot coverage for loading, auth errors,
invalid views, rollback, hook ordering, layout, and charts.

## Prior review

The original implementation was approved by Eric Traut in openai#25345 after
testing multiple themes and light/dark terminals. This PR preserves that
reviewed implementation while adapting it to current `main` and adding
regression coverage for newer rollback and hook lifecycle behavior.

## Validation

- `just test -p codex-tui token_activity palette renderable
usage_command` — 37 passed.
- Focused rollback, hook-ordering, and error snapshot tests — 4 passed.
- `just fix -p codex-tui` — passed.
- `UV_CACHE_DIR=/private/tmp/codex-uv-cache just fmt` — passed.
- `cargo insta pending-snapshots` — no pending snapshots.
- `just test -p codex-tui` — 2,870 passed; two unrelated guardian
feature-flag tests failed because their expected `OverrideTurnContext`
event was absent:
-
`update_feature_flags_disabling_guardian_clears_manual_review_policy_without_history`
-
`update_feature_flags_disabling_guardian_clears_review_policy_and_restores_default`
- `just argument-comment-lint` could not complete because the local
Bazel LLVM `compiler-rt` repository is missing `include/sanitizer/*.h`.
The touched Rust diff was manually inspected and no missing
opaque-literal argument comments were found.
…#27988)

## Summary

- Keep local plugin suggestions bounded to fallback and explicitly
configured plugins.
- Preserve app-overlap recommendations for remote plugins using cached
catalog metadata.
- Remove the WSL-specific local discovery exception and move
manager-owned discovery tests into `codex-core-plugins`.

## Why

Local curated marketplaces were allowlisted before plugin detail
loading, so every uninstalled candidate could be deep-read before its
app IDs were checked. That caused per-turn reads of candidate plugin
manifests, skills, app configs, hooks, and MCP configs, which is
especially expensive on slow disks.

Remote discovery does not need those local candidate reads because app
IDs are already available in the cached remote catalog. Installed local
plugins are still loaded when needed to determine the user's installed
app IDs.

## Validation

- `just fmt`
- `just test -p codex-core-plugins discoverable::tests` (13 passed)
- `just test -p codex-core plugins::discoverable::tests` (4 passed)
- `just bazel-lock-update`
- `just bazel-lock-check`
- `git diff --check`
## Context

Plugins can expose more than one way for Codex to use them: App
connectors for ChatGPT/SIWC-backed sessions and MCP servers for API key
login sessions. The broader goal is to make `PluginsManager` the place
that understands which plugin surfaces should be visible for the current
auth route, so callers do not each have to make that decision
themselves.

This PR is the small setup step for that work. It lets the plugin
manager be created with the current `AuthMode`, which gives the followup
auth routing PRs the information they need without relying on setter
injection.

## Stack

- PR1: openai#27652 seed plugin manager auth at construction.
- PR2: openai#27459 route plugin surfaces by auth mode.
- PR3: openai#27607 dedupe plugin MCP servers by App declaration name.
- PR4: openai#27602 preserve plugin Apps in connector listings.
- PR5: openai#27461 skip install-time plugin MCP OAuth for matching App
routes.

## Summary

- Let `PluginsManager::new_with_restriction_product` accept an initial
`AuthMode`.
- Keep `PluginsManager::new` behavior unchanged for ordinary callers.

## Validation

```bash
cargo test -p codex-core-plugins plugins_manager_tracks_auth_mode
cargo test -p codex-core list_tool_suggest_discoverable_plugins
git diff --check
```

---------

Co-authored-by: Xin Lin <xl@openai.com>
## Why

We want to make it possible for an app-server orchestrator on one OS to
control an exec-server on another host running a different OS. In
practice this kinda already works if you get lucky and the two hosts
have the same path format, but we mangle quite a lot of operations if
either end is Windows.

We should be able to test the cross-platform interactions for
exec-server, but we want to do this fairly soon and need a lightweight
option for testing. Using Wine to run the Windows side is far from
perfect, but it should give us a decent measure of how well we're
handling the basics of paths, process spawning, shell interaction, etc.

Future changes will add actual exec-server tests and possibly extensions
to the Wine testing environment.

## What

To make the cross-target-triple build easy, these tests are added only
to the Bazel build. This change adds an x86_64 Wine prebuilt managed by
Bazel and some build rules that can set up the needed toolchain
transition.

The support library for running Wine in a test environment created by
the Bazel rules comes with its own basic unit and integration tests.
Their primary priority is to make sure we don't leak child processes on
developer machines and that we can build and launch a basic hello world
binary.

## Validation

Confirmed these new tests are running on the [x86_64 bazel ubuntu
jobs](https://github.com/openai/codex/actions/runs/27446432302/job/81132356855?pr=27937):

```
//bazel/rules/testing/wine:wine-smoke-test                      (cached) PASSED in 3.7s
//bazel/rules/testing/wine:wine-test-support-unit-tests         (cached) PASSED in 15.8s
```
## Context

Some plugins expose both Apps and MCP servers. This PR moves auth-aware
surface projection into `core-plugins::PluginsManager`, so callers get a
consistent effective plugin view. Later PRs narrow the conflict rule and
update listing/install paths.

The high level goal of this PR is to set up the plumbing to
conditionally filter App/MCP in the plugin manager layer. We start by
removing MCP servers when using SIWC/Codex-backend auth, and removing
Apps when using API-key-style auth.

This PR is now stacked on openai#27652, which contains only the constructor
plumbing for seeding `PluginsManager` with the current auth mode.

## Stack

- PR1: openai#27652 seed plugin manager auth at construction.
- PR2: openai#27459 route plugin surfaces by auth mode.
- PR3: openai#27607 dedupe plugin MCP servers by App declaration name.
- PR4: openai#27602 preserve plugin Apps in connector listings.
- PR5: openai#27461 skip install-time plugin MCP OAuth for matching App
routes.

## Summary

- API-key/non-ChatGPT routes hide plugin Apps and keep plugin MCPs.
- ChatGPT/SIWC with Apps enabled keeps plugin Apps and suppresses MCPs
for dual-surface plugins.
- MCP-only plugins stay available for ChatGPT/SIWC sessions.
- Cached plugin load outcomes are re-projected when auth mode changes.

## Validation

```bash
cargo test -p codex-core-plugins plugin_auth_projection
cargo test -p codex-core list_tool_suggest_discoverable_plugins
git diff --check
```
## Why

Managed deployments need a reliable deny gate for remote control.
Persisted enablement and explicit startup requests currently remain able
to start the transport, while the removed `features.remote_control` key
is intentionally only a compatibility no-op.

This adds a dedicated requirement that administrators can use to force
remote control off without deleting the user's persisted preference.
Removing the requirement and restarting restores the prior choice.

## What Changed

- Added top-level `allow_remote_control` requirements parsing, sourced
layer precedence, debug output, and `configRequirements/read` exposure
as `allowRemoteControl`.
- Added a typed transport policy captured from the startup requirements
snapshot. Managed disable forces the initial state to disabled and
prevents enrollment, refresh, connection, and persisted-preference
mutation.
- Rejected every `remoteControl/*` RPC before parameter deserialization
with JSON-RPC `-32600` and `remote control is disabled by managed
requirements`.
- Preserved the existing disabled status notification and the previous
behavior when the requirement is `true` or omitted.
- Regenerated app-server protocol schemas and documented the new
requirement.

## Verification

- Confirmed all remote-control RPCs, including a malformed request,
return the managed-policy error while the initial status notification
remains `disabled`.
- Confirmed explicit ephemeral startup and persisted enablement make no
backend connection and leave the SQLite preference unchanged.
- Confirmed `allow_remote_control = true` does not enable or block
remote control and `configRequirements/read` returns
`allowRemoteControl: false` for the deny policy.

Related issue: N/A (managed-policy hardening).
## Why

We want to make it possible for an app-server orchestrator on one OS to
control an exec-server on another host running a different OS. In
practice this kinda already works if you get lucky and the two hosts
have the same path format, but we mangle quite a lot of operations if
either end is Windows.

This test starts exercising that interaction, although right now the
initial bootstrap fails. Future changes will expand the test's
assertions to match improved support.

## What

Stacked on openai#27964. This adds a small Windows exec-server fixture and a
Linux protocol smoke test using the reusable Wine harness, covering
Windows environment discovery, non-TTY `cmd.exe` execution, output, exit
status, and working directory.

Once we've got the full codex binary cross-building under Bazel we could
consider moving to the real binary instead of the stripped down
exec-server-only binary used here.
## Context

Turn state is scoped to one logical turn, but the WebSocket path
currently exchanges it through upgrade headers, which are scoped to the
physical connection. A connection may be reused across turns, so its
handshake cannot represent the turn lifecycle reliably.

## Change

Exchange turn state on each WebSocket response request instead:

- send an established value in `response.create.client_metadata`
- read the returned value from the existing `response.metadata` event
- retain the first value in the turn-scoped `ModelClientSession`
`OnceLock`
- start the next logical turn without state, even when it reuses the
same WebSocket connection

This gives WebSocket requests the same first-value-wins contract as the
existing HTTP path.

## Test plan

Integration coverage verifies that:

- WebSocket replays returned state on same-turn follow-ups
- later response metadata does not replace the first value
- state resets at the logical turn boundary without requiring a
reconnect

CI validates the full change.

## Stack

This is 1/2. openai#28002 builds on this request-scoped transport to carry
established state through compact requests.
## Context

Inline compaction is part of the active logical turn. Compact requests
and the sampling requests around them should use the same turn state,
including when compaction is the first request to establish it.

## Change

Pass the turn-scoped `OnceLock` directly to inline v1 compaction so
`/responses/compact` includes an established value in the existing HTTP
header. Capture `x-codex-turn-state` from the compact response into that
same lock, allowing pre-turn compact to establish the value that
subsequent sampling reuses.

V2 compact already uses the normal Responses HTTP/WebSocket path and
continues to share the same `OnceLock` without separate plumbing. The
first returned value wins for the logical turn.

## Test plan

Integration coverage verifies that:

- pre-turn v1 compact can establish state for the first sampling request
- inline v1 compact receives established state over HTTP
- inline v2 compact reuses established state over HTTP
- inline v2 compact reuses established state over WebSocket

CI validates the full change.
- Added `/usage` views for daily, weekly, and cumulative account token activity. (openai#27925)
- `/goal` now preserves oversized text, large pasted blocks, and image attachments, including in remote app-server sessions. (openai#27508, openai#27509, openai#27510)
- Added permanent session deletion through `codex delete`, `/delete`, and app-server `thread/delete`, with confirmation safeguards and subagent cleanup. (openai#25018, openai#27476)
- Added `/import` for selectively importing setup, project configuration, and recent chats from Claude Code. (openai#27070, openai#27071, openai#27703)
- Typing `@` now opens the unified mentions menu for files, plugins, and skills by default. (openai#27499)
- Added managed Amazon Bedrock API-key authentication and encrypted local storage for CLI and MCP OAuth credentials. (openai#27443, openai#27689, openai#27504, openai#27535, openai#27539, openai#27541)

## Bug Fixes

- Corrupted SQLite state databases are now backed up and rebuilt automatically from rollout data, including malformed database-directory cases. (openai#26859, openai#27719)
- Prevented `/review` from crashing when `Esc` is pressed with queued guidance, while preserving that guidance when the review is canceled. (openai#22879)
- Improved MCP reliability by retrying transient startup failures, reporting unusable OAuth credentials as logged out, and preserving explicitly disabled servers. (openai#25147, openai#26713, openai#27414)
- Fixed remote plugin uninstall requests and correctly surfaced apps requiring authentication during installation. (openai#27085, openai#27223)
- Persisted “Don’t remind me” update dismissals reliably and cleared stale running-hook indicators after completed turns. (openai#27619, openai#27783)
- Non-TTY background commands can now be interrupted with Ctrl-C while preserving their final output and exit status. (openai#26734)

## Documentation

- Clarified contributor guidance around keeping crate APIs narrow and supporting Linux, macOS, and Windows. (openai#27939, openai#27966)

## Chores

- Improved responsiveness for large repositories and long sessions by preserving Git’s built-in filesystem monitor, avoiding duplicate history reads, accelerating archive lookup, and caching turn-diff rendering. (openai#26880, openai#27031, openai#27276, openai#27489)
- Removed the experimental `/realtime` voice controls and related audio dependencies from the TUI. (openai#27801)

## Changelog

Full Changelog: openai/codex@rust-v0.139.0...rust-v0.140.0

- openai#26880 [codex] preserve fsmonitor for worktree Git reads @tamird
- openai#27085 Use server app auth requirements for remote plugin install @xl-openai
- openai#27098 [codex] Return workspace directory installed plugins @xl-openai
- openai#27007 multi-agent: add path-based v2 activity tracking @jif-oai
- openai#27166 app-server: clear stale thread watches after v2 agent interruption @jif-oai
- openai#27080 [codex] Ignore pending PR review comments @anp-oai
- openai#26420 Avoid no-op backfill state writes @zanie-oai
- openai#27031 Avoid rereading rollout history during cold resume @zanie-oai
- openai#22879 fix: Prevent /review crash when entering Esc on steer message @canvrno-oai
- openai#27173 app-server: reject direct input to multi-agent v2 sub-agents @jif-oai
- openai#27184 Load selected executor skills through extensions @jif-oai
- openai#26835 [codex] Test extension API contracts @anp-oai
- openai#27063 [codex-analytics] add extensible feature thread sources @marksteinbrick-oai
- openai#26479 [codex] Speed up local nextest runs @anp-oai
- openai#27223 fix: use plugin service route for remote uninstall @ericning-o
- openai#22685 Add SOCKS5 TCP MITM coverage @winston-openai
- openai#26681 Allow creating a new goal after completion @etraut-openai
- openai#26711 Reduce TUI legacy core dependencies @etraut-openai
- openai#27110 [1/6] Add Python goal routing foundation @aibrahim-oai
- openai#27191 Route hosted Apps MCP through extensions @jif-oai
- openai#26830 [codex] Characterize global instruction lifecycle @anp-oai
- openai#26713 [codex] Report unusable MCP OAuth credentials as logged out @anp-oai
- openai#26734 [codex] Handle Ctrl-C for non-TTY unified exec @pakrym-oai
- openai#27116 Stop mirroring Codex user input into realtime @guinness-oai
- openai#27111 [2/6] Add private Python goal operations @aibrahim-oai
- openai#25147 [codex] Retry streamable HTTP initialize failures @ssetty-oai
- openai#27257 [codex] Tighten MCP connection manager API visibility and order @aibrahim-oai
- openai#26701 TUI Plugin Sharing 1 - add remote plugin identity @canvrno-oai
- openai#27129 feat: use provider defaults for memory models @celia-oai
- openai#27094 Add spans to build_tool_router @mchen-oai
- openai#24999 Add per-session realtime model and version overrides @guinness-oai
- openai#27078 [codex-analytics] emit goal lifecycle analytics @marksteinbrick-oai
- openai#27285 [codex] Fix post-merge analytics integration failures @anp-oai
- openai#27107 Add spans to run_turn @mchen-oai
- openai#27261 [codex] Make MCP connection startup fallible @aibrahim-oai
- openai#27174 feat: keep child MCP warnings out of parent transcript @jif-oai
- openai#27198 Use plugin-service MCP as the hosted plugin runtime @jif-oai
- openai#27375 [codex] Tag multi-agent spawn metrics with version @jif-oai
- openai#27383 Remove async-trait from extension contributors @jif-oai
- openai#27259 Use latest-wins MCP manager replacement @charliemarsh-oai
- openai#27264 [codex] Store compact window id in rollout @pakrym-oai
- openai#27280 [codex] add io PathUri native conversion APIs @anp-oai
- openai#27315 [codex] link Windows releases with LLD @tamird
- openai#27276 Reduce archive rollout lookup CPU @etraut-openai
- openai#27299 [codex] Outline ToolExecutor handler bodies @anp-oai
- openai#27391 Index visible thread list ordering @zanie-oai
- openai#27407 Fix compressed rollout search path matching @jif-oai
- openai#27304 [codex] Remove async_trait from ToolExecutor @anp-oai
- openai#26041 Add app-server background terminal process APIs @etraut-openai
- openai#25018 Add app-server `thread/delete` API @etraut-openai
- openai#26859 fix: Auto-recover from corrupted sqlite databases @ddr-oai
- openai#27064 [codex] remove blocking external agent migration flow @stefanstokic-oai
- openai#27421 [codex] Raise app-server recursion limit @anp-oai
- openai#27062 [codex] Retry transient Guardian review failures @kbazzi
- openai#27065 [codex] extract external agent import picker renderer @stefanstokic-oai
- openai#26409 [plugins] Inject remote_plugin_id into install elicitations @adaley-openai
- openai#27439 feat: make ThreadStore available on ThreadExtensionDependencies @bolinfest
- openai#27343 Guard core test subprocess cleanup @etraut-openai
- openai#27070 [codex] add external agent import picker UX @stefanstokic-oai
- openai#27321 [codex] Move release platform rules into bazel package @anp-oai
- openai#27071 [codex] add /import for external agents @stefanstokic-oai
- openai#27311 [codex] Skip local curated discovery for remote plugins @xl-openai
- openai#27414 [codex] Preserve disabled MCP servers across runtime overlays @e-provencher
- openai#27312 [codex] reuse release artifacts for npm staging @tamird
- openai#27319 Forward standalone assistant output to realtime @guinness-oai
- openai#27057 [codex] Add reusable OTEL gauge instruments @richardopenai
- openai#27245 image: add shared data URL preparation utilities @fjord-oai
- openai#27392 [codex-analytics] emit internally started turn events @marksteinbrick-oai
- openai#27322 [codex] Preserve build-script dependencies in rules_rs annotations @anp-oai
- openai#27489 core: cache turn diff rendering @nornagon-openai
- openai#27465 [codex] Remove redundant plugin app auth state @xl-openai
- openai#27484 Remove TUI legacy core test_support dependencies @etraut-openai
- openai#27476 Add session delete commands in CLI and TUI @etraut-openai
- openai#27247 core: resize all history images behind a feature flag @fjord-oai
- openai#27487 Trim TUI legacy telemetry and migration dependencies @etraut-openai
- openai#27438 [codex] Add token budget context feature @pakrym-oai
- openai#27501 [codex] Expand hosted web search citation guidance @yuning-oai
- openai#27526 tools: simplify default tool search text @sayan-oai
- openai#27488 [codex] Add new context window tool @pakrym-oai
- openai#27443 feat: add Bedrock API key as a managed auth mode @celia-oai
- openai#27532 [codex] Add comp_hash to model metadata @aibrahim-oai
- openai#27246 core: strip image detail from Responses Lite requests @fjord-oai
- openai#27517 [codex] Pass auth mode to plugin manager @xl-openai
- openai#27520 [codex] Compact when comp_hash changes @aibrahim-oai
- openai#27518 [codex] Add context remaining tool @pakrym-oai
- openai#27266 image: preserve metadata when resizing prompt images @fjord-oai
- openai#27103 [codex-analytics] report cached input tokens for v2 compaction @rhan-oai
- openai#27356 Use generic search metadata for dynamic tools @sayan-oai
- openai#27082 [codex-analytics] Emit structured compaction codex errors @rhan-oai
- openai#26513 [codex] Tune cloud config cache intervals @alexsong-oai
- openai#27387 skills: make backend plugin skills invocable without an executor @jif-oai
- openai#27403 skills: cache remote catalog failures per thread @jif-oai
- openai#27573 core: enable remote compaction v2 by default @jif-oai
- openai#27388 skills: expose remote skill resource tools @jif-oai
- openai#27569 multi-agent: move concurrency guidance into v2 usage hints @jif-oai
- openai#27585 nit: cap error @jif-oai
- openai#27404 test: cover referenced backend skill reads without an executor @jif-oai
- openai#27591 skills: render catalog locators by authority @jif-oai
- openai#27413 skills: decouple the skills extension from core @jif-oai
- openai#27527 [codex] publish npm packages concurrently @tamird
- openai#27528 [codex] publish DotSlash alongside npm @tamird
- openai#27529 [codex] download only release artifacts @tamird
- openai#27490 Remove TUI legacy Windows sandbox dependency @etraut-openai
- openai#27483 Emit plugin ID on MCP tool call analytics events @chrisdong-oai
- openai#27417 Print TUI session info on fatal exits @etraut-openai
- openai#27507 lint: allow self-documenting builder arguments @anp-oai
- openai#27420 [codex] Propagate plugin app categories @charlesgong-openai
- openai#27454 [codex] add cross-platform filesystem adapter coverage @anp-oai
- openai#27415 [codex] Surface runtime warnings in codex exec @anp-oai
- openai#27639 [codex] revert concurrent npm publishing @tamird
- openai#27646 feat: disable orchestrator skills for now @jif-oai
- openai#27323 [codex] Provide ARM64 MinGW powl compatibility support @anp-oai
- openai#27433 [codex] remove EnvironmentPathRef @anp-oai
- openai#27424 [codex] migrate ExecutorFileSystem paths to PathUri @anp-oai
- openai#27101 [codex] Load user instructions through an injected provider @anp-oai
- openai#27634 Resolve MCP server registrations through a catalog @jif-oai
- openai#27122 core: Consolidate Responses API Codex metadata @owenlin0
- openai#27450 [codex-rs] enforce PAT workspace restrictions @cooper-oai
- openai#27653 [codex] migrate exec-server filesystem protocol to PathUri @anp-oai
- openai#27663 Include thread id in token budget context @pakrym-oai
- openai#26418 [codex] Avoid duplicate hooks.json discovery with profiles @abhinav-oai
- openai#27689 feat: prefer managed Bedrock auth in model provider @celia-oai
- openai#27700 Remove fs/join and fs/parent from exec-server protocol @anp-oai
- openai#26426 Warn when hooks.json has unsupported top-level fields @abhinav-oai
- openai#27318 [codex] Move persistence policy application into ThreadStore @wiltzius-openai
- openai#27498 Route image extension reads through turn environments v2 @won-openai
- openai#27623 Add spans to turn lifecycle gaps @mchen-oai
- openai#27619 tui: clear stale hook row after turn completion @kotakem-openai
- openai#27711 Fix image extension PathUri conversion @anp-oai
- openai#27475 [codex] Remove async_trait from first-party code @anp-oai
- openai#27719 fix: Recover from sqlite directory being a file @ddr-oai
- openai#27715 ci(v8): gate Windows source builds on relevant changes @cconger
- openai#27702 [codex] parallelize release code generation @tamird
- openai#27709 [codex] resolve environment shell metadata eagerly @pakrym-oai
- openai#27445 feat(app-server): persist remote-control desired state @apanasenko-oai
- openai#27508 [1 of 3] Support long raw TUI goal objectives @etraut-openai
- openai#27256 Add request_user_input auto-resolution window contract @shijie-oai
- openai#27724 code-mode standalone: extract protocol and add host crate @cconger
- openai#27778 Translate non-English issues @etraut-openai
- openai#27316 Keep request_user_input direct-model only @shijie-oai
- openai#27696 [codex] Load AGENTS.md from all bound environments @anp-oai
- openai#27670 Make MCP server contributions thread-scoped @jif-oai
- openai#27732 [code-mode] Reject remote image URLs from output helpers @rka-oai
- openai#27692 Add executor-owned plugin resolution @jif-oai
- openai#27863 Extract shared plugin MCP config parsing @jif-oai
- openai#27703 [codex] restore source-specific import copy @stefanstokic-oai
- openai#27879 fix: serialize auth environment tests @jif-oai
- openai#27791 Reject transcript backtrack in side conversations @etraut-openai
- openai#27075 [ez][codex-rs] Support approvals reviewer in app defaults @zamoshchin-openai
- openai#27538 Use dependency groups for Python SDK tooling @charliemarsh-oai
- openai#27783 Persist update dismissal without cache @etraut-openai
- openai#27814 tui: Allow extra o's in /goal command @btraut-openai
- openai#27901 Use uv as Python SDK build backend @charliemarsh-oai
- openai#27720 realtime: add AVAS architecture override @bakks
- openai#27919 chore: prompt MAv2 @jif-oai
- openai#27816 sandboxing: migrate cwd inputs to PathUri @anp-oai
- openai#27890 [codex] expose remote plugin share URL @ericning-o
- openai#27913 [codex] unify apply patch parsing @pakrym-oai
- openai#27920 Handle standalone image generation failures as terminal items @won-openai
- openai#27927 [codex] Add size to internal filesystem metadata @pakrym-oai
- openai#27504 feat: add secret auth storage configuration @celia-oai
- openai#27674 [login] revoke existing auth before starting login @cooper-oai
- openai#27535 feat: add auth-specific encrypted secret namespaces @celia-oai
- openai#27939 [codex] Add crate API surface review rule @pakrym-oai
- openai#27926 [codex] Align implicit skill reads with parser @alexsong-oai
- openai#23254 fix(plugins) rm plugin descriptions @dylan-hurd-oai
- openai#27830 Support plaintext agent messages @jif-oai
- openai#27801 Remove TUI realtime voice support @etraut-openai
- openai#27539 feat: use encrypted local secrets for CLI auth @celia-oai
- openai#27076 Warn for structured feature toggles @canvrno-oai
- openai#27541 feat: use encrypted local secrets for MCP OAuth @celia-oai
- openai#27936 [codex] add roles to realtime append text @agamble-oai
- openai#27509 [2 of 3] Support long pasted text in TUI goals @etraut-openai
- openai#27109 Add Guardian catalog diagnostics metadata @won-openai
- openai#27966 Specify platform support in AGENTS.md @anp-oai
- openai#27855 [codex] parallelize Windows compression @tamird
- openai#27499 Promote TUI unified mentions in composer to default mentions feature @canvrno-oai
- openai#27972 [codex] Let generic test turns inherit their environment @pakrym-oai
- openai#27856 [codex] package Windows symbols in parallel @tamird
- openai#27976 [codex] make PathUri::from_abs_path infallible @anp-oai
- openai#27854 [codex] parallelize Windows package archives @tamird
- openai#27853 [codex] stage npm packages concurrently @tamird
- openai#27710 [codex] add latency tracing spans @rphilizaire-openai
- openai#27510 [3 of 3] Support images in TUI goals @etraut-openai
- openai#27925 feat(tui): reland token activity command @fcoury-oai
- openai#27988 [codex] Limit app-based plugin suggestions to remote catalogs @xl-openai
- openai#27652 [codex] Add auth mode to plugin manager constructor @felixxia-oai
- openai#27964 [codex] Add hermetic Wine test support @anp-oai
- openai#27459 [codex] Gate plugin MCP servers by auth route @felixxia-oai
- openai#27961 feat(app-server): enforce managed remote control disable @apanasenko-oai
- openai#27937 [codex] Add hermetic Wine exec-server test @anp-oai
- openai#27996 [codex] Send request-scoped turn state over WebSocket @aibrahim-oai
- openai#28002 [codex] Send turn state through compact requests @aibrahim-oai
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.