InterviewPrepKit

Home / Learn / System Design

16 — The Learning Continues

This chapter is the compression: forty-six transferable rules of large-scale system design, extracted from the twenty-eight worked problems that produced them. The track is twenty-nine chapters; this one carries no problem of its own.

A rule is one line: a mechanism, plus the number that makes it true. For example: database load falls as (1-h), where h is the fraction of reads the cache answers, so each additional nine of hit rate divides database load by ten.

That rule has three parts: a mechanism (caching), a number (1-h), and something you can act on (the last few points of hit rate are worth more than the first thirty). Every row in this chapter’s rule tables has the same three parts. It is the rule, not the problem it came from, that transfers to a design question no chapter covers.

What you should be able to do when you finish. Name the pattern an unfamiliar problem belongs to, quote the arithmetic that decides it, and state which of your own assumptions the answer rests on.

Input and output. In goes a system design problem you have not seen, described in a sentence or two: “design a concert ticketing system”, “design a ride-hailing dispatcher”. Out comes a short, defensible chain:

  1. Five numbers, written down before anything else.
  2. One fork, taken because of the first of those numbers.
  3. Three independent checks, run in every case.
  4. A named architecture, with the binding constraint stated explicitly.

Worked the chart applied to a problem with no chapter runs that chain end to end on concert ticketing, from the arithmetic to the architecture.

Every idea this chapter uses is defined here before it is used. Follow a link when you want the derivation with its numbers; you should not need to follow one to understand a sentence on this page. The vocabulary everything else is written in defines the terms of art up front.

This chapter sits at the seam of the study plan. Chapters 01-15 are Volume 1. 17 through 29 are Volume 2. 1b volume 2 as twenty five more and Volume 2 the binding constraints are written to be useful both before you read Volume 2 and after.

Read it once now. Re-read Which pattern does this smell like and The numbers you cannot recompute under pressure the morning of the interview.

0. The vocabulary everything else is written in

Every term of art the rest of the chapter uses is defined here in plain English. Using a mechanism’s name without being able to define it is a common way to sound like you do not understand it.

Read it once, then treat it as a lookup table: jump back here whenever a later section uses a word you cannot define.

Terms about the systems themselves

Terms about storing and finding data

Terms about correctness when there is more than one machine

Terms about streams, queues and time

Terms about storage economics, money and the rest

Two names for people and services appear repeatedly: APNs is Apple’s push notification service, and a PSP is a payment service provider — the company that actually talks to the card networks on your behalf.

1. Volume 1 as twenty-one rules

The first of the two rule tables: twenty-one mechanisms from Volume 1, each with the chapter that derives it and the one line you should be able to say about it without preparation.

The one-line rule is the deliverable: if you can state it without looking, you know the mechanism. The name and source are the handle to reach for in an interview and where to check the arithmetic; nobody will ask you to recite them.

PatternDerived inThe rule, in one line
Estimate first02The output is not a number, it is the name of the binding constraint. If the answer would not change the design, do not compute it
Cache01, 08Latency is linear in hit rate; database load falls as (1-h), so each additional nine divides it by ten. The last few points are worth more than the first thirty
Read replicas01Buys read throughput, costs read-your-writes. Route a writer’s own reads to the primary for one RTT afterwards
Shard last01Six cheaper things come first. When you do shard, the key must be the one reads already use, or every query is a scatter-gather
Consistent hashing05, 05mod N moves 94% of keys on a resize; a ring moves 1/(N+1), which is optimal, not merely small
Virtual nodes05V buys variance, not mean: load CV falls as 1/sqrt(V). The fraction that moves is 1/(N+1) at every V
Hot key05, 08Partitioning cannot help one hot key, by construction. An in-process LRU on every app node can
Quorum06W + R > N is the entire knob. It trades availability for consistency, and only during a partition
Causality06, 15Version vectors only when there is no single owner per object. With one owner, a compare-and-swap on an integer does the same job 120x cheaper
Conflict resolution15Last-write-wins is silent data loss, not a policy. Merge, keep both, or ask a human — and say which
Anti-entropy06Comparing two replicas is O(log n) with a Merkle tree and O(n) without. That is the difference between hourly and never
Queues01Anything off the user’s critical path goes async. The queue is not a buffer, it is where backpressure is allowed to live
CDN and edge01, 02Forced by bytes and by the 150 ms cross-continent RTT, never by QPS. At video scale, egress is the business
Rate limiting04A correctness control, not a cost control. Token bucket unless you can name why not
Backpressure and jitter04, 15An unjittered retry or reconnect is a denial of service you performed on yourself
Idempotency04, 08, 15Every retryable write needs a key. Content addressing gives you one for free: the name is the checksum
Unique IDs07Uniqueness and density are different products. A shortener needs density; a database needs uniqueness and sortability
Probabilistic filters06, 089.6 bits per entry at 1% false positives turns “is it in this 10-million-item set” into a memory reference
Delta and cursors15Ship what changed since a cursor, never the whole state. Resumability and idempotency come free with the sequence number
Coding vs replication02, 15RF 3 is 3x; RS(10,4) is 1.4x. On cold data that ratio is most of the storage bill
Two stores, no transaction15You cannot make them atomic, so order the writes so the survivable failure is the one that happens, and garbage-collect the debris

If you can say fifteen of those twenty-one lines cold, you can hold a system design conversation about a problem nobody has written a chapter for.

Three Volume 1 rules, applied to a problem the track never covers

Some rows above carry their own worked instance, because the number is the instance — “94% against 1/(N+1)” is not abstract. Three rows are genuinely abstract, though, and they are the ones a first reader cannot picture. Here they are on a problem no chapter in this track contains: letting users attach photos to restaurant reviews.

Assume 3 million photos uploaded a day at 2 MB each, and 500 million review page-views a day. Every number below follows from those two.

“Estimate first” — the output is the name of the binding constraint, not a number. Run the arithmetic:

photo writes/s      3,000,000 / 86,400          =  34.7  /s
bytes/day           3,000,000 x 2 MB            =  6 TB/day
bytes over 3 years  6 TB x 365 x 3              =  6.57 PB
read : write        500,000,000 / 3,000,000     =  167 : 1

Thirty-five writes a second is nothing; a single database absorbs it without noticing. The constraint is bytes, not requests — 6.57 petabytes over three years, of data nobody edits after upload. That single sentence is what the estimate was for. It tells you the interview is about storage tiering and erasure coding, and that any minute spent on write throughput is a minute wasted. The 167:1 ratio then tells you the read path is a caching and CDN problem, which is the second thing worth knowing and not the first.

“Queues” — anything off the user’s critical path goes async. The user’s upload must return as soon as the bytes are durable. Everything after that — generating thumbnails, running the content-safety scan, extracting the location tag — is work the user is not waiting for, so it goes on a queue. The rule’s second half is the part people miss: the queue is not there to smooth out a spike, it is there so that when the thumbnail workers fall behind, the backlog has somewhere legitimate to sit instead of pushing latency back into the upload call. If the thumbnail fleet dies for an hour, uploads keep succeeding and thumbnails appear late. That is the whole reason the queue exists.

