Codex WebSocket implementation notes
- Live OpenAI WebSocket Mode guide was reachable during implementation; the implemented protocol uses
response.create, omits HTTP/SSE transport fields, keeps store:false, treats previous_response_not_found and websocket_connection_limit_reached specially, and preserves one in-flight response per socket.
- Dependency choice:
tokio-tungstenite with rustls webpki roots matches the existing reqwest rustls posture; Tokio gained only net and sync for WebSocket I/O and reusable socket state.
- Setting choice: global-only
codexTransport accepts auto (default WebSocket with SSE fallback) or sse (force legacy HTTP/SSE). Project settings cannot override it because it changes secret-bearing provider transport behavior.
- The WebSocket URL is derived from the resolved Codex HTTP endpoint by normalizing to
/codex/responses and changing https/http to wss/ws; it never targets the public API-key endpoint.
- Continuation state is memory-only per provider instance. A next WebSocket request is reduced to suffix input only when non-input request shape is unchanged and the new full input starts with prior full input plus normalized prior assistant output items; uncertainty clears continuation and sends full context.
- Fallback is allowed only before visible text, reasoning summary, or tool-input deltas are emitted. After visible output, WebSocket failures surface a sanitized fatal error to avoid duplicate visible replay.
- Cancellation abandons the active socket, clears continuation, and returns promptly; the implementation reuses sockets only while under a 55-minute age cap and 5-minute idle TTL.
- Deferred: public API-key Responses WebSocket, generate:false warmup, server-side compaction/replay, debug stats/UI controls, benchmarking, and async conversion of SSE fallback remain outside this OAuth Codex transport task.
Configurable tool-result compaction
- The structured setting resolves presets as defaults, then applies explicit nested overrides.
conservative preserves legacy superseded-read folding; balanced also clears older replayable local results; aggressive also clears older locally recoverable results; custom enables only reducers selected in nested settings.
- Where the task did not prescribe nested defaults, presets protect 2,000 recent tokens; balanced/aggressive also protect four recent results. Local clearing keeps eight eligible uses (four for aggressive), requires 1,000 reclaimable tokens, and excludes
edit, write, recall, and read_output unless explicitly overridden.
- Shared recency guards apply before semantic dedupe and local clearing.
excludedTools wins over mode and eligibility. Local clearing treats a missing or non-true result envelope as a failure and keeps it unless includeFailures is explicit.
- Project settings may override local policy and scheduling. A project cannot select
anthropicNative or auto, or alter a global native policy; those provider-side request controls remain global-only.
- Anthropic public documentation was checked on 2026-07-09. It documents
exclude_tools and clear_tool_inputs for clear_tool_uses_20250919; Iris maps both. Native clearing keeps tool inputs by default so local transcript recovery retains the original call and result.
- Native and local reducers may coexist only when their candidate tool sets are provably disjoint. Semantic dedupe has candidates
read and ls; native clearing must exclude both when semantic dedupe remains enabled.
- Anthropic exposes no success/failure selector for native clearing. Explicit
anthropicNative therefore requires includeFailures=true; auto falls back to local clearing when that consent or reducer disjointness is absent.
- Native inclusion modes are translated to
exclude_tools over Iris's current built-in tool surface. Provider telemetry for exact cleared call ids is deferred because the response reports aggregate counts/tokens, not the cleared ids.
- Tool-call-id recovery scans the existing session JSONL. No new blob store or folded-body copy is added; normal tool-output offload still handles an oversized recall response.
/settings edits enabled, aggressiveness, cache timing, trigger tokens, semantic retain-per-path, and clearing keep-recent counts. Tool-name arrays, mode, backend, failure inclusion, and native input clearing remain settings-file-only because the current menu has no safe list editor.
- The repository's named
documentation-codemap-specialist skill was unavailable in this environment. Affected codemap rows were updated manually; no generated codemap tooling was available to run.
- No new ADR was added. These decisions directly extend ADR-0048's durable fold/recovery model, ADR-0051's flush scheduler, and ADR-0022's provider-native boundary; their dated addenda are the authoritative record.