Skip to main content

Korvex

CI License: MIT

A fast router for Python, written in Rust, with an optional ASGI app on top.

pip install korvex

The router

Router maps a path and an HTTP method to a handler name. It never calls your code: what you do with the name is up to you.

from korvex import Router

router = Router()
router.get("/users/{id:int}", "get_user")
router.post("/users", "create_user", middleware=["auth"])

router.match("/users/42")         # ("get_user", {"id": "42"}, ())
router.match("/users", "POST")    # ("create_user", {}, ("auth",))
router.match("/nope")             # None
router.match("/users", "DELETE")  # raises MethodNotAllowed, .allowed == ["POST"]

Path syntax

Segment Matches Example
users exactly users /users
{id} any segment /users/{id}
{id:int} an integer (42, -7) /users/{id:int}
{id:uuid} a UUID /items/{id:uuid}
*path the rest of the path (last segment) /static/*path

Captured values are always strings. When several routes could match, the most specific one wins: literal, then {id:int}/{id:uuid}, then {id}, then *path.

API

Method Does
route(path, handler, *, method="GET", middleware=None) Registers a route (replaces an existing one).
get / post / put / patch / delete / head / options(path, handler, *, middleware=None) Shortcuts for route.
match(path, method="GET") (handler, params, middleware), None, or raises MethodNotAllowed.
remove(path, method="GET") Removes a route by its pattern. Returns whether it existed.
routes() Every route as (path, method, handler, middleware).
group(prefix, *, middleware=None) A RouteGroup (see below).

Invalid paths or methods raise ValueError.

match keeps the last 1,024 distinct lookups in a cache, and adding or removing a route clears it. Its results are shared between calls, so they are immutable: params is a read-only mapping and middleware a tuple.

Route groups

api = router.group("/api", middleware=["auth"])
api.get("/users", "list_users")             # GET /api/users, middleware ["auth"]

admin = api.group("/admin", middleware=["admin"])
admin.get("/stats", "stats")                # GET /api/admin/stats, middleware ["auth", "admin"]

The ASGI app

App runs the matched handler for you. Serve it with any ASGI server (uvicorn, hypercorn, granian...).

from korvex import App, Response

app = App()

@app.get("/users/{id:int}", middleware=["auth"])
async def get_user(request, id):
    return Response.json({"id": id})

@app.middleware("auth")
def auth(request):
    if request.headers.get("Authorization") is None:
        return Response.text("Unauthorized", status=401)  # stops here
    return None                                          # carries on
pip install "korvex[serve]"   # installs uvicorn
uvicorn mymodule:app
  • Handlers receive the Request plus path params as keyword arguments, and return a Response. Middleware returns a Response to answer early, or None to continue. Both can be sync or async.
  • Request has method, path, headers, query_params, path_params, and await request.body() / await request.json().
  • Response(body, status=, headers=), Response.text(...), Response.json(...), Response.redirect(...).
  • Unknown paths get a 404; known paths with the wrong method get a 405 with an Allow header.
  • Routes registered on app.router directly (for example through a group) are linked to a function with @app.handler("name").

More in examples/.

Performance

Under load

The same small app (1,000 routes, one JSON endpoint) in each framework, served the same way (uvicorn, one worker, one CPU core) and flooded with requests to random URLs by oha:

Requests per second on one CPU core with 200 clients: Korvex 33.9k, Starlette 3.0k to 30.6k, Litestar 18.2k, Sanic 15.8k, FastAPI 1.6k to 12.4k, Django 1.1k to 2.2k.
Framework Requests/s, 200 clients p99 latency, 1,000 clients RAM at rest, peak
Korvex 33.9k 26 ms 35 MB, 46 MB
Starlette 3.0k to 30.6k 35 to 189 ms 39 MB, 49 MB
Litestar 18.2k 79 ms 78 MB, 89 MB
Sanic 15.8k 94 ms 60 MB, 105 MB
FastAPI 1.6k to 12.4k 57 to 351 ms 66 MB, 77 MB
Django 1.1k to 2.2k 1.3 to 1.9 s 48 MB, 145 MB
  • Every framework uses a full CPU core under load, so requests per second is also how much work each one gets out of that core.
  • Starlette, FastAPI and Django try routes one by one: the ranges go from the tested route declared after the 1,000 others to declared first. Starlette's best case comes close to Korvex.
  • No request failed. Throughput holds steady as clients are added; latency grows because requests queue, not because each one gets slower. After the flood, memory stays flat and speed is back to normal.

Reproduce with uv run python benches/load_test.py (needs cargo install oha, takes about 9 minutes).

Router alone

Route matching only, without any server:

Time per route lookup at 10,000 routes. Without cache: Korvex 347 ns, Litestar 732 ns, Sanic 3.5 µs, Flask 3.5 µs, Django 1.3 ms, Starlette 1.5 ms. With each router's cache and repeated URLs: Korvex 67 ns, Litestar 92 ns, Sanic 211 ns.

Median time per lookup, 10,000 routes:

Router First time a URL is seen Same URL again (cached)
Korvex 347 ns 67 ns
Litestar 732 ns 92 ns
Sanic 3.5 µs 211 ns
Flask 3.5 µs (no cache)
Django 1.3 ms (no cache)
Starlette / FastAPI 1.5 ms (no cache)
  • Korvex is the fastest in both cases, and its time stays flat as routes are added. Django and Starlette try routes one by one, so they slow down linearly.
  • Korvex, Litestar and Sanic cache the last 1,024 lookups. The cache helps most with static URLs; URLs with parameters (/users/1, /users/2, ...) are often different, so they hit it less.
  • With few routes, the server and the handler cost more than the router. With many routes, a router that tries them one by one becomes the main cost (see Under load).

Reproduce with uv run pytest benches/bench_router.py --benchmark-only --benchmark-json=benches/results.json, then uv run python benches/plot.py to redraw both charts. Results depend on the machine: measure your own workload before relying on any number.

Development

uv run maturin develop --release   # build the Rust extension
uv run pytest                      # Python tests
cargo test                         # Rust tests

See CONTRIBUTING.md.

License

MIT

Metadata

Release files for korvex 0.3.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 korvex 0.3.0
File Size Uploaded Provenance Actions
korvex-0.3.0.tar.gz 171.1 kB With provenance Details for korvex-0.3.0.tar.gz

Built distributions (wheels)

Table of built distributions (wheels) for korvex 0.3.0
File Actions
korvex-0.3.0-cp39-abi3-win_amd64.whl CPython 3.9 abi3 Windows x86-64 Details for korvex-0.3.0-cp39-abi3-win_amd64.whl
korvex-0.3.0-cp39-abi3-manylinux2014_x86_64.manylinux_2_17_x86_64.whl CPython 3.9 abi3 Linux glibc 2.17+ x86-64 Details for korvex-0.3.0-cp39-abi3-manylinux2014_x86_64.manylinux_2_17_x86_64.whl
korvex-0.3.0-cp39-abi3-manylinux2014_aarch64.manylinux_2_17_aarch64.whl CPython 3.9 abi3 Linux glibc 2.17+ ARM64 Details for korvex-0.3.0-cp39-abi3-manylinux2014_aarch64.manylinux_2_17_aarch64.whl
korvex-0.3.0-cp39-abi3-macosx_11_0_arm64.whl CPython 3.9 abi3 macOS 11.0+ ARM64 Details for korvex-0.3.0-cp39-abi3-macosx_11_0_arm64.whl
korvex-0.3.0-cp39-abi3-macosx_10_12_x86_64.whl CPython 3.9 abi3 macOS 10.12+ x86-64 Details for korvex-0.3.0-cp39-abi3-macosx_10_12_x86_64.whl

Total release size: 1.5 MB

Release files / korvex-0.3.0.tar.gz

Download URL korvex-0.3.0.tar.gz
Size 171.1 kB
Tags Source
SHA-256 checksum
How to use checksums
0b46ff0444cae4593ed2f6ad458fd8f702b17ed89c7522b16549ca698f0502dc
BLAKE2b-256 checksum
How to use checksums
e004afbffea726c87d5fd8784034eba9461ac7dadf4df92e41f3ea0c6c24e855
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Nov 4, 2026.

Transparency log

Release files / korvex-0.3.0-cp39-abi3-win_amd64.whl

Download URL korvex-0.3.0-cp39-abi3-win_amd64.whl
Size 170.5 kB
Tags CPython 3.9 Windows x86-64 abi3
SHA-256 checksum
How to use checksums
f312f7e71e9c2a516193971ac7da37ac2c68dc15963fad87ac37802f43223d75
BLAKE2b-256 checksum
How to use checksums
6558f82aec05e170c88c22f609c8aa049f03e8e63b9fb51055de0c70e892f5c8
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Nov 4, 2026.

Transparency log

Release files / korvex-0.3.0-cp39-abi3-manylinux2014_x86_64.manylinux_2_17_x86_64.whl

Download URL korvex-0.3.0-cp39-abi3-manylinux2014_x86_64.manylinux_2_17_x86_64.whl
Size 315.8 kB
Tags CPython 3.9 Linux glibc 2.17+ x86-64 abi3
SHA-256 checksum
How to use checksums
e7eeba02799d2abe00da0c6f952134bdf6358b6a39e669397ef7a402c85054cf
BLAKE2b-256 checksum
How to use checksums
1f18428c61cce538a8dc3c5ea1b6c8a779047d3aea86ec7f1160b917201c3f06
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Nov 4, 2026.

Transparency log

Release files / korvex-0.3.0-cp39-abi3-manylinux2014_aarch64.manylinux_2_17_aarch64.whl

Download URL korvex-0.3.0-cp39-abi3-manylinux2014_aarch64.manylinux_2_17_aarch64.whl
Size 310.5 kB
Tags CPython 3.9 Linux glibc 2.17+ ARM64 abi3
SHA-256 checksum
How to use checksums
00c997d94376bb8c9a839120b26e8e7898bd3bfb1d90e2f899adcba5911a4c31
BLAKE2b-256 checksum
How to use checksums
c90b0e51f7796e20bbcb4bd130830719961d63cbfec77684cffde3850868f2fd
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Nov 4, 2026.

Transparency log

Release files / korvex-0.3.0-cp39-abi3-macosx_11_0_arm64.whl

Download URL korvex-0.3.0-cp39-abi3-macosx_11_0_arm64.whl
Size 277.6 kB
Tags CPython 3.9 abi3 macOS 11.0+ ARM64
SHA-256 checksum
How to use checksums
eea8eb03ba7528c11035dde9d8e0632260068b80d157ab3f24ea1f312766fc3f
BLAKE2b-256 checksum
How to use checksums
cdec54aedd6ecd10140544e3b97d5c50973f25f572ecedf869b48a9e0e352f6d
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Nov 4, 2026.

Transparency log

Release files / korvex-0.3.0-cp39-abi3-macosx_10_12_x86_64.whl

Download URL korvex-0.3.0-cp39-abi3-macosx_10_12_x86_64.whl
Size 276.0 kB
Tags CPython 3.9 abi3 macOS 10.12+ x86-64
SHA-256 checksum
How to use checksums
f2fff9210675fe76e1f85d8c2ba6802fa87e454b7dc08ba7c967a85983aef80d
BLAKE2b-256 checksum
How to use checksums
753316ce656de9271e04f89b76cfb6a2ca756bbe8f5c94263aefc573c02ba98a
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Nov 4, 2026.

Transparency log

Security for korvex 0.3.0

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

Full provenance

All 6 files in this release have been uploaded with provenance metadata.

Select from 6 files

Attestation for korvex-0.3.0.tar.gz

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Nov 4, 2026.

Transparency log

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

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