“Two stores, no transaction” — order the writes so the survivable failure is the one that happens. The photo bytes go in a blob store and the review row goes in a database, and there is no transaction spanning the two. So write the bytes first, then commit the row. If the process dies in between you have paid for bytes nobody references — an orphan — which a background sweep can find and delete. Commit the row first and a crash leaves a review pointing at a photo that does not exist, which the user sees as a broken image and which no sweep can repair. Same two writes, opposite failure, and the only thing you changed was the order.

1b. Volume 2 as twenty-five more

The second rule table is organized around a different question. Volume 1 answers how do I build the mechanism. Volume 2 mostly answers which constraint is actually binding, and what does the honest version of this cost.

The columns work exactly as in Volume 1 as twenty one rules: name, source, deliverable. Read the table once before chapter 17 as a preview and once after chapter 29 as recall; the rows are written to work both ways. On the first pass, a row you cannot picture is a row whose chapter you have not read yet — that is expected, and the second column tells you where to go.

PatternDerived inThe rule, in one line
Flattening 2-D into 1-D17, 17A B-tree is one-dimensional and a query disc is not. Every cell scheme is a candidate generator, and the exact distance test is always the last gate
Bounded vs unbounded candidates18Index space only when the candidate set is unbounded. A 200-element friend list is a 20 us scan that returns exactly the right set and leaks nothing
Precompute what does not move19Split an artifact by its rate of change. Topology changes when a road is built; the metric changes every two minutes, and only the cheap half may be recomputed at the fast rate
The log, not the queue20Give the read position to the consumer and the broker’s job collapses to appending bytes. Replay and a second consumer group then cost nothing
Headroom, not throughput20Recovery time is backlog / (capacity - offered load). A fleet sized at exactly its load never drains, at any throughput
Cardinality, not volume21A label is legal only if its value set is bounded and does not grow with traffic. One unbounded label is 2,134x the fleet, and the pull request was one line
Symptoms, with a derived threshold21, 21A per-series threshold’s false-positive rate scales with fleet size; burn rate against an error budget scales with incidents. 14.4 = 0.02 x 720 is arithmetic, not folklore
Shed at the door21A queue whose wait crosses the sender’s timeout raises the arrival rate. Reject where the backlog already has a home, and shed new work before work something depends on
Event time, and restatement22, 22Price both sides of the wait. When the best single watermark still misses the target, close fast and amend — and emit absolute values so a replay is a no-op
Salt the provably hot key22A ring cannot split one key, so change the key. Salt only the keys above the uniform share and the merge stage is 512 rows/s, which a laptop runs
The check and the write are one step23UPDATE ... WHERE remaining > 0 beats every lock because the predicate runs under the lock that statement already holds. The defect is never “we forgot a lock”
Saga, not two-phase commit23, 282PC’s steady-state cost is mild and its failure is not: a dead coordinator leaves participants holding locks with no authority to release them
Compensation is not rollback28The intermediate state was visible, so order the fallible step first and make every later failure a retry rather than an apology
Pay the fan-out once, deliberately24Every subsystem either pays the fan-out or dodges it. Name which, per subsystem, instead of letting the multiplier land where it happens to
Isolation by partition, not by predicate24WHERE owner = me survives until someone writes a new code path. Another tenant’s data should not be in the structure being read
Erasure coding, and its actual bill25, 251.4x against 3x looks like a dominance. You pay in tail latency, because k fetches make the object’s p99 the fragment’s p99.9, and in small objects below k x block
Immutability is the design25, 28A parity update is a delta, so it is not idempotent. Refusing in-place writes is what makes every retry in the system safe, and a correction becomes a new entry
Accuracy is a function of position26The same absolute error is 500x wrong at rank 10 and invisible at rank 10 million. Exact at the head, bucketed in the tail, and say which one the caller got
Decomposable or not26Top-k is a selection and shards perfectly; rank is a global count and no per-shard statistic reconstructs it. Ask which one a query is before you shard
Double-entry27Every transaction sums to zero, so a half-written movement has no representation. It catches asymmetry and never duplication — that is idempotency’s job
Money is an integer27Minor units end to end, Decimal only for sub-unit intermediates, and every division redistributes its remainder so the parts sum to the whole
The unknown outcome27Commit the key before the external call, and on a timeout ask what happened rather than re-sending. Every unknown becomes a detected unknown with an owner
A balance is a memoized fold28The log is the truth and the column is a cache of it, written in the same transaction. Snapshot on a count of entries, never on a clock
Determinism29No wall clock, no floats, no hash iteration order, no allocation, one thread. Then a hot standby is not a protocol, it is the same program reading the same log
Utilization is a latency knob29Queueing delay is rho / (1 - rho) service times, so you shard a system with no throughput problem in order to choose a smaller rho

One discipline runs underneath a third of that table and is worth stating on its own, because it is the single most common arithmetic mistake in this round:

State whether a rate is offered load or service capacity at the moment you derive it, and never divide one by the other without saying which is which. Both are measured in requests per second, which is why they get mixed up, and a design that divides one by the other produces a fleet size that is wrong by the ratio between them.

That discipline is stated in ch 03, spent on an ingest path in ch 18 and on partition counts in ch 20, and extended to fleet counts in ch 21, where the same rule applies to machine counts: compare capacity against capacity, or a high-availability configuration against a high-availability configuration, never one of each.

Three Volume 2 rules, applied to a problem the track never covers

Three rows above are stated as principles rather than as numbers, which makes them the hardest to picture. Here they are on a multi-tenant customer-support ticket system — many companies, each with their own agents, their own customers and their own tickets — which no chapter in this track builds.

“Pay the fan-out once, deliberately” — name which subsystem pays, per subsystem. One reply on a ticket has to reach several places: the agent’s inbox view, the customer’s email, the tenant’s analytics roll-up, and the full-text search index. Each of those either pays the fan-out — writing a copy per destination at reply time — or dodges it, by storing one copy and having each reader come find it.

The point of the rule is that you must decide this per subsystem and say so, not let the multiplier land wherever the first implementation happened to put it. Reasonable answer: the agent inbox dodges it (agents query by tenant, and the query is cheap); email pays it, because email is a copy by definition and there is no dodging available; analytics dodges it by reading the same log the inbox reads; search pays it, because an index entry per ticket is the only structure that answers a search fast. Two pay, two dodge, and you can defend each one. The failing answer is not “we fan out” or “we do not” — it is having no per-subsystem answer at all.

“Isolation by partition, not by predicate” — another tenant’s data should not be in the structure being read. The predicate version is one global ticket table with WHERE tenant_id = ? on every query. It is correct today and it stays correct only for as long as every future code path remembers the clause. One forgotten WHERE is a cross-tenant data leak, and no test that runs against a single tenant’s fixtures will ever catch it. The partition version gives each tenant its own index, so the other tenants’ rows are not in the structure the query reads at all. Then a forgotten filter returns fewer results, not somebody else’s. Access control by partition survives refactors that access control by predicate does not.

“Decomposable or not” — ask which one a query is before you shard. Two questions an agent dashboard asks look equally innocent:

