KIP-219 — improved quota throttle communication
Status: partial — see the KIP index.
What's missing
The broker never mutes the connection after a throttled response. kaas
computes throttle_time_ms and returns it, but continues reading the
socket immediately — so throttle enforcement relies on the client honouring
the advertised delay. A well-behaved Java/librdkafka/franz-go client backs
off exactly as it would against Apache; a client that ignores the field can
exceed its quota.
What the KIP changes in Apache Kafka
Before KIP-219, a quota-violating request was held on the broker for the
throttle duration before the response was sent — which interacted badly
with client-side request timeouts. KIP-219 changed the contract: the broker
sends the response immediately with throttle_time_ms set, then mutes
the connection's channel for the throttle window, so enforcement no
longer depends on client cooperation while responses stay prompt.
What kaas has
The signalling half, on accurate foundations:
- Quota accounting is a token bucket with debt-carry
(
crates/kaas-auth/src/quota.rs): overshoot goes negative and is carried forward rather than clamped at zero, so N concurrent clients can't each see a "full" bucket and burst at N× the configured rate. Themulti_client_contention_carries_debtunit test pins this. - Handlers surface the resulting delay as
throttle_time_msin responses (checked once per request on the Produce path — see Produce).
Channel muting is the tracked follow-up; the quota architecture is covered in Listeners, authentication, authorization and per-broker quota semantics in KIP-13.
How the partial state is verified
crates/kaas-auth/src/quota.rs unit tests (debt-carry, contention);
scripts/kafka-configs.sh exercises quota configuration end-to-end. The
absence of muting is verifiable by inspection — there is no mute path in
crates/kaas-protocol/src/.