|
| 1 | +# Free-threaded Python (PEP 703) |
| 2 | + |
| 3 | +HawkAPI ships a wheel for the CPython 3.13 free-threaded build (`python3.13t`, |
| 4 | +also known as "no-GIL" or PEP 703). Support is **experimental** — install works, |
| 5 | +imports work, and routing works, but shared mutable state inside the framework |
| 6 | +has not yet been systematically audited for thread-safety. |
| 7 | + |
| 8 | +## Installation |
| 9 | + |
| 10 | +```bash |
| 11 | +pip install hawkapi |
| 12 | +``` |
| 13 | + |
| 14 | +On a `python3.13t` interpreter, pip picks the `cp313t-cp313t` wheel. This is a |
| 15 | +pure-Python build — the mypyc-compiled hot paths we ship for the regular |
| 16 | +`cp313` ABI are intentionally disabled for free-threaded builds, because |
| 17 | +mypyc-compiled extensions currently require the GIL. |
| 18 | + |
| 19 | +You can confirm which wheel was installed: |
| 20 | + |
| 21 | +```bash |
| 22 | +python3.13t -c "import hawkapi, sys; print(hawkapi.__file__); print(sys._is_gil_enabled())" |
| 23 | +``` |
| 24 | + |
| 25 | +The second line should print `False` on a free-threaded interpreter. |
| 26 | + |
| 27 | +## Status |
| 28 | + |
| 29 | +| Area | Status | |
| 30 | +|---|---| |
| 31 | +| Install / import | Supported | |
| 32 | +| Unit test suite under `python3.13t` | Runs green in CI (non-blocking job) | |
| 33 | +| Mypyc hot-path compilation | **Disabled** (upstream-blocked) | |
| 34 | +| Audit for shared mutable state | **Not yet done** | |
| 35 | + |
| 36 | +The framework exposes `FREE_THREADED`, `maybe_thread_lock()`, and |
| 37 | +`maybe_async_lock()` in `hawkapi._threading` — primitives the internal |
| 38 | +codebase will use to add explicit locks around shared state during the upcoming |
| 39 | +hardening pass. |
| 40 | + |
| 41 | +## Known limitations |
| 42 | + |
| 43 | +- **No mypyc perf boost.** The `cp313t` wheel is pure Python. Throughput on |
| 44 | + free-threaded interpreters is currently lower than on the regular GIL build. |
| 45 | +- **Routing and middleware caches have not been audited.** Building routes at |
| 46 | + startup is safe (single-threaded). Hot-reloading routes or mutating the |
| 47 | + router from request handlers under concurrent threads may race. Avoid both in |
| 48 | + production. |
| 49 | + |
| 50 | +## Reporting issues |
| 51 | + |
| 52 | +Please open a GitHub issue with the `free-threaded` label and include: |
| 53 | + |
| 54 | +- Output of `python3.13t -VV` |
| 55 | +- Your install method (`pip`, `uv`, etc.) and the wheel filename pip installed |
| 56 | +- A minimal reproducer with explicit thread/task concurrency |
| 57 | +- The observed symptom (crash, wrong output, hang) |
| 58 | + |
| 59 | +## Roadmap |
| 60 | + |
| 61 | +A follow-up milestone (tracked as "Tier 1-B") will: |
| 62 | + |
| 63 | +1. Audit every module with shared mutable state (route caches, DI singletons, |
| 64 | + middleware counters, OpenAPI schema cache) and guard mutations with |
| 65 | + `maybe_thread_lock` / `maybe_async_lock`. |
| 66 | +2. Expand the CI free-threaded job to cover integration and perf tests. |
| 67 | +3. Promote the CI job from `continue-on-error: true` to a required check. |
0 commit comments