Commit Graph

3134 Commits

  • feat: sqlite 1 (#10004)
    Add a `.sqlite` database to be used to store rollout metatdata (and
    later logs)
    This PR is phase 1:
    * Add the database and the required infrastructure
    * Add a backfill of the database
    * Persist the newly created rollout both in files and in the DB
    * When we need to get metadata or a rollout, consider the `JSONL` as the
    source of truth but compare the results with the DB and show any errors
  • Add exec policy TOML representation (#10026)
    We'd like to represent these in `requirements.toml`. This just adds the
    representation and the tests, doesn't wire it up anywhere yet.
  • feat(core) RequestRule (#9489)
    ## Summary
    Instead of trying to derive the prefix_rule for a command mechanically,
    let's let the model decide for us.
    
    ## Testing
    - [x] tested locally
  • fix(core) info cleanup (#9986)
    ## Summary
    Simplify this logic a bit.
  • [skills] Auto install MCP dependencies when running skils with dependency specs. (#9982)
    Auto install MCP dependencies when running skils with dependency specs.
  • Restore image attachments/text elements when recalling input history (Up/Down) (#9628)
    **Summary**
    - Up/Down input history now restores image attachments and text elements
    for local entries.
    - Composer history stores rich local entries (text + text elements +
    local image paths) while persistent history remains text-only.
    - Added tests to verify history recall rehydrates image placeholders and
    attachments in both `tui` and `tui2`.
    
    **Changes**
    - `tui/src/bottom_pane/chat_composer_history.rs`: store `HistoryEntry`
    (text + elements + image paths) for local history; adapt navigation +
    tests.
    - `tui2/src/bottom_pane/chat_composer_history.rs`: same as above.
    - `tui/src/bottom_pane/chat_composer.rs`: record rich history entries
    and restore them on Up/Down; update Ctrl+C history and tests.
    - `tui2/src/bottom_pane/chat_composer.rs`: same as above.
  • fix: allow unknown fields on Notice in schema (#10041)
    the `notice` field didn't allow unknown fields in the schema, leading to
    issues where they shouldn't be.
    
    Now we allow unknown fields.
    
    <img width="2260" height="720" alt="image"
    src="https://github.com/user-attachments/assets/1de43b60-0d50-4a96-9c9c-34419270d722"
    />
  • fix: enable per-turn updates to web search mode (#10040)
    web_search can now be updated per-turn, for things like changes to
    sandbox policy.
    
    `SandboxPolicy::DangerFullAccess` now sets web_search to `live`, and the
    default is still `cached`.
    
    Added integration tests.
  • tui: stabilize shortcut overlay snapshots on WSL (#9359)
    Fixes #9361
    
    ## Context
    Split out from #9059 per review:
    https://github.com/openai/codex/pull/9059#issuecomment-3757859033
    
    ## Summary
    The shortcut overlay renders different paste-image bindings on WSL
    (Ctrl+Alt+V) vs non-WSL (Ctrl+V), which makes snapshot tests
    non-deterministic when run under WSL.
    
    ## Changes
    - Gate WSL detection behind `cfg(not(test))` so snapshot tests are
    deterministic across environments.
    - Add a focused unit test that still asserts the WSL-specific
    paste-image binding.
    
    ## Testing
    - `just fmt`
    - `just fix -p codex-tui`
    - `just fix -p codex-tui2`
    - `cargo test -p codex-tui`
    - `cargo test -p codex-tui2`
  • Ask user question UI footer improvements (#9949)
    ## Summary
    
    Polishes the `request_user_input` TUI overlay
    
    Question 1 (unanswered)
    <img width="853" height="167" alt="Screenshot 2026-01-27 at 1 30 09 PM"
    src="https://github.com/user-attachments/assets/3c305644-449e-4e8d-a47b-d689ebd8702c"
    />
    
    Tab to add notes
    <img width="856" height="198" alt="Screenshot 2026-01-27 at 1 30 25 PM"
    src="https://github.com/user-attachments/assets/0d2801b0-df0c-49ae-85af-e6d56fc2c67c"
    />
    
    Question 2 (unanswered)
    <img width="854" height="168" alt="Screenshot 2026-01-27 at 1 30 55 PM"
    src="https://github.com/user-attachments/assets/b3723062-51f9-49c9-a9ab-bb1b32964542"
    />
    
    Ctrl+p or h to go back to q1 (answered)
    <img width="853" height="195" alt="Screenshot 2026-01-27 at 1 31 27 PM"
    src="https://github.com/user-attachments/assets/c602f183-1c25-4c51-8f9f-e565cb6bd637"
    />
    
    Unanswered freeform
    <img width="856" height="126" alt="Screenshot 2026-01-27 at 1 31 42 PM"
    src="https://github.com/user-attachments/assets/7e3d9d8b-820b-4b9a-9ef2-4699eed484c5"
    />
    
    ## Key changes
    
    - Footer tips wrap at tip boundaries (no truncation mid‑tip); footer
    height scales to wrapped tips.
    - Keep tooltip text as Esc: interrupt in all states.
    - Make the full Tab: add notes tip cyan/bold when applicable; hide notes
    UI by default.
    - Notes toggling/backspace:
    - Tab opens notes when an option is selected; Tab again clears notes and
    hides the notes UI.
        - Backspace in options clears the current selection.
        - Backspace in empty notes closes notes and returns to options.
    - Selection/answering behavior:
    - Option questions highlight a default option but are not answered until
    Enter.
    - Enter no longer auto‑selects when there’s no selection (prevents
    accidental answers).
        - Notes submission can commit the selected option when present.
    - Freeform questions require Enter with non‑empty text to mark answered;
    drafts are not submitted unless committed.
    - Unanswered cues:
        - Skipped option questions count as unanswered.
        - Unanswered question titles are highlighted for visibility.
    - Typing/navigation in options:
        - Typing no longer opens notes; notes are Tab‑only.
    - j/k move option selection; h/l switch questions (Ctrl+n/Ctrl+p still
    work).
    
    ## Tests
    
    - Added unit coverage for:
        - tip‑level wrapping
        - focus reset when switching questions with existing drafts
        - backspace clearing selection
        - backspace closing empty notes
        - typing in options does not open notes
        - freeform draft submission gating
        - h/l question navigation in options
    - Updated snapshots, including narrow footer wrap.
    
    ## Why
    
    These changes make the ask‑user‑question overlay:
    
    - safer (no silent auto‑selection or accidental freeform submission),
    - clearer (tips wrap cleanly and unanswered states stand out),
    - more ergonomic (Tab explicitly controls notes; backspace acts like
    undo/close).
    
    ## Codex author
    `codex fork 019bfc3c-2c42-7982-9119-fee8b9315c2f`
    
    ---------
    
    Co-authored-by: Ahmed Ibrahim <aibrahim@openai.com>
  • Clarify external editor env var message (#10030)
    ### Motivation
    - Improve UX by making it explicit that `VISUAL`/`EDITOR` must be set
    before launching Codex, not during a running session.
    
    ### Description
    - Update the external editor error text in `codex-rs/tui/src/app.rs` to:
    `"Cannot open external editor: set $VISUAL or $EDITOR before starting
    Codex."` and run `just fmt` to apply formatting.
    
    ### Testing
    - Ran `just fmt` successfully; attempted `cargo test -p codex-tui` but
    it failed due to network errors when fetching git dependencies (tests
    did not complete).
    
    ------
    [Codex
    Task](https://chatgpt.com/codex/tasks/task_i_6972c2c984948329b1a37d5c5839aff3)
  • Show OAuth error descriptions in callback responses (#9654)
    ### Motivation
    - The local OAuth callback server returned a generic "Invalid OAuth
    callback" on failures even when the query contained an
    `error_description`, making it hard to debug OAuth failures.
    
    ### Description
    - Update `codex-rs/rmcp-client/src/perform_oauth_login.rs` to surface
    `error_description` values from the callback query in the HTTP response.
    - Introduce a `CallbackOutcome` enum and change `parse_oauth_callback`
    to return it, parsing `code`, `state`, and `error_description` from the
    query string.
    - Change `spawn_callback_server` to match on `CallbackOutcome` and
    return `OAuth error: <description>` with a 400 status when
    `error_description` is present, while preserving the existing success
    and invalid flows.
    - Use inline formatting for the error response string.
    
    ### Testing
    - Ran `just fmt` in the `codex-rs` workspace to format changes
    successfully.
    - Ran `cargo test -p codex-rmcp-client` and all tests passed.
    
    ------
    [Codex
    Task](https://chatgpt.com/codex/tasks/task_i_6971aadc68d0832e93159efea8cd48a9)
  • Fix: Render MCP image outputs regardless of ordering (#9815)
    ## What?
    - Render an MCP image output cell whenever a decodable image block
    exists in `CallToolResult.content` (including text-before-image or
    malformed image before valid image).
    
    ## Why?
    - Tool results that include caption text before the image currently drop
    the image output cell.
    - A malformed image block can also suppress later valid image output.
    
    ## How?
    - Iterate `content` and return the first successfully decoded image
    instead of only checking the first block.
    - Add unit tests that cover text-before-image ordering and
    invalid-image-before-valid.
    
    ## Before
    ```rust
    let image = match result {
        Ok(mcp_types::CallToolResult { content, .. }) => {
            if let Some(mcp_types::ContentBlock::ImageContent(image)) = content.first() {
                // decode image (fails -> None)
            } else {
                None
            }
        }
        _ => None,
    }?;
    ```
    ## After
    ```rust
    let image = result
        .as_ref()
        .ok()?
        .content
        .iter()
        .find_map(decode_mcp_image)?;
    ```
    
    ## Risk / Impact
    - Low: only affects image cell creation for MCP tool results; no change
    for non-image outputs.
    
    ## Tests
    - [x] `just fmt`
    - [x] `cargo test -p codex-tui`
    - [x] Rerun after branch update (2026-01-27): `just fmt`, `cargo test -p
    codex-tui`
    
    Manual testing
    
    # Manual testing: MCP image tool result rendering (Codex TUI)
    
    # Build the rmcp stdio test server binary:
    cd codex-rs
    cargo build -p codex-rmcp-client --bin test_stdio_server
    
    # Register the server as an MCP server (absolute path to the built binary):
    codex mcp add mcpimg -- /Users/joshka/code/codex-pr-review/codex-rs/target/debug/test_stdio_server
    
    # Then in Codex TUI, ask it to call:
    - mcpimg.image_scenario({"scenario":"image_only"})
    - mcpimg.image_scenario({"scenario":"text_then_image","caption":"Here is the image:"})
    - mcpimg.image_scenario({"scenario":"invalid_base64_then_image"})
    - mcpimg.image_scenario({"scenario":"invalid_image_bytes_then_image"})
    - mcpimg.image_scenario({"scenario":"multiple_valid_images"})
    - mcpimg.image_scenario({"scenario":"image_then_text","caption":"Here is the image:"})
    - mcpimg.image_scenario({"scenario":"text_only","caption":"Here is the image:"})
    
    # Expected:
    # - You should see an extra history cell: "tool result (image output)" when the
    #   tool result contains at least one decodable image block (even if earlier
    #   blocks are text or invalid images).
    
    
    Fixes #9814
    
    ---------
    
    Co-authored-by: Josh McKinney <joshka@openai.com>
  • enable live web search for DangerFullAccess sandbox policy (#10008)
    Auto-enable live `web_search` tool when sandbox policy is
    `DangerFullAccess`.
    
    Explicitly setting `web_search` (canonical setting), or enabling
    `web_search_cached` or `web_search_request` still takes precedence over
    this sandbox-policy-driven enablement.
  • chore: introduce *Args types for new() methods (#10009)
    Constructors with long param lists can be hard to reason about when a
    number of the args are `None`, in practice. Introducing a struct to use
    as the args type helps make things more self-documenting.
  • remove sandbox globals. (#9797)
    Threads sandbox updates through OverrideTurnContext for active turn
    Passes computed sandbox type into safety/exec
  • feat: make it possible to specify --config flags in the SDK (#10003)
    Updates the `CodexOptions` passed to the `Codex()` constructor in the
    SDK to support a `config` property that is a map of configuration data
    that will be transformed into `--config` flags passed to the invocation
    of `codex`.
    
    Therefore, something like this:
    
    ```typescript
    const codex = new Codex({
      config: {
        show_raw_agent_reasoning: true,
        sandbox_workspace_write: { network_access: true },
      },
    });
    ```
    
    would result in the following args being added to the invocation of
    `codex`:
    
    ```shell
    --config show_raw_agent_reasoning=true --config sandbox_workspace_write.network_access=true
    ```
  • fix(app-server, core): defer initial context write to rollout file until first turn (#9950)
    ### Overview
    Currently calling `thread/resume` will always bump the thread's
    `updated_at` timestamp. This PR makes it the `updated_at` timestamp
    changes only if a turn is triggered.
    
    ### Additonal context
    What we typically do on resuming a thread is **always** writing “initial
    context” to the rollout file immediately. This initial context includes:
    - Developer instructions derived from sandbox/approval policy + cwd
    - Optional developer instructions (if provided)
    - Optional collaboration-mode instructions
    - Optional user instructions (if provided)
    - Environment context (cwd, shell, etc.)
    
    This PR defers writing the “initial context” to the rollout file until
    the first `turn/start`, so we don't inadvertently bump the thread's
    `updated_at` timestamp until a turn is actually triggered.
    
    This works even though both `thread/resume` and `turn/start` accept
    overrides (such as `model`, `cwd`, etc.) because the initial context is
    seeded from the effective `TurnContext` in memory, computed at
    `turn/start` time, after both sets of overrides have been applied.
    
    **NOTE**: This is a very short-lived solution until we introduce sqlite.
    Then we can remove this.
  • feat(network-proxy): add a SOCKS5 proxy with policy enforcement (#9803)
    ### Summary
    - Adds an optional SOCKS5 listener via `rama-socks5`
    - SOCKS5 is disabled by default and gated by config
    - Reuses existing policy enforcement and blocked-request recording
    - Blocks SOCKS5 in limited mode to prevent method-policy bypass
    - Applies bind clamping to the SOCKS5 listener
    
    ### Config
    New/used fields under `network_proxy`:
    - `enable_socks5`
    - `socks_url`
    - `enable_socks5_udp`
    
    ### Scope
    - Changes limited to `codex-rs/network-proxy` (+ `codex-rs/Cargo.lock`)
    
    ### Testing
    ```bash
    cd codex-rs
    just fmt
    cargo test -p codex-network-proxy --offline
  • TUI footer: right-align context and degrade shortcut summary + mode cleanly (#9944)
    ## Summary
    Refines the bottom footer layout to keep `% context left` right-aligned
    while making the left side degrade cleanly
    
    ## Behavior with empty textarea
    Full width:
    <img width="607" height="62" alt="Screenshot 2026-01-26 at 2 59 59 PM"
    src="https://github.com/user-attachments/assets/854f33b7-d714-40be-8840-a52eb3bda442"
    />
    Less:
    <img width="412" height="66" alt="Screenshot 2026-01-26 at 2 59 48 PM"
    src="https://github.com/user-attachments/assets/9c501788-c3a2-4b34-8f0b-8ec4395b44fe"
    />
    Min width:
    <img width="218" height="77" alt="Screenshot 2026-01-26 at 2 59 33 PM"
    src="https://github.com/user-attachments/assets/0bed2385-bdbf-4254-8ae4-ab3452243628"
    />
    
    ## Behavior with message in textarea and agent running (steer enabled)
    Full width:
    <img width="753" height="63" alt="Screenshot 2026-01-26 at 4 33 54 PM"
    src="https://github.com/user-attachments/assets/1856b352-914a-44cf-813d-1cb50c7f183b"
    />
    
    Less:
    <img width="353" height="61" alt="Screenshot 2026-01-26 at 4 30 12 PM"
    src="https://github.com/user-attachments/assets/d951c4d5-f3e7-4116-8fe1-6a6c712b3d48"
    />
    
    Less:
    <img width="304" height="64" alt="Screenshot 2026-01-26 at 4 30 51 PM"
    src="https://github.com/user-attachments/assets/1433e994-5cbc-4e20-a98a-79eee13c8699"
    />
    
    Less:
    <img width="235" height="61" alt="Screenshot 2026-01-26 at 4 30 56 PM"
    src="https://github.com/user-attachments/assets/e216c3c6-84cd-40fc-ae4d-83bf28947f0e"
    />
    
    Less:
    <img width="165" height="59" alt="Screenshot 2026-01-26 at 4 31 08 PM"
    src="https://github.com/user-attachments/assets/027de5de-7185-47ce-b1cc-5363ea33d9b1"
    />
    
    ## Notes / Edge Cases
    - In steer mode while typing, the queue hint no longer replaces the mode
    label; it renders as `tab to queue message · {Mode}`.
    - Collapse priorities differ by state:
    - With the queue hint active, `% context left` is hidden before
    shortening or dropping the queue hint.
    - In the empty + non-running state, `? for shortcuts` is dropped first,
    and `% context left` is only shown if `(shift+tab to
    cycle)` can also fit.
    - Transient instructional states (`?` overlay, Esc hint, Ctrl+C/D
    reminders, and flash/override hints) intentionally suppress the
    mode label (and context) to focus the next action.
    
    ## Implementation Notes
    - Renamed the base footer modes to make the state explicit:
    `ComposerEmpty` and `ComposerHasDraft`, and compute the base mode
    directly from emptiness.
    - Unified collapse behavior in `single_line_footer_layout` for both base
    modes, with:
    - Queue-hint behavior that prefers keeping the queue hint over context.
    - A cycle-hint guard that prevents context from reappearing after
    `(shift+tab to cycle)` is dropped.
    - Kept rendering responsibilities explicit:
      - `single_line_footer_layout` decides what fits.
      - `render_footer_line` renders a chosen line.
    - `render_footer_from_props` renders the canonical mode-to-text mapping.
    - Expanded snapshot coverage:
    - Added `footer_collapse_snapshots` in `chat_composer.rs` to lock the
    distinct collapse states across widths.
    - Consolidated the width-aware snapshot helper usage (e.g.,
    `snapshot_composer_state_with_width`,
    `snapshot_footer_with_mode_indicator`).
  • update pnpm to 10.28.2 to address security issues (#9992)
    Updates pnpm to 10.28.2. to address security issues in prior versions of
    pnpm that can allow deps to execute lifecycle scripts against policy.
    
    I have read the CLA Document and I hereby sign the CLA
  • backend-client: add get_config_requirements_file (#10001)
    Adds getting config requirement to backend-client.
    
    I made a slash command to test it (not included in this PR):
    <img width="726" height="330" alt="Screenshot 2026-01-27 at 15 20 41"
    src="https://github.com/user-attachments/assets/97222e7c-5078-485a-a5b2-a6630313901e"
    />
  • Fix: cap aggregated exec output consistently (#9759)
    ## WHAT?
    - Bias aggregated output toward stderr under contention (2/3 stderr, 1/3
    stdout) while keeping the 1 MiB cap.
    - Rebalance unused stderr share back to stdout when stderr is tiny to
    avoid underfilling.
    - Add tests for contention, small-stderr rebalance, and under-cap
    ordering (stdout then stderr).
    
    ## WHY?
    - Review feedback requested stderr priority under contention.
    - Avoid underfilled aggregated output when stderr is small while
    preserving a consistent cap across exec paths.
    
    ## HOW?
    - Update `aggregate_output` to compute stdout/stderr shares, then
    reassign unused capacity to the other stream.
    - Use the helper in both Windows and async exec paths.
    - Add regression tests for contention/rebalance and under-cap ordering.
    
    ## BEFORE
    ```rust
    // Best-effort aggregate: stdout then stderr (capped).
    let mut aggregated = Vec::with_capacity(
        stdout
            .text
            .len()
            .saturating_add(stderr.text.len())
            .min(EXEC_OUTPUT_MAX_BYTES),
    );
    append_capped(&mut aggregated, &stdout.text, EXEC_OUTPUT_MAX_BYTES);
    append_capped(&mut aggregated, &stderr.text, EXEC_OUTPUT_MAX_BYTES);
    let aggregated_output = StreamOutput {
        text: aggregated,
        truncated_after_lines: None,
    };
    ```
    
    ## AFTER
    ```rust
    fn aggregate_output(
        stdout: &StreamOutput<Vec<u8>>,
        stderr: &StreamOutput<Vec<u8>>,
    ) -> StreamOutput<Vec<u8>> {
        let total_len = stdout.text.len().saturating_add(stderr.text.len());
        let max_bytes = EXEC_OUTPUT_MAX_BYTES;
        let mut aggregated = Vec::with_capacity(total_len.min(max_bytes));
    
        if total_len <= max_bytes {
            aggregated.extend_from_slice(&stdout.text);
            aggregated.extend_from_slice(&stderr.text);
            return StreamOutput {
                text: aggregated,
                truncated_after_lines: None,
            };
        }
    
        // Under contention, reserve 1/3 for stdout and 2/3 for stderr; rebalance unused stderr to stdout.
        let want_stdout = stdout.text.len().min(max_bytes / 3);
        let want_stderr = stderr.text.len();
        let stderr_take = want_stderr.min(max_bytes.saturating_sub(want_stdout));
        let remaining = max_bytes.saturating_sub(want_stdout + stderr_take);
        let stdout_take = want_stdout + remaining.min(stdout.text.len().saturating_sub(want_stdout));
    
        aggregated.extend_from_slice(&stdout.text[..stdout_take]);
        aggregated.extend_from_slice(&stderr.text[..stderr_take]);
    
        StreamOutput {
            text: aggregated,
            truncated_after_lines: None,
        }
    }
    ```
    
    ## TESTS
    - [x] `just fmt`
    - [x] `just fix -p codex-core`
    - [x] `cargo test -p codex-core aggregate_output_`
    - [x] `cargo test -p codex-core`
    - [x] `cargo test --all-features`
    
    ## FIXES
    Fixes #9758
  • Fixing main and make plan mode reasoning effort medium (#9980)
    It's overthinking so much on high and going over the context window.
  • make plan prompt less detailed (#9977)
    This was too much to ask for
  • make cached web_search client-side default (#9974)
    [Experiment](https://console.statsig.com/50aWbk2p4R76rNX9lN5VUw/experiments/codex_web_search_rollout/summary)
    for default cached `web_search` completed; cached chosen as default.
    
    Update client to reflect that.
  • plan prompt (#9975)
    # External (non-OpenAI) Pull Request Requirements
    
    Before opening this Pull Request, please read the dedicated
    "Contributing" markdown file or your PR may be closed:
    https://github.com/openai/codex/blob/main/docs/contributing.md
    
    If your PR conforms to our contribution guidelines, replace this text
    with a detailed and high quality description of your changes.
    
    Include a link to a bug report or enhancement request.
  • prompt (#9970)
    # External (non-OpenAI) Pull Request Requirements
    
    Before opening this Pull Request, please read the dedicated
    "Contributing" markdown file or your PR may be closed:
    https://github.com/openai/codex/blob/main/docs/contributing.md
    
    If your PR conforms to our contribution guidelines, replace this text
    with a detailed and high quality description of your changes.
    
    Include a link to a bug report or enhancement request.
  • Fix resume --last with --json option (#9475)
    Fix resume --last prompt parsing by dropping the clap conflict on the
    codex resume subcommand so a positional prompt is accepted when --last
    is set. This aligns interactive resume behavior with exec-mode logic and
    avoids the “--last cannot be used with SESSION_ID” error.
    
    This addresses #6717
  • prompt final (#9969)
    hopefully final this time (at least tonight) >_<
  • Improve plan mode prompt (#9968)
    # External (non-OpenAI) Pull Request Requirements
    
    Before opening this Pull Request, please read the dedicated
    "Contributing" markdown file or your PR may be closed:
    https://github.com/openai/codex/blob/main/docs/contributing.md
    
    If your PR conforms to our contribution guidelines, replace this text
    with a detailed and high quality description of your changes.
    
    Include a link to a bug report or enhancement request.
  • plan prompt v7 (#9966)
    # External (non-OpenAI) Pull Request Requirements
    
    Before opening this Pull Request, please read the dedicated
    "Contributing" markdown file or your PR may be closed:
    https://github.com/openai/codex/blob/main/docs/contributing.md
    
    If your PR conforms to our contribution guidelines, replace this text
    with a detailed and high quality description of your changes.
    
    Include a link to a bug report or enhancement request.
  • fix: handle all web_search actions and in progress invocations (#9960)
    ### Summary
    - Parse all `web_search` tool actions (`search`, `find_in_page`,
    `open_page`).
    - Previously we only parsed + displayed `search`, which made the TUI
    appear to pause when the other actions were being used.
    - Show in progress `web_search` calls as `Searching the web`
      - Previously we only showed completed tool calls
    
    <img width="308" height="149" alt="image"
    src="https://github.com/user-attachments/assets/90a4e8ff-b06a-48ff-a282-b57b31121845"
    />
    
    ### Tests
    Added + updated tests, tested locally
    
    ### Follow ups
    Update VSCode extension to display these as well
  • Use test_codex more (#9961)
    Reduces boilderplate.
  • Reuse ChatComposer in request_user_input overlay (#9892)
    Reuse the shared chat composer for notes and freeform answers in
    request_user_input.
    
    - Build the overlay composer with ChatComposerConfig::plain_text.
    - Wire paste-burst flushing + menu surface sizing through the bottom
    pane.
  • Reject request_user_input outside Plan/Pair (#9955)
    ## Context
    
    Previous work in https://github.com/openai/codex/pull/9560 only rejected
    `request_user_input` in Execute and Custom modes. Since then, additional
    modes
    (e.g., Code) were added, so the guard should be mode-agnostic.
    
    ## What changed
    
    - Switch the handler to an allowlist: only Plan and PairProgramming are
    allowed
    - Return the same error for any other mode (including Code)
    - Add a Code-mode rejection test alongside the existing Execute/Custom
    tests
    
    ## Why
    
    This prevents `request_user_input` from being used in modes where it is
    not
    intended, even as new modes are introduced.