mirror of
https://github.com/openai/codex.git
synced 2026-10-21 17:48:44 +00:00
rust-v0.129.0
6249
Commits
| Author | SHA1 | Message | Date | |
|---|---|---|---|---|
|
|
2808a4deb1 |
## New Features
- The TUI now supports modal Vim editing in the composer, including `/vim`, default-mode config, and Vim-specific keymap contexts. (#18595) - TUI workflows are easier to resume and copy from with a redesigned resume/fork picker, raw scrollback mode, `/ide` context injection, and workspace-aware `/diff`. (#20065, #20819, #20294, #21001) - The status line can show theme-aware colors plus optional PR and branch-change summaries, and `/keymap debug` helps inspect terminal key events. (#19631, #20892, #20794) - Plugin management now supports workspace sharing, share access controls, source filtering, local share path tracking, marketplace removal/upgrades, remote bundle sync, and admin-disabled status handling. (#20278, #21124, #21419, #20560, #19843, #20478, #20268, #20298) - Hooks can be browsed and toggled from `/hooks`, can run before/after compaction, and can add `PreToolUse` context; Codex Apps auth and eligible MCP elicitations now surface through TUI/Guardian flows. (#19882, #19905, #20692, #19193, #19431) - Experimental goals are now discoverable, stay paused across resume unless the user opts back in, and show clearer validation and multi-day duration output. (#20083, #20790, #20746, #20558) ## Bug Fixes - `/copy` works better in tmux, Alt+Enter and modified Delete/Backspace keys behave correctly, and Windows typing/paste latency was reduced. (#20207, #20535, #21058, #18914) - Large paste placeholders and Ctrl+C-stashed drafts now survive clear/editor workflows without corrupting draft history. (#21091, #21190, #21351, #21397) - TUI startup and accessibility were tightened by bounding terminal probes, clearing the first inline viewport render, and honoring `animations = false` for live rows. (#20654, #21450, #20564) - Linux sandbox startup is more reliable across older `bwrap`, slow mount probes, symlink-protected paths, and shared `/tmp` setups. (#20628, #20111, #21127, #21234) - Windows sandbox and exec policy now handle named pipes, ConPTY teardown, PowerShell-wrapped allow rules, worktree `safe.directory`, and unsafe Git options more reliably. (#20270, #20685, #20336, #21409, #21275) - Fixed custom CA login behind TLS-inspecting proxies, Bedrock runtime endpoint reporting, dangerous project config keys, heredoc redirect approval matching, and unbounded MCP/hook output growth. (#20676, #20275, #20098, #20113, #20260, #21069) ## Documentation - Updated the embedded OpenAI Docs sample skill so API-key setup guidance stays aligned with other docs variants. (#21263) - Documented how generated git commit attribution is gated by `codex_git_commit` and configured in `config.toml`. (#21379) - Removed local-only planning/spec docs and redirected config docs toward the maintained external documentation surface. (#20896) ## Chores - Linux releases now build, publish, bundle, and verify a standalone `bwrap` fallback for npm and DotSlash installs. (#21255, #21256, #21257, #21312, #21285) - Vendored Bubblewrap was updated to 0.11.2, including upstream security changes around setuid support. (#21389) - Windows Bazel CI now uses faster cross-compilation for tests, clippy, and release-build checks, and Bazel now runs sharded Rust integration tests. (#20585, #20701, #21057) - App-server and protocol internals were split and slimmed down, including transport extraction, protocol module decomposition, thread/message history moves, and tool-handler cleanup. (#20324, #20325, #20348, #20545, #21251, #21278, #21395) - Analytics and diagnostics coverage expanded for tool lifecycles, goals, plugin skills, thread sources, service tiers, and PR issue labeling. (#17089, #17090, #20799, #20923, #20949, #20969, #20893) ## Changelog Full Changelog: https://github.com/openai/codex/compare/rust-v0.128.0...rust-v0.129.0 - #20278 feat: Add workspace plugin sharing APIs @xl-openai - #20334 Make missing config clears no-ops @etraut-openai - #20246 Gate multi-agent v2 tools independently of collab @jif-oai - #20361 realtime: rename provider session ids @aibrahim-oai - #20260 fix(core): truncate large mcp tool outputs in rollouts @owenlin0 - #20083 Mark goals feature as experimental @etraut-openai - #19843 /plugins: remove marketplace @canvrno-oai - #20458 [Extension] Allowlist Chrome Extension in the tool_suggest tool @teddywyly-oai - #20324 Remove core protocol dependency [1/2] @etraut-openai - #20299 Move item event mapping into app-server-protocol @pakrym-oai - #20325 Remove core protocol dependency [2/2] @etraut-openai - #20471 Stop emitting item/fileChange/outputDelta output delta notifications @pakrym-oai - #20245 [Codex] Add browser use external feature flag @khoi-oai - #19882 Add /hooks browser for lifecycle hooks @abhinav-oai - #20275 fix: show correct Bedrock runtime endpoint in /status @celia-oai - #20270 [codex] Fix elevated Windows sandbox named-pipe access @iceweasel-oai - #20463 feat(rollouts): store EventMsg::ApplyPatchEnd in limited history mode @owenlin0 - #20101 install WFP filters for Windows sandbox setup @iceweasel-oai - #20474 [plugin] Add Canva to suggesteable list. @mzeng-openai - #20379 Send external import completion for sync imports @alexsong-oai - #19280 [codex] Migrate thread turns list to thread store @wiltzius-openai - #20348 Move plugin out of core. @xl-openai - #19160 Make apply_patch streaming parser stateful @akshaynathan - #20504 fix flaky test falls_back_to_registered_fallback_port_when_default_po… @owenlin0 - #20098 fix: ignore dangerous project-level config keys @owenlin0 - #20268 Sync remote installed plugin bundles @xli-oai - #20502 fix(tui): set persist_extended_history: false @owenlin0 - #20069 Bypass review for always-allow MCP tools in auto-review @maja-openai - #18595 feat(tui): add vim composer mode @fcoury-oai - #20267 Emit analytics for remote plugin installs @xli-oai - #20499 fix(app-server): mark thread/turns/list and exclude_turns as experime… @owenlin0 - #20522 Alias codex_hooks feature as hooks @abhinav-oai - #20336 execpolicy: unwrap PowerShell -Command wrappers on Windows @iceweasel-oai - #20113 fix(exec_policy) heredoc parsing file_redirect @dylan-hurd-oai - #20341 app-server: switch remote control to protocol v3 segmentation @euroelessar - #20300 [codex-analytics] centralize thread analytics state @rhan-oai - #20484 [codex] Improve PR babysitter CI diagnostics and guardrails @wiltzius-openai - #20298 Surface admin-disabled remote plugin status @xli-oai - #20511 [codex] Remove unused event messages @pakrym-oai - #19474 Make thread store process-scoped @wiltzius-openai - #20558 Format multi-day goal durations in the TUI @etraut-openai - #19631 Color TUI statusline from active theme @etraut-openai - #20265 Refresh remote plugin cache on auth changes @xli-oai - #20150 Add remote plugin skill read API @xli-oai - #20560 feat: Track local paths for shared plugins @xl-openai - #20600 chore: allow memories edition @jif-oai - #20602 feat: ad-hoc instructions @jif-oai - #20610 chore: improve remember prompt @jif-oai - #20606 feat: seed ad-hoc memory extension instructions @jif-oai - #20405 feat: export and replay effective config locks @jif-oai - #20540 Move apply-patch file changes into turn items @pakrym-oai - #20564 Enforce `animations = false` for screen readers @etraut-openai - #20523 Remove no-tool goal continuation suppression @etraut-openai - #20627 fix: cargo deny @jif-oai - #20545 app-server: move transport into dedicated crate @euroelessar - #20294 Add /ide context support to the TUI @etraut-openai - #20630 [codex] Add Codex environment config @pakrym-oai - #20524 deprecate legacy notify @abhinav-oai - #20486 [codex] Migrate loaded thread/read history to ThreadStore @wiltzius-openai - #20281 Use selected turn environments for runtime context @starr-openai - #20535 fix(tui): restore alt-enter newline alias @fcoury-oai - #20650 fix: reduce ConfigBuilder::build stack usage @jif-oai - #20478 /plugins: add marketplace upgrade flow @canvrno-oai - #20512 [codex] Emit image view as core item @pakrym-oai - #20562 Use the 2025-06-18 elicitation capability shape @abhinav-oai - #20674 Clear live hook rows when turns finalize @abhinav-oai - #20646 Surface multi-environment choices in environment context @starr-openai - #20542 Prune unused code-mode globals @cconger - #20585 ci: cross-compile Windows Bazel tests @bolinfest - #20701 ci: cross-compile Windows Bazel clippy @bolinfest - #20676 Fix custom CA login behind TLS-inspecting proxies @jgershen-oai - #20654 fix(tui): bound startup terminal probes @fcoury-oai - #20566 [tool_suggest] More prompt polishes. @mzeng-openai - #20751 Bound websocket request sends with idle timeout @pakrym-oai - #20893 [codex] Add issue labeler area labels @etraut-openai - #20896 Remove local docs and specs @etraut-openai - #20897 [codex] Refactor app-server dispatch result flow @pakrym-oai - #20677 [codex] Emit MCP tool calls as turn items @pakrym-oai - #20973 feat: support template interpolation in multi-agent usage hints @jif-oai - #20622 feat: memories mcp v1 @jif-oai - #20773 feat: add remote compaction v2 Responses client path @jif-oai - #20986 feat: add line offsets to memory read MCP @jif-oai - #20991 feat: add max_lines to memories MCP read @jif-oai - #20993 feat: paginate MCP memories list @jif-oai - #20994 feat: make memories MCP list shallow @jif-oai - #20996 feat: paginate memories MCP search results @jif-oai - #20997 feat: add context lines to memories MCP search @jif-oai - #20998 nit: renaming @jif-oai - #21004 feat: support multi-query memories search @jif-oai - #21006 nit: legacy @jif-oai - #20815 Speed up /side parent restore replay @etraut-openai - #20790 Keep paused goals paused on thread resume @etraut-openai - #20940 [codex] Split app-server request processors @pakrym-oai - #21023 typo @jif-oai - #21012 memories/mcp: generate tool schemas with schemars @jif-oai - #21010 memories-mcp: reject symlink traversal in local backend @jif-oai - #20989 core: share responses request builder with compact requests @jif-oai - #20853 [mcp-apps] Persist MCP Apps specific tool call end event. @mzeng-openai - #20750 Unify skip-review handling for approval_mode = "approve" @mzeng-openai - #20682 feat(app-server): always return limited thread history @owenlin0 - #20628 fix(linux-sandbox): fall back when system bwrap lacks perms @viyatb-oai - #20794 feat(tui): add keymap debug inspector @fcoury-oai - #21034 tui: retire /approvals and rename /autoreview to /approve @won-openai - #20669 Prepare selected environment plumbing @starr-openai - #20685 Fix Windows PTY teardown by preserving ConPTY ownership @iceweasel-oai - #20663 Add stdio exec-server listener @starr-openai - #20561 state: pass state db handles through consumers @euroelessar - #21054 rollout: store web search and mcp tool calls @owenlin0 - #20892 feat(tui): add PR summary statusline items @fcoury-oai - #20798 feat(tui): improve TUI keymap coverage @fcoury-oai - #21053 Use MCP server instructions in deferred namespace descriptions @sayan-oai - #21026 core: preserve last model ids in feedback tags @sayan-oai - #21060 core: fix apply_patch request permissions test @bolinfest - #20060 Add reasoning effort to turn tracing spans @charley-openai - #21058 fix(tui): support modified backspace/delete keys @fcoury-oai - #21057 bazel: run sharded rust integration tests @bolinfest - #18914 fix(tui): use shared paste burst interval on Windows @fcoury-oai - #20715 Make realtime sideband startup async @kmeelu-oai - #20514 [codex-analytics] add item lifecycle timing @rhan-oai - #20722 Remove remote plugin uninstall prefix gate @xli-oai - #19040 [codex] Add unsandboxed process exec API @euroelessar - #21105 [network-proxy] Cover DNS timeout blocking @evawong-oai - #21059 Rename agent identity login surface to access token @shijie-oai - #20576 codex: route metadata updates through ThreadStore @wiltzius-openai - #20923 Add plugin ID to skill analytics @alexsong-oai - #21122 Add turn_id to Codex skill invocation analytics @edwardysun3 - #20575 codex: migrate (more) app-server thread history reads to ThreadStore @wiltzius-openai - #21069 Spill large hook outputs from context @abhinav-oai - #20969 1- Add model service tiers metadata @aibrahim-oai - #21170 tools: remove unused experimental `list_dir` tool @jif-oai - #21201 memories-mcp: hide dot paths from list, read, and search @jif-oai - #21204 feat: support windowed multi-query memory search @jif-oai - #21205 feat: add normalized matching to memory search @jif-oai - #20207 fix(tui): make /copy work inside tmux without passthrough @fcoury-oai - #20799 Add goal lifecycle metrics @etraut-openai - #20746 Validate /goal objective length in TUI @etraut-openai - #20708 Add Windows sandbox readiness RPC @iceweasel-oai - #20692 Support PreToolUse additionalContext @abhinav-oai - #21091 [codex] Fix TUI large paste placeholder numbering after Ctrl+C @canvrno-oai - #21089 [codex] Fix fork --last cwd filtering @canvrno-oai - #21152 revert legacy notify deprecation @abhinav-oai - #21190 fix(tui): external editor expansion for same-size large pastes @fcoury-oai - #20111 fix(sandboxing): Bound advisory system bwrap startup probe @viyatb-oai - #21220 chore: add minimal proxy egress diagnostics @viyatb-oai - #20819 feat(tui): add raw scrollback mode @fcoury-oai - #21225 app-server: ignore persist_extended_history param @owenlin0 - #17089 [codex-analytics] add tool item event schemas @rhan-oai - #20647 Route process tools to selected environments @starr-openai - #20321 hook trust metadata and enforcement @abhinav-oai - #21221 [codex] Use shared app-server JSON-RPC error helpers @pakrym-oai - #21063 add turn items view to app-server turns @rhan-oai - #21001 feat(tui): route /diff through workspace commands @fcoury-oai - #20065 feat(tui): redesign session picker @fcoury-oai - #21127 fix(linux-sandbox): avoid panic on bwrap build failures @viyatb-oai - #21234 fix(linux-sandbox): isolate Linux sandbox synthetic mount registry per user for shared codex use case @viyatb-oai - #20687 [codex] Split tool handlers by tool name @pakrym-oai - #21113 Auto-deny MCP elicitations for Xcode 26.4 clients @etraut-openai - #21243 [codex] fix TUI turn items view fixtures @fcoury-oai - #21146 Enable V8 sandboxing for source-built builds @cconger - #20689 Inject state DB, agent graph store @rasmusrygaard - #19575 Add cloud executor registration to exec-server @miz-openai - #20577 codex: use ThreadStore history for core review forks @wiltzius-openai - #21261 fix build @bolinfest - #21251 chore(app-server-protocol): split v2 API definitions into modules @owenlin0 - #21259 ci: trigger rusty-v8 releases from tags @cconger - #21255 linux-sandbox: use standalone bundled bwrap @bolinfest - #21256 release: publish standalone bwrap artifacts @bolinfest - #21260 [codex] Move thread naming to app server @pakrym-oai - #21219 Add model and reasoning effort to MCP turn metadata @mchen-oai - #21275 Share Git safe-command logic on Windows @iceweasel-oai - #21257 release/npm: bundle standalone bwrap on Linux @bolinfest - #21276 [codex] Remove unused ListModels op @pakrym-oai - #21282 [codex] Remove legacy ListSkills op @pakrym-oai - #21271 Expose plugin manifest keywords in app server @alfozan - #20949 [codex-analytics] rework thread_source for thread analytics @rhan-oai - #21124 feat: Add plugin share access controls @xl-openai - #20724 app-server: align dynamic tool identifiers with Responses API @eternal-openai - #21055 Preserve session MCP config on refresh @aaronl-openai - #21277 [mcp] Return Accept early per feedback. @mzeng-openai - #21285 fix(bwrap): emit libcap after standalone archive @viyatb-oai - #21312 release: bundle bwrap with Linux codex DotSlash artifact @bolinfest - #19193 Support Codex Apps auth elicitations @mzeng-openai - #20437 feat: add `session_id` @jif-oai - #21328 test: isolate app-server-client in-process test state @jif-oai - #21329 feat: include thread ID in MCP turn metadata @jif-oai - #21332 feat: return session ID from thread/fork @jif-oai - #21337 Revert "feat: support template interpolation in multi-agent usage hints" @jif-oai - #21249 Propagate cache key and service tiers in compact @aibrahim-oai - #21182 Move installation ID resolution out of core startup @jif-oai - #21214 chore: spawn MCP for memories @jif-oai - #21336 feat(app-server): move v2 `sessionId` onto `Thread` @jif-oai - #21350 [codex] fix builtin MCP Windows path test @jif-oai - #20971 2- Use string service tiers in session protocol @aibrahim-oai - #21278 Move message history out of core @pakrym-oai - #21284 [codex] Add response.processed websocket request @pakrym-oai - #21367 rollout: coalesce thread updated_at touches @jif-oai - #21378 feat: move auto vaccum @jif-oai - #21263 [codex] Coordinate OpenAI docs sample with API key setup @mifan-oai - #21351 fix(tui): keep Ctrl-C stashed drafts after /clear @fcoury-oai - #21389 vendor: update bubblewrap to 0.11.2 @bolinfest - #21281 Remove core MCP list tools op @pakrym-oai - #21381 [codex] Handle git pagination flags by position @iceweasel-oai - #21397 fix(tui): persist ctrl-c draft via app event @fcoury-oai - #19431 Route opted-in MCP elicitations through Guardian @cd-oai - #21107 Avoid noisy OTEL diagnostics in codex exec @cpaasch-oai - #21390 Avoid hard-coded environment context shell @starr-openai - #21090 [codex] Dedupe fallback model metadata warnings @canvrno-oai - #21395 [codex] Split tool handlers into separate files @pakrym-oai - #21401 [codex-tui] pass thread source for tui threads @rhan-oai - #17090 [codex-analytics] emit tool item events from item lifecycle @rhan-oai - #21409 [codex] Fix Windows sandbox git safe.directory for worktrees @iceweasel-oai - #21379 Document Codex git commit attribution config @henzelmann-oai - #21287 Move skills watcher to app-server @pakrym-oai - #21416 [codex] Move tool specs into core handlers @pakrym-oai - #21419 feat: Add marketplace source filtering and plugin share context @xl-openai - #19905 Add compact lifecycle hooks (started by vincentkoc - external contrib) @eternal-openai - #21460 Revert "Move skills watcher to app-server" @pakrym-oai - #21450 fix(tui): clear first inline viewport render @fcoury-oai - #21427 [codex] Delete tool handler plan indirection @pakrym-oai - #21423 [codex] Add OpenAI Developers to tool suggest allowlist @mifan-oai - #21340 [codex] allow shared config reads in app-server queue @xli-oai - #21441 [codex] Parallelize skills list cwd loading @xli-oai - #21481 Revert state DB injection and agent graph store @pakrym-oairust-v0.129.0 |
||
|
|
a8488fec5e |
Revert state DB injection and agent graph store (#21481)
## Why Reverts #20689 to restore the previous optional state DB plumbing. The conflict resolution keeps the newer installation ID and session/thread identity changes that landed after #20689, while removing the mandatory state DB and agent graph store dependency from ThreadManager construction. ## What changed - Restored `Option<StateDbHandle>` through app-server, MCP server, prompt debug, and test entry points. - Removed the `codex-core` dependency on `codex-agent-graph-store` and reverted descendant lookup back to the existing state DB path when available. - Kept newer `installation_id` forwarding by passing it beside the optional DB handle. - Kept local thread-name updates working when the optional state DB handle is absent. ## Validation - `git diff --check` - `cargo test -p codex-thread-store` - `cargo test -p codex-state -p codex-rollout -p codex-app-server-protocol` - Attempted `env CARGO_INCREMENTAL=0 cargo test -p codex-core -p codex-app-server -p codex-app-server-client -p codex-mcp-server -p codex-thread-manager-sample -p codex-tui`; blocked locally by a rustc ICE while compiling `v8 v146.4.0` with `rustc 1.93.0 (254b59607 2026-01-19)` on `aarch64-apple-darwin`. |
||
|
|
5bc33fe31f |
[codex] Parallelize skills list cwd loading (#21441)
## Summary - process `skills/list` cwd entries with bounded concurrency of 5 - preserve the caller's requested cwd order in the response - add coverage that verifies response ordering remains stable ## Why Cold-start desktop traces showed that `skills/list` can dominate the shared config queue when it scans many workspace roots serially. The expensive work is largely independent per cwd, so the request was paying the sum of all cwd costs instead of the cost of the slowest bounded batch. ## Impact This keeps current request semantics intact while reducing the wall-clock time of large multi-root `skills/list` calls. That should also reduce how long later config-family requests, such as `plugin/list`, wait behind `skills/list` during startup. ## Validation - `just fmt` - `cargo test -p codex-app-server` - `cargo test -p codex-app-server skills_list_preserves_requested_cwd_order` |
||
|
|
05cd5c313e |
[codex] allow shared config reads in app-server queue (#21340)
## Summary - add a shared-read serialization mode for global app-server request families - let consecutive leading shared reads for the same family run together while keeping exclusive requests ordered - mark only `skills/list`, `config/read` and `plugin/list` as shared reads for now ## Why `skills/list` and `plugin/list` are read-only config-family requests, but the app-server queue currently treats every config request as exclusive. That means one long `skills/list` can make a later `plugin/list` wait even though the two requests do not mutate config. This change keeps the existing queue order but lets adjacent reads overlap. If a write is already waiting, later reads still stay behind it, so writes do not starve. ## Scope This intentionally keeps the first pass narrow: - shared reads: `skills/list`, `plugin/list` - still exclusive: `plugin/install`, `marketplace/*`, `skills/config/write`, `config/*write`, `config/read`, and the rest of the config family ## Validation - `just fmt` - `cargo test -p codex-app-server-protocol` - `cargo test -p codex-app-server` - `just fix -p codex-app-server-protocol` - `just fix -p codex-app-server` ## Desktop verification I ran the dev desktop app against this branch's built binary with the existing UI timing logs enabled. The app did use `/Users/xli/code/codex_6/codex-rs/target/debug/codex`. The new scheduler behavior works, but this narrow change does not remove every cold-start delay: in the observed trace, an earlier exclusive `config/read` was already queued ahead of the later `skills/list` and `plugin/list` requests, so the page-open plugin requests still waited behind that earlier exclusive config-family request before they could run together. That means this PR is the scheduler primitive needed for shared reads, not the complete end-to-end latency fix by itself. ## Not run - full workspace test suite, because repo policy requires explicit approval before running it after touching `app-server-protocol` |
||
|
|
001363188a |
[codex] Add OpenAI Developers to tool suggest allowlist (#21423)
## Summary Add `openai-developers@openai-curated` to `TOOL_SUGGEST_DISCOVERABLE_PLUGIN_ALLOWLIST` so the OpenAI Developers plugin can be surfaced through tool suggestions once it is available in the Built by OpenAI marketplace. Update the discoverable plugin test fixture to assert the plugin is returned from the curated marketplace allowlist path. ## Validation - `cargo fmt --check` passed; rustfmt emitted the existing stable-channel warnings about `imports_granularity`. - `cargo test -p codex-core list_tool_suggest_discoverable_plugins_returns_uninstalled_curated_plugins` passed. |
||
|
|
e394625ea2 |
[codex] Delete tool handler plan indirection (#21427)
## Why The spec split in the parent PR still left an intermediate registry plan that recorded `ToolHandlerKind` values and translated them into concrete handlers later. That kept tool registration dependent on static enum bookkeeping instead of registering handlers from the same code that assembles their specs. ## What Changed - Make `build_tool_registry_builder` register concrete handlers directly while adding specs. - Add small `ToolRegistryBuilder` helpers for spec augmentation and nested code-mode inspection. - Remove `ToolHandlerKind`, `ToolHandlerSpec`, and `ToolRegistryPlan`. - Update spec-plan tests to assert against the built `ToolRegistry` instead of static handler descriptors. ## Validation - `cargo check -p codex-core` - `cargo test -p codex-core tools::spec_plan::tests` - `cargo test -p codex-core tools::spec::tests` - `just fix -p codex-core` |
||
|
|
5a4b2702f2 |
fix(tui): clear first inline viewport render (#21450)
## Why The alpha TUI can render the initial trust-directory prompt with stale terminal text showing through spaces when startup begins below existing shell output. The first inline viewport transition can happen while the previous viewport is still empty, so the old clear path no-ops before Ratatui draws the prompt. Ratatui then skips blank cells because its previous buffer also thinks those cells are blank, leaving old terminal contents visible inside the prompt. ## What Changed - Clear from the new inline viewport top when the previous viewport is empty during a viewport transition. - Keep the existing clear-from-old-viewport behavior for normal viewport updates. - Add a VT100-backed regression test that pre-fills terminal contents, performs the first viewport clear, and verifies stale text inside the new viewport is removed while shell content above the viewport remains. ## How to Test 1. Start Codex alpha in a terminal that already has visible shell output above the cursor. 2. Use a fresh untrusted project directory so the trust-directory prompt appears. 3. Confirm the prompt text renders cleanly, with spaces staying blank instead of showing fragments of previous shell output. 4. As a regression check, confirm content above the inline viewport is still preserved in terminal scrollback. Targeted tests: - `cargo test -p codex-tui first_viewport_change_clears_from_new_viewport_when_old_viewport_is_empty -- --nocapture` - `cargo test -p codex-tui` |
||
|
|
103dc2b6ae |
Revert "Move skills watcher to app-server" (#21460)
Reverts openai/codex#21287 |
||
|
|
527d52df03 |
Add compact lifecycle hooks (started by vincentkoc - external contrib) (#19905)
Based on work from Vincent K - https://github.com/openai/codex/pull/19060 <img width="1836" height="642" alt="CleanShot 2026-04-29 at 20 47 40@2x" src="https://github.com/user-attachments/assets/b647bb89-65fe-40c8-80b0-7a6b7c984634" /> ## Why Compaction rewrites the conversation context that future model turns receive, but hooks currently have no deterministic lifecycle point around that rewrite. This adds compact lifecycle hooks so users can audit manual and automatic compaction, surface hook messages in the UI, and run post-compaction follow-up without overloading tool or prompt hooks. ## What Changed - Added `PreCompact` and `PostCompact` hook events across hook config, discovery, dispatch, generated schemas, app-server notifications, analytics, and TUI hook rendering. - Added trigger matching for compact hooks with the documented `manual` and `auto` matcher values. - Wired `PreCompact` before both local and remote compaction, and `PostCompact` after successful local or remote compaction. - Kept compact hook command input to lifecycle metadata: session id, Codex turn id, transcript path, cwd, hook event name, model, and trigger. - Made compact stdout handling consistent with other hooks: plain stdout is ignored as debug output, while malformed JSON-looking stdout is reported as failed hook output. - Added integration coverage for compact hook dispatch, trigger matching, post-compact execution, and the audited behavior that `decision:"block"` does not block compaction. ## Out of Scope - Hook-specific compaction blocking is not implemented; `decision:"block"` and exit-code-2 blocking semantics are intentionally unsupported for `PreCompact`. - Custom compaction instructions are not exposed to compact hooks in this PR. - Compact summaries, summary character counts, and summary previews are not exposed to compact hooks in this PR. ## Verification - `cargo test -p codex-hooks` - `cargo test -p codex-core manual_pre_compact_block_decision_does_not_block_compaction` - `cargo test -p codex-app-server hooks_list` - `cargo test -p codex-core config_schema_matches_fixture` - `cargo test -p codex-tui hooks_browser` ## Docs The developer documentation for Codex hooks should be updated alongside this feature to document `PreCompact` and `PostCompact`, the `manual`/`auto` matcher values, and the compact hook payload fields. --------- Co-authored-by: Vincent Koc <vincentkoc@ieee.org> |
||
|
|
11106016ff |
feat: Add marketplace source filtering and plugin share context (#21419)
Adds marketplaceKinds to plugin/list for local, workspace-directory, and shared-with-me; omitted params keep default local plus gated global behavior, while explicit kinds are exact. Exposes shareContext on plugin summaries from local share mappings and remote workspace/shared responses, including remotePluginId and nullable creator metadata. Adds shared-with-me listing through /ps/plugins/workspace/shared, renames the workspace remote namespace to workspace-directory, and keeps direct remote read/share/install/update/delete paths gated by plugins rather than remote_plugin. |
||
|
|
9417cf9696 |
[codex] Move tool specs into core handlers (#21416)
## Why This is the first mechanical slice of moving tool spec ownership toward the handlers. `codex-tools` should keep shared primitives and conversion helpers, while builtin tool specs and registration planning live in `codex-core` with the handlers that own those tools. Keeping this PR to relocation and import updates isolates the copy/move review from the later logic change that wires specs through registered handlers. ## What changed - Moved builtin tool spec constructors from `codex-rs/tools/src` into `codex-rs/core/src/tools/handlers/*_spec.rs` or nearby core tool modules. - Moved the registry planning code into `codex-rs/core/src/tools/spec_plan.rs` and its associated types/tests into core. - Kept shared primitives in `codex-tools`, including `ToolSpec`, schema/types, discovery/config primitives, dynamic/MCP conversion helpers, and code-mode collection helpers. - Updated handlers that referenced moved argument types or tool-name constants to use the core spec modules. - Moved spec tests next to the moved spec modules. ## Verification - `cargo check -p codex-tools` - `cargo check -p codex-core` - `cargo test -p codex-tools` - `cargo test -p codex-core _spec::tests` - `cargo test -p codex-core tools::spec_plan::tests` - `just fix -p codex-tools` - `just fix -p codex-core` Note: I also tried the broader `cargo test -p codex-core tools::`; it reached the moved spec-plan/spec tests successfully, then aborted with a stack overflow in `tools::handlers::multi_agents::tests::tool_handlers_cascade_close_and_resume_and_keep_explicitly_closed_subtrees_closed`, which is outside this spec relocation. |
||
|
|
d5eea229cc |
Move skills watcher to app-server (#21287)
## Why Skills update notifications are app-server API behavior, but the watcher lived in `codex-core` and surfaced through `EventMsg::SkillsUpdateAvailable`. Moving the watcher out keeps core focused on thread execution and lets app-server own both cache invalidation and the `skills/changed` notification. ## What changed - Added an app-server-owned skills watcher that watches local skill roots, clears the shared skills cache, and emits `skills/changed` directly. - Registers skill watches from the common app-server thread listener attach path, including direct starts, resumes, and app-server-observed child or forked threads. - Stores the `WatchRegistration` on `ThreadState`, so listener replacement, thread teardown, idle unload, and app-server shutdown deregister by dropping the RAII guard. - Removed `EventMsg::SkillsUpdateAvailable`, the core watcher, and the old core live-reload test. - Extended the app-server skills change test to verify a cached skills list is refreshed after a filesystem change without forcing reload. ## Validation - `cargo check -p codex-core -p codex-app-server -p codex-mcp-server -p codex-rollout -p codex-rollout-trace` - `cargo test -p codex-app-server skills_changed_notification_is_emitted_after_skill_change` |
||
|
|
8f5d68f9d2 |
Document Codex git commit attribution config (#21379)
## Summary - document that commit attribution for generated git commit messages is gated by the `codex_git_commit` feature flag - add an example `config.toml` snippet showing `commit_attribution` with `[features].codex_git_commit = true` - update the config schema description so the reference docs explain that `commit_attribution` only takes effect when the feature is enabled Fixes #19799. ## Validation - `cargo run -p codex-core --bin codex-write-config-schema` - `cargo test -p codex-config` - `cargo test -p codex-features` - `cargo fmt --check` - `git diff --check` ## Notes - `cargo test -p codex-core config_schema_matches_fixture` currently fails before reaching the schema test because `core_test_support` imports `similar` without a linked crate in this checkout. The narrower package checks above avoid that unrelated test-support build failure. |
||
|
|
123e78b97b |
[codex] Fix Windows sandbox git safe.directory for worktrees (#21409)
## Why Windows sandboxed commands run as a sandbox user, while workspace repositories are usually owned by the real user. The sandbox compensates by injecting a temporary Git `safe.directory` entry into the child environment. That injection was still broken for linked worktrees because the helper followed the `.git` file's `gitdir:` pointer and injected the internal `.git/worktrees/...` location. Git's dubious-ownership check expects the worktree root instead, so sandboxed Git commands still failed in worktree-based Codex checkouts. ## What changed - Treat any `.git` marker, directory or file, as the worktree root for `safe.directory` injection. - Keep the safe-directory logic in `windows-sandbox-rs/src/sandbox_utils.rs` and have the one-shot elevated path reuse it. - Add regression coverage for both normal `.git` directories and gitfile-based worktrees. ## Validation - `cargo test -p codex-windows-sandbox sandbox_utils::tests` - `cargo test -p codex-windows-sandbox` built and ran; the new `sandbox_utils` tests passed, while two pre-existing legacy sandbox tests failed locally with `Access is denied`: `session::tests::legacy_non_tty_cmd_emits_output` and `spawn_prep::tests::legacy_spawn_env_applies_offline_network_rewrite`. |
||
|
|
fbdbc6b2fe |
[codex-analytics] emit tool item events from item lifecycle (#17090)
## Why After the tool-item schemas are in place, analytics needs to emit them from the app-server item lifecycle rather than requiring bespoke tracking at each callsite. The reducer should also reuse the shared thread analytics context introduced below it in the stack so later event families do not repeat the same reducer joins or missing-state ladder. ## What changed - Tracks tool-item completion notifications and emits the matching tool analytics event when a terminal item arrives. - Derives event-specific payload details for command execution, file changes, MCP calls, dynamic tools, collaboration tools, web search, and image generation. - Denormalizes thread, app-server client, runtime, and subagent provenance metadata through the shared thread analytics context. - Adds reducer coverage for item lifecycle emission and subagent metadata inheritance. ## Duration semantics `duration_ms` is computed from the app-server item lifecycle timestamps: `completed_at_ms - started_at_ms`. That makes it the duration of the lifecycle Codex observed locally, not necessarily the upstream provider's full execution time. - Web search usually has a meaningful observed lifecycle because Responses can send `response.output_item.added` before `response.output_item.done`; in that case `started_at_ms` comes from the added event and `completed_at_ms` comes from the done event. - Image generation can be much less precise. In the current observed stream, image generation often arrives only as a completed `response.output_item.done`; when there is no earlier added event, Codex synthesizes the started item immediately before completion, so `duration_ms` can be `0` even though upstream image generation took longer. - Standalone web search and standalone image generation work is expected to land after this stack. Those paths may introduce more direct lifecycle events or timing points, so the current web-search/image-generation duration semantics should be treated as the best available item-lifecycle approximation, not the final latency contract for those tool families. - `execution_duration_ms` is populated only where the completed item already carries a native execution duration; otherwise it remains `null` while `duration_ms` still reflects the local lifecycle interval. ## Currently placeholder / partial fields Some fields are included in the schema for the intended steady-state contract, but this PR does not yet populate them from real approval/review state: - `review_count`, `guardian_review_count`, and `user_review_count` currently default to `0`. - `final_approval_outcome` currently defaults to `unknown`. - `requested_additional_permissions` and `requested_network_access` currently default to `false`. ## Verification - `cargo test -p codex-analytics` --- [//]: # (BEGIN SAPLING FOOTER) Stack created with [Sapling](https://sapling-scm.com). Best reviewed with [ReviewStack](https://reviewstack.dev/openai/codex/pull/17090). * #18748 * #18747 * __->__ #17090 * #17089 * #20514 |
||
|
|
21295f47e2 |
[codex-tui] pass thread source for tui threads (#21401)
## Summary - mark TUI-created thread starts and forks with explicit `thread_source = user` - add focused coverage for embedded and remote lifecycle request builders ## Why Thread analytics now consume an explicit thread-level source classification instead of inferring it from `session_source`. The TUI still omitted that field, so TUI-created interactive threads would continue to land as `null` even after the new analytics plumbing shipped. ## Validation - `cargo test -p codex-tui app_server_session --lib` |
||
|
|
b9c50a53d7 |
[codex] Split tool handlers into separate files (#21395)
## Why Several tool handler modules still bundled multiple `ToolHandler` implementations in one file. That made the handler directory harder to navigate and made otherwise local handler edits land in large shared modules. ## What - Split grouped tool handlers into one handler file each for agent jobs, goals, MCP resources, shell tools, and unified exec. - Kept shared parsing, payload, and runtime helpers in the existing parent modules, with re-exports preserving the existing handler import paths. - Updated the shell handler tests to construct `ShellCommandHandler` through the existing `ShellCommandBackendConfig` conversion now that the backend detail lives with the shell-command handler. ## Validation - `cargo check -p codex-core` - `cargo clippy -p codex-core --lib -- -D warnings` - `git diff --check -- codex-rs/core/src/tools/handlers` Targeted `codex-core` handler tests did not run locally because `core_test_support` currently fails to compile before reaching these tests due to an unresolved `similar` import. |
||
|
|
d5f0b6d63a |
[codex] Dedupe fallback model metadata warnings (#21090)
Fixes #21070. This is a small cleanup around model metadata handling for gateway/provider model names. It follows the report and proposed direction from @dkbush by keeping the fallback metadata warning useful without repeating it every turn, and by tightening the existing provider-prefix lookup path. - Track fallback metadata warning slugs in session state so each unresolved model warns once per session. - Keep warning emission outside the session-state lock and preserve the existing warning text. - Allow one-segment provider prefixes with hyphenated provider IDs, while preserving the multi-segment rejection behavior. - Add focused coverage for warning dedupe and hyphenated provider-prefix metadata matching. Testing: - Ran `just fmt`. - Ran `git diff --check`. - Added tests for the new warning dedupe and provider-prefix lookup behavior. |
||
|
|
63a27ad6c6 |
Avoid hard-coded environment context shell (#21390)
## Summary - make resolved turn environment shell metadata optional instead of hard-coding bash - render environment context shells from explicit environment metadata when present, falling back to the existing session shell - update environment context tests for inherited PowerShell-style fallback and explicit per-environment shell override ## Testing - Not run (not requested; formatted with `just fmt`). Co-authored-by: Codex <noreply@openai.com> |
||
|
|
f9063045e1 |
Avoid noisy OTEL diagnostics in codex exec (#21107)
`codex exec` should not print OpenTelemetry exporter self-diagnostics to stderr by default. Suppress the SDK and OTLP exporter targets unless callers explicitly opt in with `RUST_LOG`. Also stop defaulting the trace exporter to the log exporter, since OTLP HTTP endpoints are signal-specific and a logs endpoint is not valid for spans. Co-authored-by: Codex <noreply@openai.com> Co-authored-by: Codex <noreply@openai.com> |
||
|
|
346070a424 |
Route opted-in MCP elicitations through Guardian (#19431)
# Motivation Browser Use origin-access prompts are MCP elicitations, not direct tool-call approval prompts, so they were bypassing the Guardian approval path. We need a generic opt-in that lets eligible MCP elicitations use Guardian when the current turn already routes approvals there. # Description Add a generic elicitation reviewer hook in codex-mcp and wire codex-core to pass a Guardian reviewer callback when creating the MCP connection manager. The reviewer validates explicit mcp_tool_call opt-in metadata, builds a Guardian MCP tool-call review request from server/tool/connector metadata and tool params, and maps Guardian approval, denial, timeout, and cancellation decisions back to MCP elicitation responses. The new option to trigger this in the `_meta` object is: ``` "codex_request_type": "approval_request", ``` # Testing - RUST_MIN_STACK=8388608 NEXTEST_STATUS_LEVEL=leak cargo nextest run --no-fail-fast --cargo-profile ci-test --test-threads 2 - cargo clippy --tests -- -D warnings - cargo fmt -- --config imports_granularity=Item --check - cargo shear - pnpm run format - python3 .github/scripts/verify_cargo_workspace_manifests.py - python3 .github/scripts/verify_tui_core_boundary.py - python3 .github/scripts/verify_bazel_clippy_lints.py - git diff --check |
||
|
|
6b7d6cafa0 |
fix(tui): persist ctrl-c draft via app event (#21397)
## Why The main branch started failing after #21351 merged because the merge commit kept calling `AppCommand::add_to_history` from `BottomPane::clear_composer_for_ctrl_c`, but main had already removed that helper as part of the history persistence refactor. The PR head passed because it was based on an older main commit where the helper still existed. This restores the Ctrl+C draft-stashing behavior using the current app-event path instead of the removed command helper. ## What Changed - Store the active `ThreadId` in `BottomPane` when history metadata is provided. - Emit `AppEvent::AppendMessageHistoryEntry` for Ctrl+C-cleared drafts. - Update the slash-clear regression test to assert the current history event shape. ## How to Test Targeted tests: - `cargo test -p codex-tui slash_clear_after_ctrl_c_keeps_stashed_draft_recallable` Broader local checks: - `just fix -p codex-tui` - `just argument-comment-lint -p codex-tui` - `git diff --check origin/main...HEAD` - `cargo test -p codex-tui` reached completion; the fixed test passed, and the only local failures were `status::tests::status_permissions_full_disk_managed_*`, blocked by this machine config rejecting `DangerFullAccess` via `/etc/codex/requirements.toml`. |
||
|
|
f32c496144 |
[codex] Handle git pagination flags by position (#21381)
## Why This is a follow-up to the Windows Git safe-command bypass fix for BUGB-15601. Git's global `--paginate` / `-p` flags can route output through a configured pager, so they should not be auto-approved as safe before the subcommand. At the same time, `-p` after read-only subcommands like `log`, `diff`, and `show` is the common patch-output flag, so treating every `-p` as unsafe would make ordinary read-only inspection commands prompt unnecessarily. ## What Changed - Split Git option safety matching into explicit global-option and subcommand-option lists. - Treat global `git --paginate ...` and `git -p ...` as unsafe. - Keep post-subcommand patch usage such as `git log -p`, `git diff -p`, and `git show -p HEAD` safe. - Keep the pagination coverage with the shared Git safe-command implementation rather than the Windows wrapper tests. - Remove the stale `git_global_option_requires_prompt` helper now that safe-command Git option matching owns the prompt-required lists. ## Testing - `cargo test -p codex-shell-command` |
||
|
|
712305be47 |
Remove core MCP list tools op (#21281)
## Why The core `Op::ListMcpTools` request path is no longer needed. Keeping it around left a dead request/response surface alongside the app-server MCP inventory APIs that own current server status listing. ## What Changed - Removed `Op::ListMcpTools`, `EventMsg::McpListToolsResponse`, and the core handler that built the MCP snapshot response. - Removed the now-unused `codex-mcp` snapshot wrapper/export and passive event handling arms in rollout and MCP-server consumers. - Updated tests that used the old op as a synchronization hook to wait on existing startup/skills events, and deleted the plugin test that only exercised the removed listing op. ## Validation - `cargo test -p codex-protocol` - `cargo test -p codex-mcp` - `cargo test -p codex-rollout -p codex-rollout-trace -p codex-mcp-server` - `cargo test -p codex-core --test all pending_input::queued_inter_agent_mail` - `cargo test -p codex-core --test all rmcp_client::stdio_mcp_tool_call_includes_sandbox_state_meta` - `cargo test -p codex-core --test all rmcp_client::stdio_image_responses` - `just fix -p codex-core -p codex-protocol -p codex-mcp -p codex-rollout -p codex-rollout-trace -p codex-mcp-server` |
||
|
|
123ec8b035 |
vendor: update bubblewrap to 0.11.2 (#21389)
## Why `codex-rs/vendor/bubblewrap` had fallen behind upstream, and upstream `v0.11.2` is the current Bubblewrap release. The release is a security update for `CVE-2026-41163`, affecting setuid Bubblewrap builds, and deprecates setuid support in favor of the default non-setuid build mode. ## What changed - Refreshed the vendored Bubblewrap sources under `codex-rs/vendor/bubblewrap` to upstream `v0.11.2`. - Brought in the upstream `-Dsupport_setuid` build option, which defaults setuid support off. - Updated vendored release notes and documentation files included with Bubblewrap. ## Verification Not run locally; this PR only refreshes the vendored upstream Bubblewrap source snapshot. Upstream release: https://github.com/containers/bubblewrap/releases/tag/v0.11.2 |
||
|
|
e97610cf3b |
fix(tui): keep Ctrl-C stashed drafts after /clear (#21351)
## Why When a user stashes a draft with Ctrl+C, then runs `/clear`, the fresh chat session loses the in-memory composer history that held the stashed draft. Pressing Up after `/clear` can then recall an older submitted prompt instead of the draft the user explicitly saved for later. ## What Changed - Record Ctrl+C-cleared composer text through the existing message history path, so it survives the fresh session created by `/clear`. - Keep `/clear` itself out of local slash-command recall so it does not sit ahead of the stashed draft. - Add regression coverage for the full flow: submit a prompt, stash a later draft with Ctrl+C, run `/clear`, then recall the stashed draft before the older prompt. ## How to Test 1. Start Codex with `just c`. 2. Submit a short prompt such as `ok` and wait for the turn to complete. 3. Type a new draft, press Ctrl+C, then run `/clear`. 4. Press Up and confirm the stashed draft is restored. 5. Press Up again and confirm the older submitted prompt is still reachable after the stashed draft. Targeted tests: - `cargo test -p codex-tui slash_clear_after_ctrl_c_keeps_stashed_draft_recallable` Manual verification: - Reproduced the issue in tmux with `RUST_LOG=trace just c -c log_dir=...`: before the fix, Up after `/clear` recalled the older submitted prompt. - Re-tested the same tmux flow after the fix: Up after `/clear` restored the Ctrl+C-stashed draft. |
||
|
|
f2f5d6f6c7 |
[codex] Coordinate OpenAI docs sample with API key setup (#21263)
## Summary - Add the same API key setup coordination guidance to the embedded OpenAI Docs sample skill in `codex-rs/skills`. - Keep the skill description/frontmatter unchanged; the coordination lives only in the body. - Preserve direct OpenAI Docs routing for docs-only questions, citations, model/API guidance, conceptual explanations, and non-building examples. ## Why The Codex repo carries its own OpenAI Docs skill variant under `codex-rs/skills/src/assets/samples`. This keeps that embedded sample aligned with the other OpenAI Docs variants patched in the related PRs. ## Validation - `cargo test -p codex-skills` - `git diff --check` |
||
|
|
ab43db44a2 |
feat: move auto vaccum (#21378)
The initial vaccum is not needed anymore. We can consider all the DBs have been reclaimed by now |
||
|
|
0e821b380a |
rollout: coalesce thread updated_at touches (#21367)
## Why Metadata-irrelevant rollout events currently refresh `threads.updated_at` on every flush. That keeps thread recency accurate, but it also turns high-frequency agent output into unnecessary SQLite writes. Recency only needs to advance periodically during an active session, while the final suppressed touch still needs to be persisted before shutdown. ## What changed - coalesce touch-only `updated_at` writes in the rollout writer, with a short production interval between persisted touches - retain the latest suppressed touch and flush it during shutdown so the thread is not left stale - extend rollout recorder coverage for coalesced touches, delayed refresh, shutdown flushing, and the existing missing-thread fallback path ## Verification - Added regression coverage in `rollout/src/recorder_tests.rs` for coalescing and shutdown flushing behavior. --------- Co-authored-by: Codex <noreply@openai.com> |
||
|
|
2070d5bfd3 |
[codex] Add response.processed websocket request (#21284)
## Summary - Add a `response.processed` websocket request payload and sender for Responses API websockets. - Send `response.processed` from `try_run_sampling_request` after a response completes, local turn processing succeeds, and the session-owned feature flag is enabled. - Add websocket coverage for both enabled and disabled feature-flag behavior. ## Validation - `just fmt` - `cargo test -p codex-core response_processed` - `cargo test -p codex-api responses_websocket` - `cargo test -p codex-features responses_websocket_response_processed_is_under_development` - `git diff --check` - `just fix -p codex-api -p codex-core -p codex-features` - `git diff --check origin/main...HEAD` |
||
|
|
2004173cd7 |
Move message history out of core (#21278)
## Why Message history was implemented inside `codex-core` and surfaced through core protocol ops and `SessionConfiguredEvent` fields even though the current consumer is TUI-local prompt recall. That made core own UI history persistence and exposed `history_log_id` / `history_entry_count` through surfaces that app-server and other clients do not need. This change moves message history persistence out of core and keeps the recall plumbing local to the TUI. ## What changed - Added a new `codex-message-history` crate for appending, looking up, trimming, and reading metadata from `history.jsonl`. - Removed core protocol history ops/events: `AddToHistory`, `GetHistoryEntryRequest`, and `GetHistoryEntryResponse`. - Removed `history_log_id` and `history_entry_count` from `SessionConfiguredEvent` and updated exec/MCP/test fixtures accordingly. - Updated the TUI to dispatch local app events for message-history append/lookup and keep its persistent-history metadata in TUI session state. ## Validation - `cargo test -p codex-message-history -p codex-protocol` - `cargo test -p codex-exec event_processor_with_json_output` - `cargo test -p codex-mcp-server outgoing_message` - `cargo test -p codex-tui` - `just fix -p codex-message-history -p codex-protocol -p codex-core -p codex-tui -p codex-exec -p codex-mcp-server` |
||
|
|
be1d3cff93 |
2- Use string service tiers in session protocol (#20971)
## Summary - break service tier session/op/app-server protocol fields from the closed enum to string tier ids - send the service tier string directly through model requests, prewarm, compaction, memories, and TUI/app-server turn starts - regenerate app-server protocol JSON/TypeScript schemas, removing the standalone ServiceTier TS enum ## Verification - just fmt - cargo check -p codex-core -p codex-app-server -p codex-tui - just write-app-server-schema --------- Co-authored-by: Codex <noreply@openai.com> |
||
|
|
ebd9ec05b4 |
[codex] fix builtin MCP Windows path test (#21350)
## Summary
- make the builtin MCP config test derive the expected `--codex-home`
argument from `AbsolutePathBuf`
## Why
`AbsolutePathBuf::try_from("/tmp/codex-home")` is rendered as
`D:\\tmp\\codex-home` on Windows, but the test asserted the Unix literal
`"/tmp/codex-home"`. That made the Windows Bazel job fail even though
the production code was behaving correctly.
## Impact
This keeps the test cross-platform while preserving the same transport
assertion on Unix and Windows.
## Validation
- `cargo test -p codex-builtin-mcps`
Co-authored-by: Codex <noreply@openai.com>
|
||
|
|
5ecff05196 |
feat(app-server): move v2 sessionId onto Thread (#21336)
## Why `session_id` and `thread_id` are separate identities after #20437, but app-server only surfaced `sessionId` on the `thread/start`, `thread/resume`, and `thread/fork` response envelopes. Other thread-bearing surfaces such as `thread/list`, `thread/read`, `thread/started`, `thread/rollback`, `thread/metadata/update`, and `thread/unarchive` either lacked the grouping key or forced clients to special-case those three responses. Making `sessionId` part of the reusable `Thread` payload gives every v2 API surface one place to expose session-tree identity. ## Mental model 1. thread.sessionId lives on `Thread` 2. It is a view/runtime identity for the current live session tree, not durable stored lineage metadata 3. When app-server has a live loaded thread, it copies the real value from core’s session_configured.session_id 4. When it only has stored/unloaded data, it falls back to thread.sessionId = thread.id ## What changed - Added `sessionId` to the v2 [`Thread`](https://github.com/openai/codex/blob/8fc9e9b4cf81b6f61d432e71f1eb266f6f104b63/codex-rs/app-server-protocol/src/protocol/v2/thread_data.rs#L105-L109). - Removed the duplicate top-level `sessionId` fields from `thread/start`, `thread/resume`, and `thread/fork`; clients should now read `response.thread.sessionId`. - Populated `thread.sessionId` when building live thread responses, replaying loaded threads, and returning stored-thread summaries so the field is present across start, resume, fork, list, read, rollback, metadata-update, unarchive, and `thread/started` paths. See [`load_thread_from_resume_source_or_send_internal`](https://github.com/openai/codex/blob/8fc9e9b4cf81b6f61d432e71f1eb266f6f104b63/codex-rs/app-server/src/request_processors/thread_processor.rs#L2824-L2918) and [`thread_from_stored_thread`](https://github.com/openai/codex/blob/8fc9e9b4cf81b6f61d432e71f1eb266f6f104b63/codex-rs/app-server/src/request_processors/thread_processor.rs#L3671-L3719). - Preserved the stored-thread fallback: if a thread has not been loaded into a live session tree yet, `thread.sessionId` falls back to `thread.id`; once the thread is live again, the field reports the active session tree root. - Regenerated the JSON/TypeScript schemas and updated the app-server README examples to show [`thread.sessionId`](https://github.com/openai/codex/blob/8fc9e9b4cf81b6f61d432e71f1eb266f6f104b63/codex-rs/app-server/README.md#L306-L310) on the thread object. |
||
|
|
ca257b6ce5 |
chore: spawn MCP for memories (#21214)
Co-authored-by: Codex <noreply@openai.com> |
||
|
|
8f3bb355f4 |
Move installation ID resolution out of core startup (#21182)
## Summary - resolve or inject the installation ID before core startup and pass it through `ThreadManager`, `CodexSpawnArgs`, and `Session` as a plain `String` - keep child sessions on the parent installation ID instead of rediscovering it inside core - propagate installation ID startup failures in `mcp-server` instead of panicking ## Why Core was still touching the filesystem on the session startup path to discover `installation_id`. This moves that work to the outer host boundary so core no longer depends on `codex_home` reads during session construction. --------- Co-authored-by: Codex <noreply@openai.com> |
||
|
|
5d6f23a27b |
Propagate cache key and service tiers in compact (#21249)
## Why `/responses/compact` should preserve the request-affinity fields that apply to the active auth mode. ChatGPT-auth compact requests need the effective `service_tier`, and compact requests for every auth mode need the stable `prompt_cache_key`, so compaction does not quietly lose routing or cache behavior that normal sampling already has. This follows the request-parity direction from #20719, but keeps the net change focused on the compact payload fields needed here. ## What changed - Add `service_tier` and `prompt_cache_key` to the compact endpoint input payload. - Build the remote compact payload from the existing responses request builder output so `Fast` still maps to `priority` when compact sends a service tier. - Pass the turn service tier into remote compaction, but only include it in compact payloads for ChatGPT-backed auth. - Keep `prompt_cache_key` on compact payloads for all auth modes. - Add request-body diff snapshot coverage in `core/tests/suite/compact_remote.rs` for: - API-key auth reusing `prompt_cache_key` while omitting `service_tier` even when `Fast` is configured. - ChatGPT auth reusing both `service_tier` and `prompt_cache_key`. - Drive the snapshot coverage through five varied turns: plain text, multi-part text, tool-call continuation, image+text input, local-shell continuation, and final-turn reasoning output. ## Verification - Added insta snapshots for compact request-body parity against the last normal `/responses` request after five varied turns. - Not run locally per repo guidance; relying on GitHub CI for test execution. --------- Co-authored-by: Codex <noreply@openai.com> |
||
|
|
cc84e6bc6d |
Revert "feat: support template interpolation in multi-agent usage hints" (#21337)
Reverts openai/codex#20973 |
||
|
|
06e5dfa4dd |
feat: return session ID from thread/fork (#21332)
## Why `thread/start` and `thread/resume` already return `sessionId`, but `thread/fork` only returned the new thread. That left clients to infer the forked thread's session identity from `thread.id`, which kept the new `session_id` / `thread_id` split implicit at one lifecycle boundary. Follow-up to #20437. ## What changed - Add `sessionId` to `ThreadForkResponse`. - Populate it from the forked session configuration. - Regenerate the v2 JSON/TypeScript schema fixtures and update the app-server docs/example. - Extend the fork integration test to assert the returned `sessionId`. ## Verification - Added coverage in `thread_fork_creates_new_thread_and_emits_started` for the new response field. |
||
|
|
fe24a180ab |
feat: include thread ID in MCP turn metadata (#21329)
## Why MCP tool calls already include `session_id` in `x-codex-turn-metadata`, but descendant threads intentionally share that value with the root thread. Consumers that need to correlate work at the concrete thread level also need the current `thread_id`. ## What changed - add `thread_id` to `x-codex-turn-metadata` while preserving `session_id` as the shared session identity - thread the two identities separately through normal turns and spawned review threads - add regression coverage for resumed sessions, reserved metadata fields, and deferred MCP tool calls ## Verification - added focused coverage in `core/src/session/tests.rs`, `core/src/turn_metadata_tests.rs`, and `core/tests/suite/search_tool.rs` |
||
|
|
b5e965e1d7 |
test: isolate app-server-client in-process test state (#21328)
## Why The in-process `app-server-client` tests were still building their configs from the ambient `codex_home` and letting the embedded app server create its own state DB when `state_db` was absent. That matters because in-process startup falls back to `init_state_db_from_config(...)` in that case, so tests can otherwise share persisted state instead of getting isolated fixtures: [`app-server/src/in_process.rs`](https://github.com/openai/codex/blob/a98623511ba433154ec811fc63091617f5945438/codex-rs/app-server/src/in_process.rs#L368-L373). ## What changed - Give each in-process test client its own temporary `codex_home`. - Initialize the matching state DB from that per-client config and pass it into the client explicitly. - Keep the temp directory alive for the lifetime of the test client through a small `TestClient` wrapper. - Add `tempfile` as a dev dependency for the new harness. The updated setup lives in [`app-server-client/src/lib.rs`](https://github.com/openai/codex/blob/35c1133d45d10931914dbb88a1246a195d025ff6/codex-rs/app-server-client/src/lib.rs#L982-L1055). ## Testing - Existing `codex-app-server-client` tests continue to exercise the updated in-process client path through the isolated helper. |
||
|
|
a98623511b |
feat: add session_id (#20437)
## Summary Related to https://openai.slack.com/archives/C095U48JNL9/p1777537279707449 TLDR: We update the meaning of session ids and thread ids: * thread_id stays as now * session_id become a shared id between every thread under a /root thread (i.e. every sub-agent share the same session id) This PR introduces an explicit `SessionId` and threads it through the protocol/client boundary so `session_id` and `thread_id` can diverge when they need to, while preserving compatibility for older serialized `session_configured` events. --------- Co-authored-by: Codex <noreply@openai.com> |
||
|
|
f9a907aebe |
Support Codex Apps auth elicitations (#19193)
## Summary - request URL-mode MCP elicitations when Codex Apps tool calls fail with connector auth metadata - route Codex Apps auth URL elicitations into the TUI app-link flow ## Test plan - `just fmt` - `cargo test -p codex-core mcp_tool_call::tests` - `cargo test -p codex-mcp` - `cargo test -p codex-tui bottom_pane::app_link_view::tests` - `just fix -p codex-core` - `just fix -p codex-mcp` - `just fix -p codex-tui` Also attempted broader local runs: - `cargo test -p codex-core` fails in unrelated config/request-permission/proxy-sensitive tests under the current Codex Desktop environment. - `cargo test -p codex-tui` fails in unrelated status snapshots/trust-default tests because the ambient environment renders workspace-write/network permission defaults. |
||
|
|
22326e263c |
release: bundle bwrap with Linux codex DotSlash artifact (#21312)
## Why #21255 changed the Linux sandbox fallback so Codex can use a bundled `codex-resources/bwrap` executable when no suitable system `bwrap` is available. That lookup is relative to the native Codex executable returned by `std::env::current_exe()`, as implemented in [`bundled_bwrap.rs`](https://github.com/openai/codex/blob/9766d3d51cec885114b6d6c53a02e9efbaf87171/codex-rs/linux-sandbox/src/bundled_bwrap.rs#L83-L93). The release already publishes a separate `bwrap` DotSlash output, but the Linux `codex` DotSlash output still pointed at a single-binary `.zst` payload. Running the `codex` DotSlash manifest only materializes the native `codex` executable; it does not also create sibling files from the separate `bwrap` manifest. The fallback path therefore needs the Linux `codex` DotSlash artifact itself to include the real `bwrap` executable at `codex-resources/bwrap`. ## What changed - stage a Linux primary `codex-<target>-bundle.tar.zst` release artifact containing `codex` and `codex-resources/bwrap` - point the Linux `codex` DotSlash outputs at that bundle tarball - leave the standalone `bwrap` DotSlash output in place for consumers that want to fetch `bwrap` directly ## Verification - `jq . .github/dotslash-config.json` - Ruby YAML parse of `.github/workflows/rust-release.yml` |
||
|
|
9766d3d51c |
fix(bwrap): emit libcap after standalone archive (#21285)
## Why #21255 added the standalone `codex-bwrap` binary. In the Cargo build, [`pkg_config::probe("libcap")`](https://github.com/openai/codex/blob/a736cb55a2bce57b4c8e5a4fe56f70c2b2ad892b/codex-rs/bwrap/build.rs#L37-L39) emits `-lcap` before [`cc::Build::compile("standalone_bwrap")`](https://github.com/openai/codex/blob/a736cb55a2bce57b4c8e5a4fe56f70c2b2ad892b/codex-rs/bwrap/build.rs#L50-L67) adds the static bwrap archive. The Linux musl link then sees `-lcap -lstandalone_bwrap`; because static archives are resolved left-to-right, `cap_from_name` is still undefined once `standalone_bwrap` introduces that reference. The musl setup already builds `libcap.a` and exposes it through [`libcap.pc`](https://github.com/openai/codex/blob/a736cb55a2bce57b4c8e5a4fe56f70c2b2ad892b/.github/scripts/install-musl-build-tools.sh#L78-L88), so the failure is link ordering rather than a missing dependency. ## What changed - probe `libcap` with `cargo_metadata(false)` so `pkg-config` does not emit its link flags early - emit the discovered `libcap` search paths and libraries after `standalone_bwrap` is compiled, preserving the needed static-link order ## Verification - `cargo test -p codex-bwrap` - `cargo clippy -p codex-bwrap --all-targets` The affected Linux musl release link is exercised by CI, which is the path this fix targets. |
||
|
|
41505bcea2 |
[mcp] Return Accept early per feedback. (#21277)
- [x] Return Accept early when auto_deny is enabled per feedback. |
||
|
|
9f06d171e2 |
Preserve session MCP config on refresh (#21055)
# Overview MCP refreshes were rebuilding active threads from fresh disk-backed config only, which dropped thread-start session overlays such as app-injected MCP servers. This keeps refreshes current with disk config while preserving the thread-local config that only the active thread knows about. # Changes - Rebuild refreshed config per active thread using that thread's current `cwd`, rather than fanning out one app-server config to every thread. - Preserve each thread's `SessionFlags` layer while replacing reloadable config layers with freshly loaded config, then derive the MCP refresh payload from the rebuilt result. - Move MCP refresh orchestration into app-server so manual refreshes fail loudly while background refreshes remain best-effort, and route plugin-triggered refreshes through the same per-thread reload path. - Add regression coverage for session overlays, fresh project config, plugin-derived MCP config, current requirements, and strict vs best-effort refresh behavior. # Verification - Passed focused Rust coverage for the thread-config rebuild behavior and deferred MCP refresh flow, plus `cargo test -p codex-app-server --lib`. - Verified end to end in the Codex dev app against the locally built CLI: registered an MCP via thread config, verified that it could be used successfully before refresh, manually triggered MCP refresh, and verified that it continued to be available afterward. |
||
|
|
8ef31894dc |
app-server: align dynamic tool identifiers with Responses API (#20724)
## Why Codex currently accepts dynamic tool names and namespaces that the upstream Responses function-tool path does not actually support. In practice, that means app-server can register a dynamic tool successfully and only discover later that the LLM-facing tool contract will reject or mishandle it. This PR tightens the app-server-side dynamic tool contract to match the Responses API before we stack dynamic tool hook support on top of it. ## What changed - validate dynamic tool `name` against the Responses function-tool identifier contract: `^[a-zA-Z0-9_-]+$`, length `1..128` - validate dynamic tool `namespace` the same way, with the Responses namespace length limit `1..64` - reject namespaces that collide with the always-reserved Responses runtime namespaces such as `functions`, `multi_tool_use`, `file_search`, `web`, `browser`, `image_gen`, `computer`, `container`, `terminal`, `python`, `python_user_visible`, `api_tool`, `tool_search`, and `submodel_delegator` - escape invalid identifiers in error messages so control characters do not spill raw into logs or client-visible error text - document the tightened dynamic tool identifier contract in `codex-rs/app-server/README.md` - add both unit coverage for the validator and an app-server integration test that rejects a `thread/start` request with Responses-incompatible dynamic tool identifiers ## Verification - `cargo test -p codex-app-server validate_dynamic_tools_` - `cargo test -p codex-app-server --test all thread_start_rejects_dynamic_tools_not_supported_by_responses` |
||
|
|
5119680f85 |
feat: Add plugin share access controls (#21124)
Extends `plugin/share/save` to accept optional discoverability and shareTargets while uploading plugin contents, and adds `plugin/share/updateTargets` for share-only target updates without re-uploading. |
||
|
|
b3d4f1a9f0 |
[codex-analytics] rework thread_source for thread analytics (#20949)
## Summary - make `thread_source` an explicit optional thread-level field on `thread/start`, `thread/fork`, and returned thread payloads - persist `thread_source` in rollout/session metadata so resumed live threads retain the original value - replace the old best-effort `session_source` -> `thread_source` mapping with an explicit caller-supplied analytics classification ## Why Before this change, analytics `thread_source` was populated by a best-effort mapping from `session_source`. `session_source` describes the runtime/client surface, not the actual thread-level origin, so that projection was not accurate enough to distinguish cases such as `user`, `subagent`, `memory_consolidation`, and future thread origins reliably. Making `thread_source` explicit keeps one thread-level analytics field while letting callers provide the real classification directly instead of recovering it indirectly from `session_source`. ## Impact For new analytics events, `thread_source` now reflects the explicit thread-level classification supplied by the caller rather than an inferred value derived from `session_source`. Existing protocol fields remain optional; callers that omit `threadSource` now produce `null` instead of a best-effort inferred value. ## Validation - `just write-app-server-schema` - `cargo test -p codex-analytics -p codex-core -p codex-app-server-protocol --no-run` - `cargo test -p codex-app-server-protocol generated_ts_optional_nullable_fields_only_in_params` - `cargo test -p codex-analytics thread_initialized_event_serializes_expected_shape` - `cargo test -p codex-core resume_stopped_thread_from_rollout_preserves_thread_source` |