System Design Interview Walkthrough: A Rate Limiter in 45 Minutes
System design frameworks are easy to find, and I've written one myself (the requirements, estimates, high level, deep dive, tradeoffs structure in how to pass system design without scale experience). What's much harder to find is a complete round actually played out, with the interviewer's reasoning visible at each step. So that's this article: one full 45 minute system design interview on a rate limiter prompt, minute by minute, including the steer moments where the interviewer redirects you mid-design. I've run a lot of these rounds and sat in the debriefs where the hire decisions got made, though practices vary company to company, so hold the specifics loosely at any given employer.
The prompt, delivered in one sentence: "Design a rate limiter for a public API." The brief is vague on purpose, because the ambiguity is part of what's being tested.
Minutes 0-5: requirements before anything gets drawn
These are the clarifying questions I'd hope to hear, with the answers I'd typically give as the interviewer:
- Is this a library embedded in each API server, or standalone infrastructure in front of them? (Standalone, at the gateway.)
- What are we limiting on: user account, API key, IP address? (API key for authenticated traffic, IP for anonymous.)
- What shape are the rules? ("100 requests per minute per key" to start, with different limits per pricing tier.)
- When a client exceeds the limit, do we reject or queue? (Reject with a 429, and tell them when to retry.)
- Roughly how much traffic? (10 million daily users.)
- How strict does enforcement need to be? If a burst slips a few extra requests through during a race, is that acceptable, or is this billing-grade accuracy? (Small overages are acceptable.)
In the loops I've run, these questions get graded in their own right, and reaching for the marker before asking anything was a downlevel signal I saw constantly. The strictness question is the standout: it shows you already see the central tension (accuracy versus latency) before a single box exists, and the answer quietly determines half of what comes later.
Minutes 5-8: the estimate that shapes the design
Back of the envelope: 10M users at maybe 50 API calls each per day is 500M requests daily, roughly 6,000 QPS on average, so plan for something like 30,000 at peak. Per-key state is a counter and a timestamp, call it 50 bytes, so 10M active keys is around 500 MB. The part that matters is the conclusion, spoken out loud: all counter state fits comfortably in memory, storage is a non-issue, and the genuine constraint is that this check runs on every single request with a latency budget of a millisecond or two.
Nobody in a debrief has ever audited a candidate's arithmetic in my presence, and being off by 2x is fine. The estimate earns signal through what you conclude from it, because "fits in memory" is the sentence that justifies the entire architecture that follows. (The numbers worth having memorized for this section get their own article in this series, The Only Math You Need for System Design Interviews.)
Minutes 8-18: a deliberately boring high level design
Narrated: every request passes through the gateway, where the middleware builds a key like ratelimit:{api_key}:{current_minute}, increments it in Redis with an expiry, compares the count against that tier's limit, and either forwards the request or returns a 429 with a Retry-After header (plus the usual X-RateLimit-Remaining headers so clients can back off on their own).
Then the algorithm families, named briefly and out loud: fixed window counters (simple, but bursty at boundaries, since 100 requests at 12:00:59 followed by 100 at 12:01:01 is 200 requests inside two seconds), sliding window log (exact but memory hungry), sliding window counter (a weighted compromise), and token bucket (controlled bursts, two numbers per key). My recommended move is to start with the fixed window design, surface the boundary burst flaw yourself, and offer token bucket as the upgrade if bursts matter.
Surfacing the flaw in your own design before being asked is, in my experience, among the strongest senior signals this round can produce, and it lands completely differently than having it extracted from you. The boring-first instinct is doing real work here too: a design you understand down to the byte survives probing far better than a fancier one you can only half defend.
Want to practice this on a real prompt, with feedback attached?
Minutes 18-35: the deep dive, and the art of taking a steer
Around the midpoint the interviewer takes the wheel, and this is the mechanic I most wish candidates understood. A steer is the interviewer telling you precisely which rubric box they still cannot fill in, so following it is almost always correct, while steering back toward rehearsed material reads badly every time. (Narration matters just as much here as in coding rounds: interviewers can't grade what they can't hear.)
First steer: "You've got a dozen gateway nodes now. How do you handle distributed counters?"
Taking it well looks like this. All gateway nodes share the central Redis, so the counter is already global, but the read-modify-write race is real: two nodes both read 99 and both admit a request. Fixed windows survive because INCR is atomic on its own. Token bucket needs its refill-and-check math executed as one atomic unit, which in practice means a small Lua script running inside Redis. When a single Redis box runs out of headroom, shard by key, noting that any given key lives on exactly one shard so counters stay coherent. Then raise the hot key problem unprompted: one huge customer means one huge key on one shard, and the honest mitigations (per-node pre-limits, or short-lived local caching of counts) all trade accuracy for load, which is exactly why the strictness question got asked in minute three.
Second steer: "What happens when Redis goes down?"
Fail open or fail closed, framed explicitly as a product decision as much as a technical one. Failing open protects availability but waves through exactly the abuse the limiter exists to stop; failing closed converts a Redis outage into a full API outage. The middle path is the one already drawn above: a conservative in-memory fallback limiter on each gateway node, plus a circuit breaker so you stop paying a Redis timeout on every request while the cluster is dark.
The steers are where the round mostly gets decided, and both answers trace back to requirements gathered in the first five minutes rather than to trivia. If either steer would have caught you flat, don't be too hard on yourself; they exist precisely because most candidates haven't operated this machinery live, and in my rounds "I haven't run this, but here's how I'd reason about it" scored fine, while invented war stories reliably collapsed by the second follow-up.
Minutes 35-42: tradeoffs and failure modes
I'd enter this section assuming everything on the board eventually fails (the grim darkness of the far future has nothing on a Redis cluster at peak load) and aim to show I know the order it fails in. The Redis round trip gives out first as traffic grows, since it rides on every request, so at 10x traffic I'd move counting onto the gateway nodes with asynchronous reconciliation and state the accuracy cost plainly. Then a handful of honest failure modes: thundering herd when a popular key's window resets (jitter the Retry-After values), clock skew between nodes corrupting window math, and what the 429 experience feels like for a legitimate but spiky client. In the debriefs I've sat in, this closing section carried surprising weight in senior versus mid-level decisions.
The last three minutes, and how to practice this
Minutes 42-45 belong to your questions for the interviewer, and genuinely curious ones (asking what the rubric weights most heavily at your target level is completely fair) land better than rehearsed flattery.
As for practice, a walkthrough like this one has a built-in limitation: the steer is interactive, and you can't rehearse being interrupted by reading, so timed reps out loud are what close the gap. A friend with this article open can play interviewer and deliver both steers verbatim, peer mocks on Pramp (now hosted on Exponent, with 5 free credits a month) work well, and interviewing.io offers paid human mocks if the budget allows.
If you'd rather practice against something that steers you mid-design the way a real interviewer does, and then grades the round afterward, that's what we built Preppable's system design mocks to do. Whichever medium you pick, the honest advice is the same one this article keeps circling: the reps have to happen out loud, under time, with something pushing back.
Practice this for real
Put this into practice on a real design question
Whiteboard the design the way you would in the round, then get structured feedback on the tradeoffs you named and the ones you skipped. Free to start, no credit card.
Not ready yet? Get new posts by email. We usually publish a couple times a week.
Unsubscribe any time. See our Privacy Policy.
About the author
Jordan Beland
Co-founder & CTO, Preppable
Principal architect with 10+ years designing and scaling production-grade Azure systems, with deep expertise in distributed systems and developer platforms. Has run countless interview loops from the interviewer side across coding, system design, and behavioral rounds, and sat in the debriefs afterward.
Connect on LinkedIn