Same dashboard, same table, and one of the two queries silently becomes a scatter-gather across the entire fleet the moment you shard. The rule says to ask the question before you choose the layout, not after.

2. The twenty-eight problems, and what each one is actually for

Every problem in the track maps to the single mechanism it exists to teach and the single mistake it exists to catch — which is how to pick a chapter by what you need rather than by its title.

No chapter exists for its own sake. Each one is a delivery vehicle for one mechanism you would otherwise never derive, plus one thing candidates reliably get wrong, and compressing a chapter to those two things is the test of whether you read it or skimmed it.

The two tables below hold fifteen problems and thirteen, which is twenty-eight. This chapter is the one that carries no problem of its own.

Volume 1 — the mechanisms

These fifteen chapters each introduce a mechanism.

#ProblemWhat it exists to teachThe reliable mistake
01Scale to millionsThe ladder, and that sharding is the last rung, not the firstSharding at step 1
02EstimationAn estimate names the binding constraint; the number is a by-productComputing something that changes no decision
03The framework45 minutes has a shape, and you pick the deep diveWaiting to be told what to go deep on
04Rate limiterFour algorithms that differ only in exactly how wrong they are at a window boundaryTreating the client contract as an afterthought
05Consistent hashing1/(N+1) against 94%, and that virtual nodes buy variance“It minimizes reshuffling,” with no number
06Key-value storeLeaderless replication end to end: quorum, siblings, Merkle repairClaiming vector clocks resolve conflicts. They only detect them
07Unique ID generatorA bit budget is a design decision, and clocks run backwardsAssuming a monotonic wall clock
08URL shortenerKeyspace arithmetic, and that a short code is obscure but never secretPicking a length with no arithmetic behind it
09Web crawlerPoliteness as a scheduling constraint, and that “dedup” means two unrelated thingsTreating URL dedup and content dedup as one problem
10Notification systemRouting as a cost lever, over a delivery path you do not ownAssuming your own delivery guarantees apply to APNs or a carrier
11News feedFan-out on write against fan-out on read, and that the celebrity decides itPicking one fan-out mode for the whole corpus
12ChatConnection tiers, per-conversation ordering, and delivery semanticsSizing a socket tier by RAM
13Search autocompleteRebuild beats update, and the client deletes most of the trafficDesigning a server for keystrokes the client should never send
14YouTubeTranscoding as a DAG, and that egress is the businessSpending the interview on the player
15Google DriveContent boundaries against offset boundaries; two stores with no transaction between them“We only sync the diff,” with no definition of a boundary

Chapters 09 through 14 introduce almost no new mechanism. They recombine Volume 1 as twenty one rules’s list under different constraints — which is exactly the claim you are being tested on, that the mechanisms transfer.

Chapter 15 is the exception, and Volume 1 as twenty one rules’s own second column says so. You can check this yourself against the table above rather than taking it on trust.

Count the appearances of 15 in §1’s Derived in column: seven of the twenty-one rows. Now count the rows where 15 is the only citation: three — conflict resolution, delta and cursors, and two stores with no transaction. No other chapter is the sole source of more. Only chapter 01 matches it, with read replicas, shard-last and queues.

So the recombination claim has a boundary, and it is worth stating rather than smoothing over. The six problems before 15 are recombinations. Chapter 15 earns three rules of its own, by being the first problem in the track where two stores must agree without a transaction between them.

If a chapter contributes a rule nobody else derives, saying it introduced no new mechanism would leave three rows of §1 with no home.

Volume 2 — the binding constraints

These thirteen chapters mostly reuse those mechanisms and teach instead which constraint decides the design.

#ProblemWhat it exists to teachThe reliable mistake
17Proximity serviceEvery geospatial index is a scheme for flattening two dimensions into one without losing localityQuerying one cell when the disc cannot fit inside one
18Nearby friendsThe same points, moving — which makes it a presence system with a payload, not a spatial problemDurably storing a value that is wrong 30 seconds later
19Google MapsPrecomputation beats search by 61,800x, and the precomputation must be split by rate of change“Run Dijkstra,” with no cost estimate
20Message queueChapter 01’s queue box, opened: it is an append-only file and the consumer owns the offsetTreating throughput as the health metric instead of d(lag)/dt
21Metrics and alertingThe system is sized by active series, and an alert threshold is derived from an error budgetAdding a label, then paging on a per-series threshold
22Ad click aggregationCounting when the count is multiplied by a price and mailed to a customerBelieving a single watermark can be tuned to hit the accuracy target
23Hotel reservationEight writes a second, and the entire interview is one race conditionA sharded pipeline for 8 writes/s, then a payment call inside the transaction
24Distributed emailWhere the fan-out lands, subsystem by subsystem, and what a per-user index buysStoring a copy per recipient; “we add Elasticsearch” with no index sized
25Object storageA small mutable index against an enormous immutable byte pool, and what coding really costsQuoting eleven nines as if it came out of a model
26Gaming leaderboardTop-k is a decomposable selection; rank is a global aggregate. Only one of them shardsAnswering both with ZREVRANK and stopping
27Payment systemThe books, and the three seconds in which nobody knows whether the card was chargedRetrying the charge instead of asking what happened
28Digital walletThe same ledger with no third party, where one balance row does 1,333 writes/sAssuming 2PC is fine because you own both shards
29Stock exchangeDeterminism inside a budget of 11.55 microsecondsSharding the matching engine for throughput it does not need

Volume 2 is organized by constraint rather than by mechanism, and three of its chapters are the corners of the space. Ch 23 is pure correctness at a scale that is a rounding error; ch 29 is the same correctness inside a microsecond budget; ch 25 is durability at exabyte scale where the budget is dollars per petabyte-month. Each of those three chapters says so about the other two. Placing an unfamiliar problem against those three corners is faster than pattern-matching it against a mechanism.

3. Which pattern does this smell like?

An architecture for a problem you have never seen can be chosen with one number rather than intuition — and the failure mode to prevent is reaching for a pattern before you have any numbers at all.

Everything below is keyed off five questions you should have asked and answered in the first eight minutes (ch 03):

  1. Read:write ratio — how many reads the system does per write.
  2. Consistency, field by field — what must be current, and what may be stale.
  3. p99 latency target, and where in the world the users are.
  4. Retention — how long the data must be kept.
  5. Growth — over two years.

Only the first of those five genuinely dispatches. “Dispatches” means it decides which further question you ask; the other four are checks you run in every case, and the gates below are where they land.

The chart reads top to bottom. You enter at the box that says write the five numbers down. You branch once, on the read:write ratio. Each branch asks one follow-up question, and you land in one of six leaves. Every leaf names an architecture and the chapter that prices it. There is nothing else in the chart — no components, no data flow, no arrows meaning “sends a request to”.

