Skip to main content

aiopquic - Async QUIC + WebTransport (picoquic)

aiopquic is a Python/Cython binding to picoquic, providing high-performance QUIC transport and WebTransport for asyncio applications.

Overview

aiopquic exposes picoquic's QUIC implementation through a lock-free SPSC ring buffer architecture that bridges the picoquic network thread with Python's asyncio event loop. It provides an asyncio QUIC/HTTP3 transport API in the spirit of aioquic (and its fork qh3) — similar shapes for QuicConfiguration, QuicConnection, connect / serve, and event types — plus a native WebTransport client/server layered on picoquic's H3 + h3zero. Not a drop-in replacement: semantics differ around backpressure (send_stream_data raises BufferError on full per-stream ring) and flow-control sizing.

Architecture

  • SPSC Ring Buffers -- Lock-free single producer/single consumer rings for event passing between threads, separate TX and RX rings per TransportContext.
  • TX path -- Asyncio pushes into per-stream byte ring; picoquic pulls at wire rate via prepare_to_send.
  • RX path -- picoquic pushes per-event StreamChunks; ownership transfers at pop for 1-copy delivery.
  • Cross-platform wake fd -- Linux eventfd for efficient asyncio add_reader() notification; pipe() self-pipe fallback on macOS / BSD.
  • Dedicated Network Thread -- picoquic runs in its own thread via picoquic_start_network_thread(). One worker thread per TransportContext; multiple contexts share the asyncio event loop within a single Python process.
  • Cython Bridge -- Thin Cython layer over C callbacks, minimal overhead.
  • WebTransport -- asyncio.webtransport.WebTransportSession (client + server) over picoquic's picowt_* API and h3zero.

Features

  • QUIC client and server: connect, serve, QuicConnectionProtocol
  • Stream data send/receive with FIN signaling, stream reset, stop_sending
  • WebTransport client + server: serve_webtransport, WebTransportSession
  • QUIC datagram TX + RX (note: WebTransport datagram TX not yet wired)
  • Connection migration / 0-RTT (inherited from picoquic)
  • Connection management: create, close, idle timeout, application close codes
  • Per-cnx multiplexing on the server side via QuicEngine
  • TLS keylog (NSS Key Log Format) for pcap decryption
  • Native picoquic_ct / picohttp_ct subprocess smoke (catches upstream regressions on every submodule update)

Performance

