-
Notifications
You must be signed in to change notification settings - Fork 0
Performance
All numbers are reproducible on your own hardware via npm run bench (and npm run bench:compare for the head-to-head). They are measured on the dev machine, not vendor claims, and vary run-to-run (~±10%). The full table — algorithms labelled, methodology, and every place ThrottleKit loses — lives in SCOREBOARD.md.
Node 24, reproducible via npm run bench:
checkSync(GCRA): ~3.1M ops/s, ~320 ns/op, allocation-free.-
check(async, GCRA): ~1.7M ops/s (~600 ns/op) — 2.7× faster after the sync-store fast path. - Token bucket
checkSync: ~2.5M ops/s; fixed windowcheckSync: ~2.1M ops/s. - Redis: exactly one
EVALSHAround trip per check.
npm run bench:compare — same machine, process, warmup, and iteration count; all on the allow path. The algorithm each library actually implements is labelled (a fixed-window counter and a GCRA cell are not the same guarantee even at equal ops/s).
- Sync: ThrottleKit is one of the few JS limiters with a synchronous API at all, and it's allocation-free.
-
Redis (loopback): roughly tied with
rate-limiter-flexibleon throughput and p50 (both one atomic Lua round trip), with a tighter tail (p999 ~1.6× lower — cachedEVALSHA+ a leaner script). - Async in-memory: the counter-based libraries are faster (~2–5M vs ~1.3–1.7M ops/s). That is the trade: their async edge is a plain fixed-window counter, while ThrottleKit's headline path is GCRA over a timing-wheel + CLOCK store — more real work per check. All contenders are far past real-world per-process need.
-
Postgres: a single bare check trails
rate-limiter-flexible's one-statement upsert (~3×, by design —PostgresStoreruns one generic transaction per strategy so the same proven transform drives every backend). Under load,twoTier(leased)over Postgres amortizes one transaction perbatchrequests into a ~34× throughput win (12.6k vs 366 ops/s).
A rate limiter's value is its correctness guarantee, not its microbenchmark. ThrottleKit publishes the cases where a leaner counter beats it precisely because the trade is deliberate: a bounded-memory GCRA cell with a smooth pacing guarantee and a proven distributed bound is worth a few hundred nanoseconds against a plain counter that offers neither. The benchmark harness is in the repo so you can confirm all of this on your own hardware.
ThrottleKit · MIT · 1.0 — API frozen under SemVer (Stability)
- Getting Started
- Choosing a strategy
- Frameworks & the edge
- Distributed & provable
- Federation
- Scaling & the Fleet
- Unified admission
- Pillar 4 — Weighted Fair Escrow
- Middleware integration
- Distributed adaptive concurrency
- Advanced limiting
- Overload, fairness & DDoS
- Operations
- Monitoring — ThrottleKit Lens
- Policy Plans
- Replay
- Performance
- Migrating
- Polyglot & Python
- GALE & TALE