Files
codex/codex-rs/websocket-client
Michael Bolin 2780bd588f websocket-client: add proxy-aware connector (#31622)
## Why

The route-aware WebSocket connection setup in #31441 is transport
infrastructure rather than Responses API protocol logic. Landing it
first in a dedicated crate keeps `codex-api` focused on request and
response behavior and makes the transport reusable by future WebSocket
clients.

WebSockets must also apply the same effective outbound proxy and
custom-CA policy as HTTP without disabling the lower-latency WebSocket
path. Requiring an `HttpClientFactory` when constructing the connector
makes proxy-policy resolution part of the API instead of an optional
call-site convention.

This PR is an independent prerequisite based directly on `main`. After
it merges, #31441 can rebase onto it and replace its in-crate connector
with this API.

## What changed

- Add a new `codex-websocket-client` workspace crate with a
`WebSocketConnector` constructed from the effective `HttpClientFactory`.
- Resolve every destination through that factory before connecting, then
support direct connections, transport-default routing, HTTP proxies, and
TLS-encrypted HTTPS proxies.
- Preserve custom-CA trust for proxy and target TLS handshakes and
preserve Happy Eyeballs fallback for explicit direct and proxy routes.
- Expose an established `WebSocketConnection` as a uniform `Stream` and
`Sink`, hiding route-specific transport types from protocol clients.
- Add focused integration-style coverage for the public connector and
message stream, real WSS over direct and CONNECT routes, implicit and
explicit HTTPS proxy ports, and stalled-address-family fallback.

## Review guide

1. `codex-rs/websocket-client/src/lib.rs` defines the small public API
and the factory-required policy invariant.
2. `codex-rs/websocket-client/src/dialer.rs` contains DNS, TCP, proxy
tunneling, TLS, and WebSocket handshake setup.
3. `codex-rs/websocket-client/src/dialer_tests.rs` verifies the public
stream, direct and proxied WSS paths, HTTPS port preservation, and Happy
Eyeballs timing.
4. There is intentionally no consumer migration here; #31441 will become
the first consumer after this prerequisite merges.

## Test plan

- `cargo check -p codex-websocket-client --tests`
- `just test -p codex-websocket-client`
- `cargo shear`
- `just bazel-lock-check`
2026-07-08 12:57:27 -07:00
..