Multi-Gbps sustained throughput over loopback on commodity hardware: 2+ Gbps through the full asyncio API at the QUIC default MTU (where the kernel's sendmsg syscall rate is the wall), 11+ Gbps protocol-only. Numbers, methodology, reproduction commands, build flags, and runtime tuning (jemalloc, GSO, wake thresholds) live in PERFORMANCE.md. The TX/RX dataflow and flow-control model — including the TX backpressure configuration parameters — are documented in DATAFLOW.md.

Installation

Wheels for cp312 / cp313 / cp314 on Linux (manylinux_2_34, glibc 2.34+) and macOS arm64 are published to PyPI:

uv pip install aiopquic     # or: pip install aiopquic

For older Linux (glibc 2.28–2.33) install via sdist; build toolchain required.

From source

git clone https://github.com/gmarzot/aiopquic.git
cd aiopquic
./bootstrap_python.sh    # creates .venv with uv-managed Python 3.14 (GIL build) and pins cython 3.2+
source .venv/bin/activate
./build.sh               # reconcile submodules, build picotls/picoquic + drivers, relink + verify
uv pip install -e '.[dev]'    # add dev/test extras — or: pip install -e '.[dev]'

Re-run ./build.sh after any git checkout or submodule bump — it is idempotent (a matching fingerprint skips the compile) and guarantees the imported aiopquic reflects the current source, host-tuned. ./build.sh --check is a read-only doctor that reports submodule drift, a stale native build, or a portable wheel shadowing the editable install, and exits nonzero — handy as a pre-benchmark or CI gate.

On macOS, set OPENSSL_ROOT_DIR if Homebrew OpenSSL is not auto-detected (the build script tries openssl@3 then openssl@1.1).

Reporting issues

Include the full version report in any issue — it captures aiopquic plus the picoquic + picotls submodule SHAs the binding was built from:

python -m aiopquic.versions   # or the console script: aiopquic-versions

Sample output:

aiopquic:  0.3.7.dev12+g6eef9caf6 (~/Projects/moq/aiopquic/src/aiopquic) [2026-06-12 08:55]
  - picoquic:  1.1.49.2 (d6c5653d) [2026-06-05]
  - picotls:   master (bfa67875) [2026-04-20]

If you're running aiomoqt on top, prefer python -m aiomoqt.versions — it chains through to this report and includes the aiomoqt version too.

Usage

Low-level Transport API

from aiopquic._binding._transport import TransportContext

server = TransportContext()
server.start(port=4433, cert_file="cert.pem", key_file="key.pem", alpn="moq-00", is_client=False)

client = TransportContext()
client.start(port=0, alpn="moq-00", is_client=True)
client.create_client_connection("127.0.0.1", 4433, sni="localhost", alpn="moq-00")

Asyncio API

from aiopquic.asyncio.client import connect
from aiopquic.quic.configuration import QuicConfiguration

configuration = QuicConfiguration(alpn_protocols=["myproto"], is_client=True)

async with connect("server", 4433, configuration=configuration) as protocol:
    quic = protocol._quic
    stream_id = quic.get_next_available_stream_id()
    quic.send_stream_data(stream_id, payload, end_stream=True)

payload is opaque bytes; the library doesn't impose framing. Consumers that want HTTP/3 layer on top of aiopquic's picowt-backed h3zero plumbing; consumers that want WebTransport use serve_webtransport / connect_webtransport. Most direct users of the asyncio API ship their own protocol bytes (MoQT, custom binary frames, etc.).

WebTransport

from aiopquic.asyncio.webtransport import (
    serve_webtransport, WebTransportSession,
)
# See src/aiopquic/asyncio/webtransport.py and tests/ for full examples.

Development

uv pip install -e '.[dev]'    # or: pip install -e '.[dev]'
python -m pytest tests/ -v -m "not interop and not native"

# Microbenches (opt-in)
python -m pytest tests/bench

Test-suite coverage, benchmark methodology, performance builds (AIOPQUIC_PERF=1, io_uring scaffolding), and runtime tuning are documented in PERFORMANCE.md.

Known Limitations

  • Free-threaded Python (3.14t) not yet supported -- the TX-ring producer side, TransportContext lifecycle, and the WebTransport engine state currently rely on the GIL for serialization. FT support deferred until a per-context locking audit lands.
  • STOP_SENDING error codes surface as 0 today: picoquic's public stream-error getter only returns the RESET_STREAM code. STOP_SENDING's code lives in stream->remote_stop_error in picoquic_internal.h (no public getter). A small helper that pulls the field is straightforward future work — see TODO in src/aiopquic/_binding/c/callback.h.

TODO

  • Windows support (eventfd alternative — IOCP / WSAEventSelect on the wake-fd path)
  • Free-threaded Python (3.14t) support after producer-side locking audit
  • STOP_SENDING error-code surfacing helper (read remote_stop_error from picoquic_internal.h)
  • WebTransport datagram TX path through the C bridge
  • Datagram benches: latency percentiles, payload-size sweep, loss / jitter under load (today's bench_datagram is fire-and-count throughput only)
  • Pure stream open/close microbench (lifecycle rate without payload, separate from bench_stream_churn_highlevel which bundles writes + FIN)
  • Submit aiopquic to the QUIC interop runner for cross-implementation coverage

Resources



A Marz Research project.
Author: G. S. Marzot <gmarzot@marzresearch.net>

License

MIT License -- see LICENSE

Metadata

Release files for aiopquic 0.4.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for aiopquic 0.4.0
File Size Uploaded
aiopquic-0.4.0.tar.gz 3.4 MB Details

Built distributions (wheels)

Table of built distributions (wheels) for aiopquic 0.4.0
File
aiopquic-0.4.0-cp314-cp314-manylinux_2_34_x86_64.whl CPython 3.14 CPython 3.14 Linux glibc 2.34+ x86-64 Details
aiopquic-0.4.0-cp314-cp314-manylinux_2_34_aarch64.whl CPython 3.14 CPython 3.14 Linux glibc 2.34+ ARM64 Details
aiopquic-0.4.0-cp314-cp314-macosx_14_0_arm64.whl CPython 3.14 CPython 3.14 macOS 14.0+ ARM64 Details
aiopquic-0.4.0-cp313-cp313-manylinux_2_34_x86_64.whl CPython 3.13 CPython 3.13 Linux glibc 2.34+ x86-64 Details
aiopquic-0.4.0-cp313-cp313-manylinux_2_34_aarch64.whl CPython 3.13 CPython 3.13 Linux glibc 2.34+ ARM64 Details
aiopquic-0.4.0-cp313-cp313-macosx_14_0_arm64.whl CPython 3.13 CPython 3.13 macOS 14.0+ ARM64 Details
aiopquic-0.4.0-cp312-cp312-manylinux_2_34_x86_64.whl CPython 3.12 CPython 3.12 Linux glibc 2.34+ x86-64 Details
aiopquic-0.4.0-cp312-cp312-manylinux_2_34_aarch64.whl CPython 3.12 CPython 3.12 Linux glibc 2.34+ ARM64 Details
aiopquic-0.4.0-cp312-cp312-macosx_14_0_arm64.whl CPython 3.12 CPython 3.12 macOS 14.0+ ARM64 Details

Total release size: 46.8 MB

Release files / aiopquic-0.4.0.tar.gz

Download URL aiopquic-0.4.0.tar.gz
Size 3.4 MB
Tags Source
SHA-256 checksum
How to use checksums
363d35a28472f614267eea7cf3d7fb92dded5962b048fd966a809bf3b272afb5
BLAKE2b-256 checksum
How to use checksums
d24118692b061acfc871bd5be22005b48e16cb65c0395d33dbd83945b585eda7
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.14.7

Release files / aiopquic-0.4.0-cp314-cp314-manylinux_2_34_x86_64.whl

Download URL aiopquic-0.4.0-cp314-cp314-manylinux_2_34_x86_64.whl
Size 5.4 MB
Tags CPython 3.14 Linux glibc 2.34+ x86-64
SHA-256 checksum
How to use checksums
6dd6c585f80c0646e130b6a62657d7208dca799ecbe30249b328ebaee93deb65
BLAKE2b-256 checksum
How to use checksums
5ca48a6f03955b6815bd58c276dfbcd0559f53b479eca74e3fca927ca3022693
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.14.7

Release files / aiopquic-0.4.0-cp314-cp314-manylinux_2_34_aarch64.whl

Download URL aiopquic-0.4.0-cp314-cp314-manylinux_2_34_aarch64.whl
Size 5.1 MB
Tags CPython 3.14 Linux glibc 2.34+ ARM64
SHA-256 checksum
How to use checksums
f970f112a6afdff269891e8be29435253953898018a046c43d9c4268ca5aca3e
BLAKE2b-256 checksum
How to use checksums
8ca7daa3589c1eae9ccbc01445a702a11cbafa28500a311c146479610e5ba9ca
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.14.7

Release files / aiopquic-0.4.0-cp314-cp314-macosx_14_0_arm64.whl

Download URL aiopquic-0.4.0-cp314-cp314-macosx_14_0_arm64.whl
Size 4.0 MB
Tags CPython 3.14 macOS 14.0+ ARM64
SHA-256 checksum
How to use checksums
f1c56d8087430efd20f757a5b33b3cb7ea6b33f4c5bd27c2149ab1f6f5df93a5
BLAKE2b-256 checksum
How to use checksums
b384cfd484c5d6b29a25739030b20d7b06b40c965eb18055b5ebec4241789137
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.14.7

Release files / aiopquic-0.4.0-cp313-cp313-manylinux_2_34_x86_64.whl

Download URL aiopquic-0.4.0-cp313-cp313-manylinux_2_34_x86_64.whl
Size 5.3 MB
Tags CPython 3.13 Linux glibc 2.34+ x86-64
SHA-256 checksum
How to use checksums
2bfe97a2c03a4200edf637f1f50ce5d7fffad05c9712c4c5d505ba96b29ed8d0
BLAKE2b-256 checksum
How to use checksums
06805d35b97f2307e60993bb90bb800e0102f102115c42421ae6c41baae989f4
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.14.7

Release files / aiopquic-0.4.0-cp313-cp313-manylinux_2_34_aarch64.whl

Download URL aiopquic-0.4.0-cp313-cp313-manylinux_2_34_aarch64.whl
Size 5.1 MB
Tags CPython 3.13 Linux glibc 2.34+ ARM64
SHA-256 checksum
How to use checksums
bbd6cfa485494a015bda9b53e4103d526eeb27af49982cd1afdbb135dfc9b3ea
BLAKE2b-256 checksum
How to use checksums
e476de26ab975c95d0fe3251405494c25058f65e4ef9c33f9440f4a2237bffc3
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.14.7

Release files / aiopquic-0.4.0-cp313-cp313-macosx_14_0_arm64.whl

Download URL aiopquic-0.4.0-cp313-cp313-macosx_14_0_arm64.whl
Size 4.0 MB
Tags CPython 3.13 macOS 14.0+ ARM64
SHA-256 checksum
How to use checksums
a0c3782ec5aa23c51624916393f4c0898bef2c46e5fcf08556d46c95edd43e5d
BLAKE2b-256 checksum
How to use checksums
27e12f5da489db8973646ab1de7345374a98704bd2b993a7a30ada96927f42a2
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.14.7

Release files / aiopquic-0.4.0-cp312-cp312-manylinux_2_34_x86_64.whl

Download URL aiopquic-0.4.0-cp312-cp312-manylinux_2_34_x86_64.whl
Size 5.4 MB
Tags CPython 3.12 Linux glibc 2.34+ x86-64
SHA-256 checksum
How to use checksums
c7c8d039ad6f37c95064318bad663ffd6be2c7e22fda81b7b9162530cb9fc053
BLAKE2b-256 checksum
How to use checksums
4aa57c59051597c09bec53d47dcb4cb2c147869d0a93d8465d86fab57b2ee5a7
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.14.7

Release files / aiopquic-0.4.0-cp312-cp312-manylinux_2_34_aarch64.whl

Download URL aiopquic-0.4.0-cp312-cp312-manylinux_2_34_aarch64.whl
Size 5.1 MB
Tags CPython 3.12 Linux glibc 2.34+ ARM64
SHA-256 checksum
How to use checksums
75d42b881d1dc9295d7b1ae1b89245943bbf904d9da0633def145e97397c75d3
BLAKE2b-256 checksum
How to use checksums
b89a57e8a865a5eafb0fcca31be79a69d99bb5bd8dde9d99b486bf55f9d3319c
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.14.7

Release files / aiopquic-0.4.0-cp312-cp312-macosx_14_0_arm64.whl

Download URL aiopquic-0.4.0-cp312-cp312-macosx_14_0_arm64.whl
Size 4.0 MB
Tags CPython 3.12 macOS 14.0+ ARM64
SHA-256 checksum
How to use checksums
b5f3a42ee4ca9fa5b7fc6d572b7dab8ffe69bd41a80bd8723fb2cf1d58eb09b1
BLAKE2b-256 checksum
How to use checksums
3b7cfcb594070ea291e91ca995788838ead5ba56abd73d16193ac592e38f91ec
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.14.7
Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page