Skip to content

v0.3#7

Merged
eareimu merged 318 commits into
mainfrom
endpoint
Jun 15, 2026
Merged

v0.3#7
eareimu merged 318 commits into
mainfrom
endpoint

Conversation

@eareimu

@eareimu eareimu commented Jun 9, 2026

Copy link
Copy Markdown
Collaborator

h3x v0.3.0

  • target version: 0.3.0
  • release type: incremental crates.io release
  • release surface: crates.io
  • planned tag: v0.3.0
  • previous tag: v0.2.0

Release gate

This PR is release-prep only.

It must not merge or tag until:

  1. dquic v0.5.1 is published and visible on crates.io
  2. the release workflow on this PR is rerun against that published upstream
  3. all release-relevant PR checks are green

Current known wait condition:

  • h3x 0.3.0 depends on dquic ^0.5.1
  • downstream release validation must wait for crates.io registry visibility

Summary

This release focuses on three large areas: a substantial endpoint/network
rework around the dquic backend, expanded WebTransport session support,
and a major cleanup of the stream / message / RPC / IPC surface.

Endpoint, network, and dquic backend

  • introduced QuicEndpoint as the lower-level QUIC transport surface
  • generalized H3Endpoint over the QUIC transport layer
  • added owned-transport serving, direct H3 connection acceptance, and QUIC
    transport extraction for advanced ownership/reload flows
  • reorganized network management around a bind-driver model and SNI fan-out
  • tightened endpoint connect / accept / reconcile flows to avoid races in
    cache invalidation, path establishment, SNI dispatch, and bind cleanup
  • aligned the backend with dquic 0.5.1

WebTransport session support

  • added Extended CONNECT establishment and accept flows for WebTransport
  • added typed session identifiers, capsule payload codecs, close values, and
    session-control APIs
  • added session stream wrappers
  • enforced incoming and local stream credit more explicitly
  • required negotiated peer settings before starting or accepting sessions
  • tightened rejection and closure paths around WebTransport session semantics

Stream, message, and hyper surface cleanup

  • added a generic stream capability layer decoupled from QUIC-specific errors
  • reorganized message streams under dhttp::message
  • collapsed Hyper integration into a single-file h3x::hyper facade
  • moved service adapters under the endpoint-facing surface
  • standardized concrete and boxed stream types around Reader / Writer
  • normalized QUIC send-side reset naming to ResetStream / reset

RPC and IPC stream transport

  • introduced shared stream-frame vocabulary and frame bridges
  • routed RPC / IPC QUIC streams through explicit frame bridges and drivers
  • removed the old FD-transfer ACK/CANCEL protocol layer
  • tightened mux preparation, frame delivery ordering, cancellation behavior,
    and latch/error propagation
  • updated WebTransport-related RPC / IPC adapters to the newer session model

Correctness fixes and publish readiness

  • full bind-URI identity is now used where required
  • SNI registration and identity conflict handling were made atomic
  • local address tracking and removals were preserved through endpoint updates
  • qpack, pseudo-header, deferred-error, and lifecycle edge cases were tightened
  • all-features test / coverage / publish CI was strengthened for the published
    crate surface

Upgrade notes

  • H3Endpoint / QuicEndpoint usage may require updates if downstream code
    depended on the older endpoint/server facade layout
  • deprecated h3x::server, h3x::endpoint::server, and
    h3x::hyper::{client, server} surfaces have been removed
  • message-stream imports should move to dhttp::message where applicable
  • QUIC send-side reset APIs are now named ResetStream / reset
  • WebTransport callers should compose support through Settings fragments and
    wait for negotiated peer settings before starting or accepting sessions
  • this release expects the dquic 0.5.1 backend surface

Full changelog: v0.2.0...v0.3.0

eareimu and others added 30 commits May 13, 2026 00:05
… unify ReadStream/WriteStream connection state

Replace errored: Cell<bool> + arbiter: Arc<Arbiter> with arbiter: RefCell<Option<Arc<Arbiter>>>
in Request to fix E0509 (Arc::try_unwrap forbidden on Drop type). None represents
poisoned/consumed state, releasing arbiter reference for cleanup.

Merge ReadStream/WriteStream connection + dhttp_state fields into
ConnectionState<dyn DynConnection> by value, fixing E0308 (DynConnection
required at serve_connection call site). WriteStream bound upgraded from
DynLifecycle to DynConnection.
- Add Clone derive to MessageStreamError
- Implement manual Clone for RequestError<E> (Arc-wrapped ConnectError/MalformedHeaderSection, no E:Clone bound)
- Add authority field (SyncMutex<Option<Authority>>) and init_done atomic to Arbiter
- Refactor init_state to Option<Result<(), RequestError>> for error caching
- Add AuthorityFrozen error and Arbiter::set_authority()
- Add H3Endpoint::new_request_owned() and new_request() — authority starts as None
- Rewrite Request::uri() to sync authority and poison message on freeze
- Refactor IntoFuture: two concrete impls for &H3Endpoint and Arc<H3Endpoint> (BoxFuture with named lifetime)
- Simplify convenience methods (get/post/...) via new_request_owned().method().uri()
- Update unit tests (13 pass) and integration tests (5 simple + 4 axum pass)
- Remove BleEndpontAddr, SocketEndpointAddr, BoundAddr re-exports
- Rename ParseBindUriError -> ParseError, BindUriScheme -> Scheme
- Update EndpointAddr::Socket(..) -> EndpointAddr::direct(..)
- Remove BLE address handling (BLE support dropped in dquic)
- Update VarInt::into_inner() -> into_u64()
- Fix BoundAddr pattern matches (bound_addr() now returns SocketAddr)
- Fix integration tests: common/mod.rs, simple.rs, network.rs
Change get/post/put/delete/patch/head/options/trace from &Arc<Self> to
&self, returning ClientRequest<T, &H3Endpoint<T>> instead of
ClientRequest<T, Arc<Self>>. Internal impl delegates to new_request()
rather than new_request_owned(). Users no longer need to wrap their
endpoint in Arc for the common case.