flowchart TD
    A["Write the five numbers down FIRST<br/>read:write · consistency per field · p99 and where users are<br/>retention · growth (ch 03 step 1)"] --> B{"read : write"}

    B -->|"under ~10:1"| W{"Is a write a NEWER VALUE<br/>or a NEW FACT?"}
    W -->|"newer value,<br/>supersedes the last"| W1["One slot per key, overwritten.<br/>A 10-deep queue serves a fix 5 TTLs stale.<br/>ch 18 section 12"]
    W -->|"new fact,<br/>must be counted"| W2["Append-only log, then windowed aggregation.<br/>Dedup key plus absolute-value upsert,<br/>never INCREMENT. ch 20, ch 22"]

    B -->|"~10:1 to ~100:1"| M{"Does a small hot set<br/>cover most of the reads?"}
    M -->|"yes, Zipfian"| M1["Cache-shaped after all.<br/>ch 08 at exactly 10:1 buys h = 0.962<br/>with 10 GB of RAM"]
    M -->|"no, flat"| M2["Build both paths and say so.<br/>The middle band is a finding,<br/>not a failure to decide"]

    B -->|"over ~100:1"| R{"Does ONE key carry a<br/>large share of the reads?"}
    R -->|"no"| R1["Shared cache plus replicas.<br/>Each extra nine divides DB load by ten.<br/>ch 02 estimation 5"]
    R -->|"yes"| R2["Hot key. In-process LRU, or replicate<br/>that one key everywhere. Partitioning<br/>cannot help: one key, one hash. ch 05"]

The six leaves in words

The chart is readable without squinting at it if you take the three branches one at a time.

Write-heavy, under about 10 reads per write. The follow-up question is whether a write is a newer value or a new fact.

The middle band, about 10:1 to about 100:1. The follow-up question is whether a small hot set covers most of the reads.

Read-heavy, over about 100 reads per write. The follow-up question is whether one key carries a large share of the reads.

Why the chart has no colours

Every other diagram in this track uses chapter 01’s published key: blue is the authoritative copy of the data, green is read capacity, orange is a box forced by something other than processor time, and red is the one rung you cannot undo.

That key describes components. This chart has no components. Its boxes are a question, three more questions and six answers, so colouring them can only mislead: blue would land on the entry box, green on an append-only log that is itself the authority, orange on a cache, and red on a hot key, which is among the most undoable conditions in the book.

A decision chart is not an architecture diagram, and the key does not apply to it.

Five things the chart is deliberately saying

The three gates the chart deliberately does not contain

The remaining three questions do not branch, so they are not in the chart. They are independent gates: checks that either fire or do not fire, in any of the six leaves above. A gate that fires changes the design regardless of which leaf you landed in.

Drawing them as further levels of a tree would make a flat checklist look like a decision procedure, when only the read:write node in that tree actually carries a number. Run them as a list, every time, in every problem.

Each gate below is a yes-or-no question, the number you check it against (with the chapter that derived it), and what changes in the design when the answer comes back yes.

GateThe number that decides itIf it fires
Does the working set — the data actually touched by live traffic — fit in one machine’s memory?Default to a 128 GB commodity box and say so (ch 02). Every business on Earth is 60 GB (ch 17); every road on Earth is 10.2 GB (ch 19); a 5,000-hotel chain’s forward inventory is 900 MB (ch 23)Do not shard. Replicate identical full copies for reads, and spend the interview elsewhere. This fires far more often than candidates believe
Is the p99 budget under one cross-continent round trip?150 ms, and a page needing two sequential round trips is 300 ms against a 200 ms budget (ch 03)Regional replicas, a CDN, or precomputation at the edge. Physics, not preference
Can two writers touch the same object?With one owner per object, a compare-and-swap on an 8-byte revision number replaces a 960-byte version vector — 120x smaller (ch 15). With no single owner, you are in ch 06Replication stops being a cost question and becomes a correctness question. This is the gate people skip, and it is what makes chapters 06 and 15 different chapters

4. Worked: the chart applied to a problem with no chapter

The claim in The twenty eight problems and what each one is actually for is that the rules transfer. This section tests that claim on concert ticketing, which the track never covers: Which pattern does this smell like’s fork and its three gates run end to end, so you can see what the procedure produces.

The problem, in one line: 50,000 people want to buy tickets to the same concert, and they all arrive at once.

Start where the framework says to start, with the arithmetic. The input is two lines of product description. The output is the six quantities below, and the last of them turns out to be the design.

assume  a 50,000-seat venue, 500,000 buyers arriving in the first 60 s,
        each refreshing the seat map every 5 s

seat-map reads/s at peak
  500,000 / 5                           =  100,000
purchase attempts/s, if every buyer tries once inside that minute
  500,000 / 60                          =  8,333
read : write
  100,000 / 8,333                       =  12
successful writes over the entire event, one per seat
  50,000
failed purchase attempts, since 500,000 buyers chase 50,000 seats
  500,000 - 50,000                      =  450,000
failure rate of the purchase call
  450,000 / 500,000                     =  0.9

Now walk the fork, and then the three gates, in that order.

The domain then overrides exactly one branch, and that is the part worth noticing. The chart’s action when two writers collide is “keep both versions”. Here you cannot: a seat is not a document that can be merged. So the losing writer gets an HTTP 409 Conflict and picks another seat.

The last line of the arithmetic is the actual design. Ninety percent of purchase calls must fail. The error path is not an edge case, it is the dominant response of the system — nine out of every ten times the endpoint is called, its job is to say no politely and tell the buyer what to do next.

That reframes the problem away from throughput and onto admission control: a virtual waiting room that lets buyers through at the rate the seat inventory can absorb. It is ch 04’s rate-limiter client contract applied to a product surface.

flowchart LR
    U["Buyer"] --> CDN["CDN: seat map<br/>cached, stale by design"]
    U --> WR{"Virtual waiting room<br/>admission control"}
    WR -->|"admitted at inventory rate"| P["Purchase<br/>compare-and-swap on seat version"]
    WR -->|"rate exceeded"| Q["429, wait"]
    P -->|"version matched"| OK["Seat booked"]
    P -->|"lost the race"| C["409 Conflict, pick another seat"]

One fork gave you a second question, three gates gave you the shape, one number gave you the actual problem, and the domain overrode exactly one branch. That is what the chart is for. It is not a decision procedure, it is a way to stop guessing.

5. The numbers you cannot recompute under pressure

What follows is a recall sheet of forty-odd derived numbers, each paired with the decision it makes. The derivations themselves are slow: every one of these costs a minute or two to rebuild on a whiteboard, and the interviewer stops learning anything new from watching you do so after the second time.

Primitive against derived, because they are memorized differently. A primitive is a hardware constant — how long a memory reference or a disk seek takes. Those live in Latency numbers and what each one forbids, with the full memorization table in Numbers worth memorizing cold. A handful appear below only because a later row depends on them.

Everything else here is derived: a number this track produced by combining primitives with an assumption. Derived numbers are the ones you cannot rebuild in your head inside a forty-five-minute conversation, which is why they are worth carrying.

The only column that matters in an interview is the last: what decision the number makes. A number that decides nothing is not on this sheet.

Volume 1

These are the numbers Volume 1 produces, in chapter order.

NumberValueFromWhat it decides
Seconds per day86,400 -> 1e502Every per-day to per-second conversion, at 16% error you state once
Memory reference100 ns02In-memory work is free at any web scale
SSD random read100 us per read; a device does 500 k-1 M IOPS at depth02100 sequential random reads is 10 ms of pure I/O. Do not divide 1 by 100 us to get a device ceiling
Datacenter round trip500 us02Ten chained internal calls cost 5 ms before any work happens
Disk seek10 ms, so 100/s per spindle02Why B-tree depth and LSM compaction are worth arguing about
Cross-continent RTT150 ms02You cannot serve Europe from California. This one number forces multi-region
Sequential NVMe~1 GB/s15A 4 TB index scan is 1.1 machine-hours, which makes mark-and-sweep GC cheap
Cache economicsDB load = QPS x (1-h)02Each additional nine divides DB load by ten: 90 -> 99% is 10x, not 4x
mod N resize94% of keys move05The single number that justifies consistent hashing existing
Ring resize1/(N+1), so 5.9% at N = 1605Optimal, and independent of the virtual-node count
Virtual nodesCV ~ 1/sqrt(V), so 7% at V = 20005How many virtual nodes, and what they actually buy
QuorumW + R > N06The only consistency knob in a leaderless store
Merkle comparisonO(log n) vs O(n)06Whether replica repair is a background job or a fantasy
Snowflake rate4,096/ms/node, so 4.1 M/s/node07ID generation is never your bottleneck; stop designing it
2^41 milliseconds69.7 years07Why 41 bits of timestamp, and when your epoch runs out
Base-62 code space62^7 = 3.52e12 = 96.5 years at 100 M/day08Seven characters, derived rather than remembered
Birthday boundFirst collision at 1.177 x sqrt(M)08“Collisions are rare” is usually off by six orders of magnitude
Bloom filter9.6 bits/entry at 1% FP08A 10 M-domain blocklist is 12 MB, so it fits in every process
Chunking on insertfixed blocks 100%, CDC 4%8a overwrite is fine insert loses everything for the 100% and the 50,000x, 8b how content defined chunking survives it for the 4%Offset boundaries versus content boundaries, and 50,000x amplification
Coding vs replicationRF 3 = 3x, RS(10,4) = 1.4x15On a 100 PB corpus that dedups to 75 PB: 225 PB replicated against 105 PB coded, so coding saves 120 PB. Quote the deduplicated figure or the saving does not reproduce
Connection tiers20 M sockets = 200 GB = 40-200 boxes02Sized by file descriptors, handshake CPU and blast radius — never by RAM

Volume 2

These are the numbers Volume 2 produces, again in chapter order.

NumberValueFromWhat it decides
Geohash character5 bits, base32; precision 6 is 1,221 x 610 m17At 500 m radius the disc fits inside a precision-6 cell with probability zero, so the query is nine cells
k-ring — the k rings of hexagons around a centre cell1 + 3k(k+1) cells, k = ceil(r / (1.5a))17At r = 1 km: 2.0x overfetch against geohash’s 5.9x, or 68x if geohash stays on character boundaries. Compare the two schemes at the same radius or the comparison means nothing. A k picked by eye misses a crescent 1.5 m wide
World road graph205 M nodes, 512 M directed edges, 10.2 GB19Every road on Earth is one box, so distributed shortest path is off the table
Dijkstra vs contraction hierarchies — precomputed shortcut edges that let a query skip most of the graph30.9 s against 0.5 ms, 61,800x19Precomputation, not a better heuristic — A* only buys 7.24x and the ellipse bounds it
Tile pyramid4^z, so the bottom two zoom levels are 15/16 of it19Where you stop at the bottom is the entire cost of a tile scheme
Log against table-as-queue8 random page I/Os against one append: 320x20One NVMe device instead of 328, and a second consumer group for 131 KB
Drain timebacklog / (capacity - offered): 150 s at 20% headroom, 600 s at 5%20Cutting headroom 4x multiplies recovery 4x on identical hardware
Active series2 KB each; one unbounded label is 2,134x the fleet21Whether a label is allowed at all. $8,760/year becomes $18.7 M
Gorilla encoding — delta-of-delta on timestamps, XOR on values16 B down to 1.40 B, 11.4x21Why samples of one series must be stored adjacently. A general key-value store has no two samples of a series next to each other to compress against, and writes 161x-1,500x more to disk depending on compaction strategy
Burn-rate thresholdbudget_fraction x 720 / window_hours; 2% over 1 h = 14.421Every row of the alerting table, and a 51.8 s detection time you did not have to choose
WatermarkBest single value is 0.30%, at least 3x over budget; 30 s plus amendment is 0.011%22That a single-horizon pipeline cannot bill, however well you tune it. Quote 0.30% as a floor — “at least 3x over” — not as a tuned optimum
Hot partition10% of traffic on one key is 7.30x at P = 64; salt 16 gives 1.30x22Salt only the provably hot keys and the merge stage takes 512 rows/s, which one machine runs
Booking transaction5 ms gives 200/s on one row; a 3 s gateway call inside it gives 0.33/s23A 601x collapse. The external call goes outside the transaction, always
Per-user inverted index774 B per message, 7.7% of that message’s text; 44 MB per mailbox24An index is affordable. A global one costs 300,000,000x on the read, and that factor is the user count
RS(10,4)1.4x, tolerates 4; 19.1 nines modelled against 11 advertised25The gap is correlated failure. Rack diversity alone is worth 16 orders of magnitude
Small-object linek x block = 10 x 4,096 = 40 KB25Below it, code the extent rather than the object. IOPS, not storage, is the real reason
Scatter-gather tail1 - 0.99^S: 47% at 64 shards, 99.4% at 51226When fan-out stops being an answer, on a query whose per-shard cost is 2% of a core
Ledger invariantSUM(amount_minor) = 0 per currency; 9.6 s on the open partition27Drift detected in five minutes rather than at the quarterly audit
One balance row1,333 writes/s, of which 500 us of the 750 us lock hold is the replica ack28Durability is what serializes, not the hardware. 16 buckets take it to 47% utilization
Tick-to-trade8.70 + 2.85 = 11.55 us, of which the sequencer is 4.5 (39%)29Which microsecond to attack, and that the biggest one is a durability decision
Kernel network stack13.2 us round trip = 114% of that budget29Bypass is bought for the jitter, not the mean — and it costs one spinning core

The point of these tables is not recall, it is speed. Every one of these is a number you would otherwise spend ninety seconds deriving in a forty-five minute conversation, and the derivation adds nothing the interviewer wants once you have shown you can do it twice.

6. Seven failure shapes, which is all of them

Twenty-seven of the twenty-nine chapters carry a failure-modes table — every one except ch 02, which is an estimation drill, and this one — and across all of them the same seven shapes recur.

Learning the shape is worth more than memorizing the instances, because the shape tells you what to alert on. An instrument you did not decide to build is an instrument you do not have during the incident.

The instances are there so you can see the shape repeat across unrelated domains — skim them, do not memorize them. The tell is the observable signal that says this failure is happening right now, and the guard is what prevents it. In an interview you spend the tell and the guard; the instances are only evidence that the shape is real.

ShapeInstancesThe tellThe guard
Step function on dependency lossCache tier dies and the database goes 26x in one second (08); one lagging consumer evicts the page cache and every other consumer’s reads become disk reads (20)Load on the dependency, not on the thing that failedProvision the dependency for a survivable multiple; in-process LRU; coalesce misses per key
StormRetry storm (04), reconnect storm and cursor stampede (15), rebalance storm (20), a 20x replay burst after a ten-minute partition (21), 500 subscribers detecting one dropped packet at once (29)A spike in request or connection rate with no matching spike in workExponential backoff with full jitter, a client-side cap, and a server-side admission limit. Never a queue whose wait can exceed the sender’s timeout
Silent data lossLast-write-wins and a dropped reference count (15), a pruned version vector (06), unclean leader election truncating 234,240 records with offsets going backwards (20), a Bloom false positive discarding a real billable click (22)Nothing. There is no error, which is what makes it the worst classAn invariant you can check offline, and a resolution rule that never discards
Hot keyViral link (08), celebrity fan-out (11), a chunk in two million accounts (15), a 10% advertiser at 7.30x (22), the top-10 board (26), one merchant’s balance row (28)Requests per second per key, which most dashboards do not showLocal LRU or a TTL cache for hot reads; salting or sub-balance buckets for hot writes. Partitioning cannot help either one
ClockSnowflake rewind (07), timestamp-ordered conflict resolution (15), out-of-order samples rejected by an append-only chunk encoder (21), game-server skew reordering equal scores (26)Duplicate IDs, or an ordering that disagrees with causalityMonotonic clocks locally; timestamp at the one service that owns the order; never order across machines by wall clock
Unbounded growthChange journal and orphaned chunks (15), the raw click log (08), noncurrent object versions at $560,000/month with no lifecycle rule (25), pending holds a stopped sweeper never releases (23)A side table growing faster than the thing it describesA retention policy and a GC pass, both decided at design time rather than during the incident
Drift between two computations of the same quantityStreaming aggregate against the batch recount (22), the ledger against the payment provider’s settlement file (27), a stored balance column against the sum of the entries it should equal (28), a hot standby’s output hash against the primary’s (29)Nothing at all, until something compares them on purposeAn independent recount on a schedule, a threshold aged — required to hold for a while before it pages — and a stated rule for which side wins

Three of these seven are invisible without an instrument you had to decide to build — silent data loss, hot keys, and drift — and those are the three an interviewer is most impressed to hear you name unprompted. All three share the same tell, which is that nothing is on fire: no error rate moves, no latency graph bends, and the only way to see them is a check you wrote before you needed it.

7. What this track does not cover

Eight subjects this track uses without teaching, where each gap will bite you, and what to read instead.

Being honest about the boundary is more useful than pretending there is not one. It is also the answer to the wrap-up question about what you are least sure of — an answer you can give in one sentence because you decided it in advance rather than on the spot.

Not coveredWhere the gap bitesWhere to go
Consensus internalsChapters 05, 06 and 20 use leader election and cluster membership as a black box; 29 prices a majority acknowledgement at 4.5 us without deriving the protocol that produces itThe Raft paper, described in Seven papers and the problem each one actually solved. Then implement leader election once; it is a weekend
Cross-shard serializable transactions23 and 28 both price two-phase commit and both choose a saga instead. Nothing here builds a system that actually offers the guaranteeSpanner and Percolator, both Google systems that do offer it — Spanner a globally distributed database, Percolator an incremental-processing layer built over BigTable. Spanner is also Seven papers and the problem each one actually solved’s honest counterweight: the guarantee is purchasable and the invoice is in latency
Stream joins, and the engine underneath22 derives windowing, watermarks, exactly-once processing and restatement, but never joins two streams together, and it names checkpoint-barrier alignment — the way a stream engine takes a consistent snapshot mid-flight — as a cost without deriving itThe Dataflow model paper — Google’s formalization of windowing and watermarks — for the semantics ch 22 does not reach; then the checkpointing design of Flink, the open-source stream engine that implements it
Query planning and storage enginesAssumed throughoutsql/03 covers B-trees, log-structured merge trees, query plans and multi-version concurrency control properly
Authorization models and key hierarchiesTenant isolation is covered — per-tenant limits and selective shedding in 21, isolation-by-partition in 24. What is missing is authorization modelling — deciding who may do what — plus key rotation and encryption key hierarchies; 15 and 24 price the side channel that convergent encryption opens and stop there — convergent meaning the encryption key is derived from the content itself, so identical files encrypt identically and can therefore be deduplicated, which is exactly what lets an attacker test whether a file is already storedAny serious treatment of capability-based authorization; your employer’s threat model
Tracing, and logs as a designed system21 covers metrics, service level objectives and alerting end to end. Distributed tracing — spans, context propagation, tail sampling — appears nowhere, and logs are only ever priced (01), never designedThe SRE workbook’s SLO chapters alongside ch 21; then instrument something and watch it lie to you
Cost as an org functionPriced per design — dollars per petabyte-month in 25, dollars per box-year in 21, dollars per day of miscounting in 22 — never as a budget owned by a teamThe GenAI and agents tracks price model inference explicitly
ML and generative systemsA different interview with a different scoring rubricThe other tracks in this repo

8. Seven papers, and the problem each one actually solved

Seven foundational systems papers, each summarized to the level you would need to discuss it in an interview: what problem it solved, and what that solution costs.

Read the originals for the problem statement, not the implementation. Every one of them is a case of “we could not buy this, so we had to invent it,” and knowing what could not be bought is what makes the design legible. Each entry below is written in the same three moves — the problem, the mechanism, the price — because that is the shape of the answer an interviewer wants when they ask what a paper is about.

Dynamo (Amazon, 2007)

The problem. A shopping cart must accept a write during a network partition. A rejected “add to cart” is lost revenue, and a rejected checkout is worse.

The mechanism. Everything follows from refusing to ever say no to a write. Consistent hashing places data without asking a coordinator. Version vectors exist because concurrent conflicting writes are now normal rather than exceptional. Sloppy quorums and hinted handoff — accepting a write on whatever replicas can be reached, and having them hand it to the rightful owner once the network heals — mean a partition does not stop writes. Merkle trees then find and repair the divergence afterwards.

The price, and the part worth internalizing: Dynamo pushes reconciliation to the application. That is why the cart resurrects deleted items. The merge rule for a cart is “union,” and union has no delete.

Chapters 05 and 06 are this paper with the arithmetic filled in.

BigTable (Google, 2006)

The problem. Petabytes of structured data whose schema varied per row, at a write rate that made B-trees untenable.

The mechanism. A sparse, sorted, distributed map keyed by (row, column, timestamp). It is stored as immutable files called SSTables, with an in-memory buffer called a memtable in front of them absorbing writes, and a background compaction process behind them merging the files back together.

That arrangement — buffer in memory, write out whole sorted files, merge later, never update in place — is the log-structured merge tree, or LSM. It is why sequential writes beat random ones by three orders of magnitude (sql/03), and that same gap is the whole of ch 20’s 320x.

The price, and the consequence that decides designs: the row key is the only index, so the schema is the access pattern. You cannot add a query later without rewriting the data. Everything modern that calls itself a wide-column store is a descendant.

GFS (Google, 2003), and Colossus after it

The problem. Storing files larger than any single disk, on hardware that fails constantly, for a workload that appends far more than it overwrites.

The mechanism, and the design decision worth stealing: one master holding all metadata in memory, and dumb chunkservers holding all the bytes. That is exactly the metadata-versus-blob division chapters 15, 24 and 25 keep returning to.

The single master looks like a scandal until you notice two things: metadata is about a thousandth of the data, and the client talks to the master once per file, not once per byte.

Colossus is the sequel. It removed the single master and moved from whole copies to Reed-Solomon erasure coding; ch 25 is that arithmetic derived, including the parts the marketing skips.

MapReduce (Google, 2004)

The problem, stated correctly. The commonly told story is that MapReduce made parallelism easy. It did not — parallelism was already easy. It made fault tolerance easy, and that is the actual contribution.

The mechanism. If every task is deterministic and free of side effects, a task on a dead machine can simply be re-run somewhere else. Nothing needs to be undone, and no other task needs to know. A 1,000-machine job stops being a coordination nightmare and becomes bookkeeping.

That is the same determinism ch 29 buys at the opposite end of the timescale, and the same reason ch 22 can treat replay as routine. Spark and Flink changed the execution model and kept the insight exactly.

Kafka (LinkedIn, 2011)

The problem. Many consumers reading the same event stream at different speeds. A traditional queue cannot do this, because the broker tracks per-message delivery state for every consumer.

The mechanism: make the log the primary object and push the offset — the read position — out to the consumer. The broker then does sequential disk writes and nothing else. Replaying old messages is free, because nothing on the server had to be undone.

That is the same structural idea as the per-user cursor in ch 15: the reader owns its position, so the server holds no per-reader state, and both resume and replay come for free.

Ch 20 is this paper with every constant priced.

Raft (Ongaro and Ousterhout, 2014)

What consensus is, first. Consensus is the problem of getting a group of machines to agree on a single ordered sequence of decisions even while some of them fail. It is what “elect a leader” and “replicate this log” actually rest on.

The problem Raft addressed was not correctness. Paxos, the earlier protocol, was already correct. The problem was that almost nobody could implement Paxos without getting it wrong.

The mechanism is decomposition: leader election, log replication, and safety presented as three separable mechanisms, plus a membership-change protocol that Paxos papers left as an exercise.

The price. Read this paper before you say “we use consensus” in an interview, because the follow-up is what happens during an election. The answer is that writes stop for an election timeout — typically 150-300 ms. That is a real number, and you should be prepared to defend it against your latency budget.

Spanner (Google, 2012)

The problem. External consistency across datacenters: if transaction B commits after transaction A finished, then every observer anywhere must see B ordered after A. Not eventually — immediately and globally.

The mechanism is TrueTime, which stops pretending a clock reading is a point and treats it as an interval. Bound the clock uncertainty using GPS receivers and atomic clocks, then have each commit wait out that interval before releasing its locks. Waiting guarantees that the next transaction’s timestamp really is later.

The price, and the honest lesson: every commit waits roughly the clock uncertainty. Global strong consistency costs milliseconds per write, permanently, by design.

That is the counterweight to the entire eventual-consistency argument in chapter 06, and to the gap What this track does not cover admits this track never fills. Strong consistency across regions is purchasable, and the invoice is denominated in latency.

9. The other tracks in this repo

Four different design rounds share a shape and are scored on completely different things, so it matters which one you are actually in — reading the wrong framework an hour before the interview is a recoverable mistake only if you notice. Five things are listed below and only four of them are rounds: the fifth, database internals, is the substrate all four stand on and nobody interviews you on it under that name.

The framework chapters are interchangeable in structure and not in content. Read the framework for the round you are actually in, an hour before you are in it.

10. How to practice, in the order that works

Five practice steps, arranged so that each depends on the one before it. Doing them out of order mostly wastes the later ones.

  1. Redo chapter 02’s six estimations on a timer, out loud, without notes, three minutes each. If the arithmetic is not automatic, nothing else in this track will surface under pressure, because every other skill here is downstream of a number you produced quickly.
  2. Take one chapter and rebuild it from the requirements, without reading it. Chapter 08 is the right one to start with because the whole design turns on two numbers; chapter 15 is the right one to finish Volume 1 with because it turns on six. From Volume 2, rebuild chapter 23 — it is the one where the arithmetic’s entire job is to buy you permission to spend forty minutes on a race condition, which is a different skill from sizing a fleet.
  3. Do a problem this track does not contain — a ticketing system, a ride-hailing dispatcher, a collaborative text editor — and use Which pattern does this smell like’s fork and its three gates to pick your two deep dives, exactly the way Worked the chart applied to a problem with no chapter does. Then check yourself against ch 03’s rubric. For each one, write down where the decisive constraint came from, and whether the chart got you there or the domain overrode a branch — that is the same move Worked the chart applied to a problem with no chapter makes at its last step.
  4. Practice the wrap. Five minutes of “here is what I would build first, here is what I would measure, here is what I am least sure about” is worth more than a fourth deep dive, and it is the part almost nobody rehearses (ch 03). The last of those three clauses is what The assumption ledger is for.
  5. Read one paper from Seven papers and the problem each one actually solved a week. Not to implement it, but to be able to say what problem it solved in two sentences.

11. The assumption ledger

Every design is a set of assumptions with a diagram attached, and the diagram is only correct relative to them. This chapter is no exception: its advice, its decision chart and its worked example all rest on things that could be otherwise. They are collected here, so that you can state the foundations in twenty seconds and say what replaces the advice when each one fails.

Sort each assumption into one of three bins:

The one-line test for which bin something goes in, from ch 03: move the assumption an order of magnitude in each direction and ask whether the set of boxes changes, or only the number of machines inside them.

The table below applies that test to the thirteen assumptions this chapter rests on; the last column — what you would build instead — is the one that turns an admission into an answer.

AssumptionBinWhat it holds upWhat replaces it if it is false
The mechanisms recombine — an unseen problem is a new arrangement of known partsLoad-bearingThe existence of this chapter. Both rule tables (Volume 1 as twenty one rules, 1b volume 2 as twenty five more), the claim in The twenty eight problems and what each one is actually for that chapters 09-14 introduce no new mechanism, and the whole of Worked the chart applied to a problem with no chapterIf each problem were genuinely novel, a rule table is a liability rather than an aid, and the right preparation is deriving from primitives every time instead of recognizing shapes
The round is roughly forty-five minutes of open conversation, scored on reasoning rather than on a correct answerLoad-bearingWhy The numbers you cannot recompute under pressure is a recall sheet instead of a derivation, why How to practice in the order that works rehearses the wrap, and why Which pattern does this smell like optimizes for speed of dispatchFor a multi-hour take-home or a written exercise, none of the compression helps — you would want the full derivations, and time pressure stops being the constraint the chapter is built around
Exactly one of the five opening questions dispatchesLoad-bearingThe shape of Which pattern does this smell like’s chart: one branch node and three flat gates, rather than a tree several levels deepIf two questions dispatched independently the correct picture is a grid rather than a tree, and the reader would need to evaluate combinations instead of walking one path
The three gates fire independently of which fork you tookLoad-bearingPresenting them as a checklist run every time, rather than as further levels of the chartIf a gate only applied inside certain leaves it belongs inside the tree, and the flat checklist would hide a dependency the reader has to know about
In Worked the chart applied to a problem with no chapter, demand exceeds supply by an order of magnitude — 500,000 buyers chasing 50,000 seatsLoad-bearingThe 90% failure rate, and therefore the entire reframing from throughput onto admission control and a virtual waiting roomIf supply met demand the failure path is a genuine edge case, the waiting room disappears, and the answer is an ordinary transactional booking system
In Worked the chart applied to a problem with no chapter, all buyers arrive inside 60 secondsLoad-bearingThe 8,333 purchase attempts a second, and therefore the 12:1 ratio that puts the problem in the middle band at allHolding the read rate fixed, spreading the same buyers over an hour gives 500,000 / 3,600 = 138.9 writes/s and 100,000 / 138.9 = 720 reads per write. That is past the 100:1 ceiling, so the problem leaves the middle band entirely and becomes an ordinary read-heavy caching design
The ~10:1 and ~100:1 fork thresholdsAsk itWhich of the three branches a borderline problem takes, including Worked the chart applied to a problem with no chapter’s at 12:1Moving a threshold reclassifies borderline problems, but the middle band’s instruction — build both paths and let the access distribution break the tie — is what a borderline problem gets under any threshold. The instruction is the durable part, not the boundary
The 5-second seat-map refresh in Worked the chart applied to a problem with no chapterAsk itThe 100,000 reads/s, and so the other half of the ratioIt is a client-side product decision, which makes it the cheapest thing in the whole design to change and therefore exactly what an interviewer should probe. Halving the refresh rate halves the read tier
A 128 GB commodity machine as the default in gate 1Ask itWhere the “does it fit in one machine” line sits, and therefore how often that gate declines to shardBigger machines exist and move the line up by roughly an order of magnitude. The gate’s finding — that it fires far more often than candidates believe — gets stronger, not weaker
The 50,000-seat venue in Worked the chart applied to a problem with no chapterState it — explicitly not load-bearing for the forkThe 450,000 failed attempts, the 90% failure rate, and gate 1’s verdict that the working set is trivially smallIt cannot change which branch you take. See the paragraph below
Which chapter derived a given ruleState it — explicitly not load-bearingOnly the second column of both rule tables, which is navigationA rule’s truth does not depend on where it was derived. If a mechanism had been introduced in a different problem, every one-line rule in Volume 1 as twenty one rules and 1b volume 2 as twenty five more reads identically
The 150 ms cross-continent round trip in gate 2State itThe verdict that a page needing two sequential round trips cannot meet a 200 ms budgetIt is close to a physical constant — the speed of light in fibre over intercontinental distance — so it does not move much. If it did, the gate would fire on a different set of designs and nothing about how you check it would change
The exact counts: 28 problems across 29 chapters, 46 rules, 7 failure shapes, 7 papersState itOnly the section headingsThese are inventory. A track with 35 chapters would produce a longer table and the same reading procedure

Why the venue size cannot move the answer

The 50,000-seat venue is the number to mark as explicitly unable to change the answer. It looks decisive: it appears in three of the six lines of Worked the chart applied to a problem with no chapter’s arithmetic, and it produces the memorable 90% failure rate.

It still cannot move the fork, and the reason is structural rather than numerical. The seat count appears in neither rate. Write the two rates out symbolically, with B for the buyer population:

reads/s         B / refresh interval        =  B / 5
writes/s        B / arrival window          =  B / 60
read : write    (B / 5) / (B / 60)          =  60 / 5     =  12

B cancels, and the seat count was never in the expression at all. The ratio is a function of the two time intervals and nothing else.

That is a stronger statement than it first looks. You can concede the venue size, and you can concede the crowd size too. The only two numbers that can move this problem out of the middle band are the refresh interval and the arrival window.

Test it: shrink the venue to 5,000 seats. The failure rate rises to 495,000 / 500,000 = 0.99, the read:write ratio stays at exactly 12:1, and every architectural conclusion holds.

What the seat count does decide is how loudly the error path dominates, and whether the inventory fits in memory. Fifty thousand rows clears the memory bar by a factor of thousands, and so would five thousand or five hundred thousand.

So concede the venue size instantly and spend the challenge on the arrival window, which is the one input that genuinely moves the design.

The sentence that makes this visible to an interviewer: “This whole approach rests on four things. One, that unfamiliar problems are recombinations of known mechanisms, which is what makes a rule table worth carrying. Two, that I have forty-five minutes and am being scored on reasoning, which is why I recall numbers instead of deriving them twice. Three, that the read:write ratio is the one question that dispatches, which is why my first move is always to compute it. Four, on this specific problem, that all the demand lands inside a minute — that is what makes it a write-path problem, and if it were spread over an hour I would be designing something else. The size of the venue is not one of them.”

Cheat sheet

This is the whole chapter compressed to twenty lines. If you read nothing else the morning of the interview, read this and Which pattern does this smell like.

The one-line thesisTwenty-eight problems, forty-six rules. The problems were the delivery vehicle
The two volumesVol 1 teaches the mechanism; Vol 2 teaches which constraint is binding and what the honest version costs
Before any designFive questions (ch 03): read:write · consistency per field · p99 and where the users are · retention · growth
The one forkUnder ~10:1 the write path is the system; over ~100:1 caching is the design; between them, build both and let the access distribution break the tie
If write-heavyNewer value: one slot, overwritten. New fact: a log, then windowed aggregation with absolute-value upserts
If read-heavyDB load goes as (1-h), each extra nine divides it by ten — then ask whether one key carries the reads
The three gatesDoes the working set fit in RAM · is the budget under one 150 ms RTT · can two writers touch one object
Before shardingAsk whether the working set fits in RAM. Every business on Earth is 60 GB; every road is 10.2 GB
When shardingHash ring, key = the one reads use, 1/(N+1) moves instead of 94%. And salt the provably hot key
When replicatingW + R > N, and say which side of CAP you took during a partition
When two writers collideOne owner: compare-and-swap. No owner: version vectors. Never last-write-wins
On any retry pathIdempotency key, exponential backoff, full jitter. Content addressing gives you the key free
Across a boundary you ownSaga with compensations, not 2PC. A dead coordinator holds locks nobody may release
Across a boundary you do notCommit the key before the call; on a timeout, ask — never re-send
On any moneyDouble-entry, integer minor units, and reconcile against an independent computation
On any storage billRF 3 vs RS(10,4) is 3x vs 1.4x, and coding is paid for in tail latency and small objects
On any rate you deriveSay whether it is offered load or service capacity, and never divide one by the other
The estimate’s real outputThe name of the binding constraint, not a number
The wrapWhat you would build first, what you would measure, what you are least sure about
What to read nextDynamo, then GFS, then Raft. In that order

Where to go from here: 03 — Interview Framework is how the forty-five minutes is spent, minute by minute; 02 — Back-Of-The-Envelope is the estimation drill you repeat until it is automatic; 17 — Proximity Service opens Volume 2 and is the next chapter in the study plan; and ML and GenAI are the same conversation scored against a different rubric.