new_request_owned is preserved as an escape hatch for 'static lifetime
requirements (e.g. async spawning).
Split 7 builder methods into consuming (self -> Self) and set_ prefixed
(&self -> &Self) variants, following the reqwest convention. Consuming
methods enable fluent chaining (e.g., .get(uri).header("x","y").body("hello").await?),
while set_ methods allow non-consuming access for shared-ref contexts.

Also add debug_warn_consumed helper — issues tracing::warn in debug
builds when builder methods are called on an already-consumed Request;
no-op in release. Update test call sites accordingly.
…nt client tests

wrap RefCell borrows in block scope to ensure they are dropped
before the subsequent .await point
when the server uses SilentRefuse, the QUIC PTO exponential backoff
takes ~18s before giving up. wrap the request in a 5s timeout to cut
it short — treat timeout (not an explicit error) as the expected
outcome for silently-refused connections.
remove Pool parameter from the builder — H3Endpoint always starts with
Pool::empty(). construct ref_ep via struct literal in ServiceFactory
instead of going through the builder for a reference-based endpoint.
… test

- Rename src/ipc/quic/tests.rs → test_utils.rs (shared test helpers)
- Update ipc/quic.rs module declaration: mod tests → mod test_utils
- Delete tests/endpoint.rs placeholder (replaced by integration tests)
- Move ReadStream::new_for_test / WriteStream::new_for_test from stream.rs to test.rs
- Rename to read_stream_for_test / write_stream_for_test (pub)
- Add #[cfg(test)] pub mod test declaration in message.rs
- Remove #[cfg(test)] impl blocks with new_for_test from stream.rs
- Parameterize dquic/binds tests: 56 individual tests → ~15 parameterized tests
  preserving all scenarios via test-case-style data tables
- Consolidate connection hash tests: 12 individual → 4 parameterized tests
  covering all hash variant scenarios
…kers

- Delete 5 low-value Debug/Clone/PartialEq derive tests from dquic/client.rs
- Delete 1 low-value derive test from dquic/identity.rs
- Rename qpack/encoder Fix 2/3/4/7 section headers to descriptive titles
- Rename qpack/field/repr Fix 6 section header to descriptive title
- Add connection_refused test (UDP port 2 — verifies connection error handling)
- Add request_timeout test (unresponsive server — verifies timeout handling)
- Add empty_authority_error test (missing authority — verifies validation)
… remove AI traces

- Update 5 call sites to use message::test::{read_stream,write_stream}_for_test API
- Replace 3 AI-generated section headers with descriptive titles
- Delete commented-out test_acquire_message_cycle block (~56 lines)
- Clean 2 #[ignore] messages to remove task references
- Replace direct dquic::prelude imports with h3x::dquic:: equivalents in simple.rs
- Move all inline use statements to file top in simple.rs (4 test functions)
- Simplify axum.rs tests: use test_server()/test_client() instead of _with(_network)
- Add dhttp-identity dependency for identity type migration
- Add QuicEndpoint::new() convenience constructor with default network
- Update README example to use QuicEndpoint/H3Endpoint API
- Remove duplicate dhttp-identity entry in Cargo.toml
…anup

- Replace wholesale map assignment with retain + or_insert merge in
  run_reconcile to avoid clobbering concurrent bind() insertions
- Add termination comments on two unheld spawns in endpoint.rs per
  async code conventions
- Add TODO in Cargo.toml to track dhttp-identity path→git migration
- Document benign zombie Weak behavior in bind_server early returns
- Remove unused imports (Name, CertificateDer) from test code
- Finish ServerName::new → Name::from_str / parse migration in tests

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Use the merged dhttp repo (git://genmeta/dhttp.git) as the source
for dhttp-identity. Retain a [patch] section for local monorepo
development.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Split the single generic T: quic::Connect into Q (transport) and
C: quic::Connection (connection type).  This enables server-only
usage where Q only needs quic::Listen, removing the requirement
to provide a dummy connect().  Client-side types bridge C via
Q::Connection without adding an explicit generic parameter.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Replace request arbiter ownership with shared RequestState and stream locks. Make Message mutation APIs validate stage before mutation while keeping set_body independent from IO stage. Add compatibility server wrapper and update tests for request/response state handling.
@eareimu eareimu merged commit ba4f6a6 into main Jun 15, 2026
7 checks passed
@eareimu eareimu deleted the endpoint branch June 17, 2026 12:40
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant