๐Ÿ›๏ธ System Design

Notes from our discussions. One idea per card, shown by topic or by course.

๐Ÿงฒ Article extractor prompt (Claude in Chrome)

Open the lesson in Chrome โ†’ start Claude in Chrome โ†’ paste this โ†’ bring the output to the notes thread. It keeps callouts ๐Ÿ’กโš ๏ธ, do's/don'ts, images, code and every comment.

You are extracting a HelloInterview course lesson from the page open in this tab. The goal is a **faithful, complete copy** of the lesson that another assistant will turn into study notes. Do **not** summarize, shorten, reword, or add anything of your own.

## Before you extract
1. Scroll the whole page from top to bottom so everything loads.
2. Do NOT use plain page-text extraction โ€” it flattens tables, drops link URLs and loses callout types. Read the DOM / accessibility tree, and screenshot + zoom to read images.
3. Comments: click "Show All Comments", then click every "Show more" inside long comments so the full text is visible.
4. Skip: left course sidebar and progress UI, "Get the app" banner, Listen / Focus / Quick ref buttons, "On This Page" table of contents, rating stars, "Complete & next: โ€ฆ quiz" button, comment input box, footer.

## What to output
One Markdown document, in the **exact order the content appears on the page**:

1. **Header**
   - `# <Lesson title>`
   - `Course: <breadcrumb exactly as shown, e.g. "Course ยท 02 Foundations">`
   - `Subtitle: <description line under the title>`
   - `URL: <page URL>`

2. **Body, verbatim**
   - Keep every heading level (`##`, `###`), every paragraph, list, and numbered step, word for word.
   - Keep **bold**, *italic* and `inline code`. Keep links as `[text](url)` with the real URL.
   - Code blocks go in fenced blocks, exactly as shown. Add a language tag only if obvious (http, json, graphql, protobuf, sql); otherwise leave it blank.
   - Tables are NOT real <table> elements. Rebuild each one as a Markdown table with its header row, every row and every column, and keep the label above it (e.g. "Users table:").

3. **Callout boxes** are `div.callout.callout-tip`, `callout-warning` and `callout-info`. Use the class to pick the type and mark each one where it appears:
   > [CALLOUT: TIP ๐Ÿ’ก] <exact text>
   > [CALLOUT: WARNING โš ๏ธ] <exact text>
   > [CALLOUT: INFO โ„น๏ธ] <exact text>

4. **Do's and Don'ts / Good vs Bad / Pros and Cons** (only if present): keep them as two clearly labelled lists:
   [DO โœ…] โ€ฆ
   [DON'T โŒ] โ€ฆ

5. **Images and diagrams.** Images have no alt text; the caption is the short text line directly under the image (e.g. "Sharding", "Final Whiteboard"). Some diagrams are drawn as SVG text โ€” capture that text ONLY inside the [IMAGE] block, never as body paragraphs. Write a block at the exact spot where the image sits:
   [IMAGE <n>: <caption under the image, if any>]
   - Type: <diagram / screenshot / chart / sequence diagram / table image / photo>
   - All text in the image, exactly: <every label, box name, arrow label, number, step number>
   - Structure: <what connects to what, arrow directions, order of steps, groupings, solid vs dashed lines, meaningful colours>
   - What it shows: <one or two plain sentences, nothing beyond what's drawn>
   For a step-by-step diagram (e.g. a request flow), list every step in order with its label.

6. **Videos:** the lesson has a walkthrough video near the top. Write `[VIDEO: <title> ยท <length>]` where it appears. Don't transcribe it.

7. **Comments**: put them under `## Comments`, in "Popular" order. Take the top 20 comments plus all of their replies. Remove the single-letter avatar shown before names. For each one:
   ### <author> [ADMIN] [<badges e.g. Top 5%, Premium>] ยท <votes> votes ยท <time ago>
   <exact comment text, keep its lists and formatting>
     โ†ณ reply โ€” <author> [ADMIN] [<badges>] ยท <votes> votes ยท <time ago>
       <exact reply text>
   Mark course staff or admin authors with [ADMIN].

## Rules
- Verbatim. If something can't be read, write `[unreadable]` and don't guess.
- Don't merge or drop any section, even if it looks repetitive.
- If the output is too long for one reply, split it into `PART 1/N`, `PART 2/N`โ€ฆ at a heading boundary, and keep going until it's complete.
- At the very end, add:
  ## Extraction checklist
  - Headings: <count> ยท Callouts: <count> ยท Images: <count> ยท Code blocks: <count> ยท Tables: <count> ยท Comments: <count incl. replies>
  - Headings match the "On This Page" list? <yes / no โ€” list any missing>
  - Comments captured: <X> of <total shown in "Comments (N)">
  - Anything skipped or unreadable: <list, or "none">
๐Ÿ—‚๏ธ Index

๐Ÿงญ What a System Design Interview Tests

๐Ÿ’ก Break a vague, big problem into infra pieces. There's no single right answer. You're judged on 4 things, and Problem Navigation matters most.

  • ๐Ÿง  Vague problem โ†’ infra pieces: services, load balancers, databases.
  • ๐Ÿ› ๏ธ Practical, closer to real work than a LeetCode round.
  • ๐ŸŽฏ Many right answers. They judge how you navigate, weigh trade-offs, and communicate.
  • โš ๏ธ Going deeper than an interview needs can be a yellow flag.

๐Ÿ—บ๏ธ 6 interview types

e.g. "Design Uber" (product) ยท "Design a rate limiter" (infra). Dashed = other guides.

๐Ÿ“‹ Interviewer rubric

What they check ยท what an interviewer writes

๐Ÿงญ Problem Navigation
โญ Most important
Break it down, focus on what matters
They spent all their time on the User table, never touching the most important part!
๐Ÿงฉ Solution Design
Solve each piece, fit them together
The multi-layer cache was an elegant solution to the massive read volume
โš™๏ธ Technical Excellence
Know modern tech and patterns
They had strong command of Redis, Elasticsearch, and Inverted Indexes
๐Ÿ—ฃ๏ธ Communication
Explain clearly, take feedback well
They got quite defensive when I asked about alternative approaches
  • ๐ŸŽค #1 cause of failure = no structure โ†’ follow the Delivery Framework.
  • ๐Ÿค” They probe, doubt you, and ask "why not X?" to catch memorised answers โ†’ answer with trade-offs, don't defend.
  • ๐Ÿ‹๏ธ Practice beats just reading: people who only read stumble on the day.
๐Ÿ”ฌ Details
๐ŸŽ“ Course path
๐Ÿงญ Delivery Frameworkโ†’๐Ÿงฑ Core conceptsโ†’๐Ÿ—๏ธ Full problems
Early:๐ŸŽฅ video๐Ÿ“„ guideโ“ quiz
Later:๐Ÿงช try problemโ†’โœ… solutionโ†’๐Ÿงฉ pattern
โฑ๏ธ โ‰ˆ 28 h๐Ÿ“… 2โ€“4 months
๐Ÿ—บ๏ธ Not your interview type?
๐Ÿงฑ Low-level / OODโ†’LLD in a Hurry ๐Ÿค– ML modellingโ†’ML System Design in a Hurry ๐ŸŽจ Frontendโ†’GreatFrontend

๐Ÿ›ค๏ธ Delivery Framework

Most mid-level candidates don't fail for lack of knowledge. They fail because the clock runs out before they have a working system, and the feedback says "time management". The fix isn't going faster. It's a track to run on: 6 steps, in order. It's also your fallback when nerves hit.

โฑ๏ธ The track ยท tap a step

Steps 1โ€“5 ยท make it work (functional requirements)

1๐Ÿ“‹ Requirements~5 min

Everything after this is measured against your requirements, so this is where you start. Requirements come in two kinds, and you need both:

๐ŸŽฏ Functional: what the system must do
โš™๏ธ Non-functional: how well it must do it

๐ŸŽฏ A. Functional requirements: what it does

โœ๏ธ Write each one as "Users should be able toโ€ฆ". For an infra system with no end users (e.g. a rate limiter), the caller is a service: "Clients should be able toโ€ฆ".

๐Ÿ”Ž How to find them ๐Ÿ’ฌ: go through the actors and ask three things:

๐Ÿ‘ค Who sends it?โ†’๐Ÿ“ฆ What do they send?โ†’๐ŸŽฏ What outcome do they want?

๐Ÿ—ฃ๏ธ Then ask the interviewer like a PM: "does it need X?", "what if Y?".

โœ‚๏ธ Keep only the top 3. Twitter has hundreds of features. A long list hurts, and top FAANG companies grade you on choosing what matters.

๐Ÿฆ Users should be able to post tweetsโž• โ€ฆfollow users๐Ÿ“ฐ โ€ฆsee tweets of people they follow

Now the twist. Picture two Twitters with exactly those 3 features. One has 100 users: a single server and one database are enough. The other has 100M users who expect their feed in 200ms: now you need caches, sharding, many servers. Same features, completely different design. What made the difference is how well it must work, and that's the second kind of requirement.

โš™๏ธ B. Non-functional requirements: how well it does it

โœ๏ธ Write each one as "The system should beโ€ฆ". Pick the top 3โ€“5, put each in context and give it a number.

โŒ "low latency" (every system wants that)
โœ… "search < 500ms" (which part, and the target)
๐Ÿฆ availability > consistency100M+ DAUfeed < 200ms

๐Ÿ”Ž How to find them: walk this checklist, so you don't blank. Remember it as FCC + SLEDS ๐Ÿ’ฌ. For each letter, ask its question; keep the 3โ€“5 that really matter for this system.

F ๐Ÿ›ก๏ธ Fault toleranceA server or region dies: must it keep working?
C ๐Ÿ”€ CAPWhen the network splits, stay consistent or stay available? (Partition tolerance is a given.)
C ๐Ÿ“œ ComplianceAny legal or industry rules on the data? (e.g. payments, personal data)
S ๐Ÿ“ˆ ScalabilityHow many users and requests? Bursty (events, holidays)? Read-heavy or write-heavy?
L โšก LatencyWhich requests must be fast, and how fast? Focus on the heavy ones (e.g. Yelp search)
E ๐Ÿ“ฑ EnvironmentClient limits: battery, memory, bandwidth (video on 3G)
D ๐Ÿ’พ DurabilityCan we ever lose data? A social feed can lose some. A bank can't.
S ๐Ÿ” SecurityWho may see or change what? How is the data protected?

๐Ÿ’ฌ Tips from the comments:

  • ๐Ÿ—บ๏ธ "Highly available" alone isn't enough. Say where, why and how. ๐ŸŸข Availability = fail open (most systems; quantify the eventual consistency, e.g. "< 1 min"). ๐Ÿ”’ Consistency = fail closed (money, double booking, 1 ride โ†” 1 driver). Still say "CAP": interviewers expect the term.
  • โฑ๏ธ Guess latency targets from the client's point of view. For LLM chat, it's time-to-first-token.
  • โž• Two more checks: ๐Ÿ”” how real-time must updates be (ticket reserved, new bid)? โœจ What's unique here (LeetCode judge โ†’ isolate user code)?

Many guides tell you to do the math now. Don't, unless the answer changes a decision.

โŒ DAU, QPS, storage โ†’ "ok, it's a lot". It only shows you can do arithmetic.
โœ… TopK trending: number of topics โ†’ one min-heap or sharded?

๐ŸŽค Say: "I'll skip estimates and do the math when it changes the design."

2๐Ÿงฑ Core Entities~2 min

You know what to build. Now name the things it's built from. Core entities are the nouns of the system: what your API sends and your DB stores.

๐Ÿ”Ž How to find them: read your functional requirements and pick out the nouns.

Users should be able toโ€ฆ

๐Ÿฆ post tweetsโ†’๐Ÿ‘ค User ยท ๐Ÿฆ Tweet
โž• follow other usersโ†’โž• Follow
๐Ÿ“ฐ see tweets of people they followโ†’Tweet + Follow again, nothing new

๐Ÿ’ก A Follow is a link between two users. You have to store it, so it's an entity too.

๐Ÿ‘ค User๐Ÿฆ Tweetโž• Follow

โ“ Also ask: who are the actors? Each one is usually an entity too (๐Ÿ‘ค User here).

Why bother? Because the next step gets easy: each entity usually becomes an API resource, so you can map entities to endpoints almost one to one.

๐Ÿฆ Tweetโ†’POST /v1/tweets ยท GET /v1/tweets/{id} โž• Followโ†’POST /v1/follows ๐Ÿ“ฐ (no entity)โ†’GET /v1/feed: built from Tweet + Follow

โš ๏ธ Not always 1:1: the feed isn't stored as its own entity, it's computed from others. That's fine. Use entities as the starting point, not a rule.

Keep it rough, as a quick list said out loud as a "first draft". You don't know what you don't know yet. Fields get added later, once you see what each request changes.

๐Ÿท๏ธ Pick good names. Some interviewers check this ("one of the hardest problems in CS").

3๐Ÿ”Œ API / Interface~5 min

Entities are the nouns. The API is what users can do with them. It's the contract your design must satisfy, and it usually maps 1:1 to the functional requirements.

โญ RESTDefault. HTTP verbs on resources
GraphQLMany clients needing different data
RPC (gRPC)Internal service-to-service, when speed matters
WS / SSEReal-time, added after the core API

Don't overthink it: REST unless there's a reason not to.

POST /v1/tweets      {text}
GET  /v1/tweets/{id}  โ†’ Tweet
POST /v1/follows     {followee_id}
GET  /v1/feed        โ†’ Tweet[]

๐Ÿ“ฆ Resources are plural nouns: tweets, not tweet.

๐Ÿ” Notice: there's no userId anywhere. The current user comes from the auth token, never from the body or path. Interviewers flag this.

4๐ŸŒŠ Data Flow (optional)~5 min

Only for pipelines. If data goes through a long chain of steps (crawlers, data processing), write the steps as a list. If not, skip it.

๐Ÿ•ท๏ธ Web crawler:Fetch seed URLsโ†’Parse HTMLโ†’Extract URLsโ†’Store dataโ†’๐Ÿ” Repeat
5๐Ÿ—๏ธ High-level Design~10โ€“15 min

Now draw. The trick: don't design "Twitter". Satisfy one endpoint at a time, and the design builds itself ๐Ÿ‘‡

๐Ÿ“ฑ Clientโ†’๐Ÿšช API Gateway
โœ๏ธ Tweet CRUD Serviceโ†’๐Ÿ—„๏ธ Tweet DB (Postgres)id ยท authorId ยท text ยท media: s3Links[]
๐Ÿ‘ฅ Follower Serviceโ†’๐Ÿ—„๏ธ Following DB (Postgres)userId1 ยท userId2
๐Ÿ“ฐ Feed Serviceโ†’โ‘  getFollowers()
โ‘ก getTweets(followers)

The big trap is adding complexity too early and never finishing. Keep it simple. Spot a cache or a queue? Say it, write a note, move on. It'll get its turn.

๐Ÿ—ฃ๏ธ Talk while you draw: how data flows, and what state changes on each request.

๐Ÿ—„๏ธ Write the key fields next to the DB. Skip the obvious ones (name, email) and the types.

๐Ÿ–Š๏ธ Ask your recruiter which whiteboard tool you'll use (e.g. Excalidraw) and practice with it.

Step 6 ยท make it good (non-functional requirements)

6๐Ÿ”ฌ Deep Dives~10 min

Your design works, but the feed is slow: it fetches tweets from everyone you follow on every load. Good. That's exactly what deep dives are for. Go back to your non-functional list and harden.

โœ… meet the non-functional requirements๐Ÿงฉ edge cases๐Ÿšง bottlenecks๐ŸŽฏ interviewer probes
100M+ DAUโ†’ horizontal scaling ยท caches ยท DB sharding
Feed < 200msโ†’ fanout-on-read vs fanout-on-write + caches (the most interesting part of Twitter)

โš ๏ธ Don't talk over the interviewer. They're looking for specific signals, and if you never pause, you miss them and lose points on communication.

Real interviews rarely wait politely for step 6. Often the interviewer jumps into a deep dive while your design is still half drawn. That's normal: the 6 steps are your default track, not a script they follow. ๐Ÿ’ฌ

๐Ÿšจ When the interviewer jumps in early
1๏ธโƒฃ ๐Ÿ™‹ Go with them: it's where their signals areโ†’2๏ธโƒฃ ๐Ÿ“ Note what's unfinished, on the boardโ†’3๏ธโƒฃ ๐Ÿ”™ Come back and finish it if time allows

"Sure. I'll note that the follow flow isn't drawn yet and come back to it."

"Happy to go deeper, but I may not finish the full design. Pause here, or keep going?"

๐Ÿค” Many interruptions can mean they doubt a choice. Answer with the reason, then check: "I'm using X because Y. Did you have a different concern?"

โš–๏ธ The rule: they can pull you into a deep dive early. You shouldn't wander there on your own before the design works end to end. That's how candidates run out of time.

That's the loop: the first five steps get you a simple system that works. The last step makes it fast, scalable and reliable. Never the other way round, unless the interviewer pulls you there first.

๐Ÿ’ฌ What we learned from the comments

๐Ÿ”ข Math (from the course admin)
  • Only for a real decision: in-memory vs disk, 10 vs 10,000 machines. Time is zero-sum, so useless math costs you deep dives.
๐Ÿ” API (from the course admin)
  • The auth token is a JWT or session token in the header. A JWT is signed, so tampering gets rejected.
๐ŸŽค In the room
  • Name the real tech: "Kafka", not "a durable queue".
  • Interrupted a lot or pulled into a deep dive early? See ๐Ÿšจ When the interviewer jumps in early in step 6.

๐ŸŒ Layers and the Life of a Web Request

Every design you draw is boxes talking over a network. Networking is a huge field ("one of the heaviest textbooks in school, gross"), but interviews need only a few layers and one story: what happens when you load a page. Learn that once and every arrow between boxes makes sense.

๐Ÿ’ก Know 3 layers: IP (L3) routes, TCP / UDP (L4) deliver, HTTP and friends (L7) carry your app's data. One "request" is really many packets, and each one costs latency.

โ„น๏ธ Note Networking weighs most in infra and distributed-systems interviews. Full-stack and product roles need a surface understanding. But if your interviewer just got off an oncall rotation fighting load balancer or CDN problems, be ready for probes.

๐Ÿงฑ 7 layers, 3 that matter

Layers are abstractions. You don't need to know which voltage means 1 on the wire, only how to use the layer below. Like calling open instead of telling the disk how to read bytes.

๐Ÿง  The OSI model, top to bottom, 7 โ†’ 1.

OSI is the textbook's 7 layers. The real internet runs on TCP/IP, which squeezes them into 4. โž• not in the article

One analogy for the whole stack: sending a letter โœ‰๏ธ. Each layer does one job, top to bottom on the sender, bottom to top on the receiver. โž• Adi's notes, checked; not in the article

"The important ones": 3, 4, 7.

๐Ÿ“ฆ Inside a packet: MAC, IP, port

Each layer has one job, and it does it by writing a label on the data. On the way down, every layer wraps the data in its own envelope; the receiver opens them in reverse. โž• not in the article

๐Ÿ“ One carries about 1,500 bytes, and the TCP + IP labels take ~40 of them. A 1 MB image โ‰ˆ 700 packets, which is why TCP numbers them (seq #) to put them back in order.

Saysโœ‰๏ธ Like
๐Ÿท๏ธ MACwhich network card, on this network. Burned in at the factory.your name: the next hand to pass it to
๐Ÿ“ IPwhich machine, anywhere. Given by the network you join ().the postal address on the envelope
๐Ÿšช Portwhich app on that machine. 0โ€“65535; 443 = HTTPS, 53 = DNS.the flat number in the building
  • ๐Ÿ  A joins two networks, so it has two IPs: private inside (192.168.1.1) and public outside (from your ISP). It swaps your private IP for its public one on the way out: .
  • ๐Ÿ“ฃ To find the router's MAC, your phone shouts "who has 192.168.1.1?" and only the router answers: .

So the IP says who it's finally for, the MAC says who gets it next, the port says which app. Now watch those packets move.

๐ŸŽž๏ธ One web request, packet by packet

Now watch the three layers work together. DNS finds the server, TCP builds a connection over IP, HTTP asks for the page, and TCP tears it all down. Tap the diagram to step.

โ„น๏ธ Note "What happens when you type hellointerview.com into your browser and press enter?" used to be a popular interview question (less so in BigTech now). It's rarely part of system design, but it may save you headaches on the job.

๐Ÿ”ญ 3 things to take from it

What the animation just showed you:

1๏ธโƒฃ ๐Ÿง˜ You only work at the top

๐Ÿ‘€ The app only said "GET". โžก๏ธ DNS finds the IP, TCP delivers in order, IP (+ your ) routes. You never touch packets.

2๏ธโƒฃ โฑ๏ธ Every message costs time

๐Ÿ‘€ 1 request = 11 trips. โžก๏ธ โญ Higher layer = more work per message, so an L4 load balancer beats L7 on speed (๐Ÿ”— Load Balancing).

3๏ธโƒฃ ๐Ÿงท An open connection is memory on both sides

๐Ÿ‘€ Between ACK and FIN, both sides remember it. โžก๏ธ Reuse it (, ) to skip the handshake. Hold it for hours (WebSockets) = memory for hours (๐Ÿ”— Real-time).

๐Ÿ“ Layer 3: where IPs come from

IP routes to addresses. So who hands them out?

๐Ÿ–ฅ๏ธ node bootsโ†’a gives it an IP
  • ๐ŸŽฒ IPs are arbitrary. They only mean something because we tell people about them. On your own private network you can pick any.
  • ๐ŸŒ For internet traffic to find you, you need public IPs: routable, allocated by an . Internet routing is optimised to know where public IPs are.
  • ๐ŸŽ Any address starting with 17 (e.g. 17.0.0.0) is Apple's. The backbone knows to send those packets to Apple's routers.

That's the base of every arrow you'll draw: DNS to find, TCP to connect, HTTP to talk. Next up: TCP isn't the only way to deliver.

๐Ÿ’ฌ What we learned from the comments

๐Ÿ“ž When does TCP really close? (course admin)

Not after every request. Think of calling a shop with questions: โž• analogy not in the article

โ˜Ž๏ธ HTTP/1.0: ask one question, hang up, dial again. Every request pays the full handshake. "Super inefficient."
๐Ÿ“ž HTTP/1.1: stay on the line, ask the next one. Connection stays open by default (keep-alive).

๐Ÿ”š A 1.1 connection closes when:

  • ๐Ÿ‘‹ either side says bye: a Connection: close header (then both sides send a FIN),
  • โณ nobody talks for a while: the server's idle timeout hangs up (seconds to about a minute; โž• nginx default 75 s),
  • โŒ the tab closes or the network drops.

๐ŸŒ Why it matters: one page = HTML + CSS + JS + images, often 50+ requests to the same server. Keep-alive reuses a few open lines instead of 50 handshakes (โž• browsers keep up to ~6 per server).

๐Ÿ“ž Keep-alive: one question at a time per line. A slow answer holds up the rest.
๐ŸŽ™๏ธ HTTP/2: many questions at once on one line. Faster, but one lost TCP packet still stalls them all (HTTP/3 runs on QUIC over UDP to fix that).

๐ŸŽž๏ธ So why does the animation end with FIN? It shows one request on its own, start to finish. In a real browser, that FIN comes much later.

๐ŸŒ Public IPs
  • They go on whatever faces the internet: API gateways, load balancers.

๐Ÿšš TCP vs UDP

IP just throws packets at an address and hopes. Before an app can use them, someone has to decide: do we care if packets get lost or arrive out of order? That's the transport layer. In an interview it boils down to one choice: TCP or UDP.

๐Ÿ’ก Default to TCP: reliable and ordered, and interviewers assume it. Pick UDP only when speed beats reliability, and say what browsers get instead.

The transport layer gives us guarantees "instead of handing us a jumbled mess of packets". Three protocols live here: TCP, UDP, QUIC. โญ The real choice is TCP vs UDP. Treat QUIC as "a better TCP" that isn't widely adopted yet.

โœ… Remember Some performance-oriented interviewers are impressed by QUIC and HTTP/3. Most want you to spend your time elsewhere in the design.

๐Ÿ”ซ vs ๐Ÿด Machinegun vs workhorse

๐Ÿ”ซ UDP: fast, unreliable
"Spray and pray"
๐Ÿšซ Connectionless: no handshake
๐Ÿ“ญ No delivery guarantee: lost without notice
๐Ÿ”€ No ordering
โšก Lower latency: less overhead
You see where a datagram came from and where it's going (IP + port). The rest is a .
๐Ÿด TCP: reliable, overhead
"The workhorse of the internet"
๐Ÿค Connection-oriented: 3-way handshake first
โœ… Reliable: in order, no errors (ACK, else retransmit)
๐Ÿšฐ : don't overwhelm the receiver
๐Ÿšฆ : adapt so the network doesn't collapse
The connection is a stateful "stream": two messages sent in the same stream arrive in the same order.

๐ŸŽฏ Why would anyone want UDP?

No setup sounds great, but losing and reordering packets "kinda suck". So UDP wins only where speed matters more than reliability, and the client can cope with a missing packet.

๐Ÿ“บ live video๐ŸŽฎ online gaming๐Ÿ“ž VoIP๐Ÿ“– DNS lookups

๐Ÿ“ž VoIP drops the odd packet: a hiccup in the audio, but the call is still intelligible. That beats retransmitting and clogging the network with ACKs.

โš ๏ธ Watch out Browsers don't widely support UDP outside WebRTC. If your design uses UDP (e.g. the flood of hearts and reactions in Facebook Live Comments), plan for browser users.
๐Ÿ“ฑ App users: real-time UDP stream of reactions
๐ŸŒ Browser users: slower, batched HTTP stream, spread out over time in the UI

โš–๏ธ When to choose each

Interviewers expect TCP by default, often without you even saying it. That's also the course's advice. Extra points come from making a solid case for UDP "and not bungling the details".

๐Ÿ”ซ Choose UDP when:

โšก low latency is critical (real-time, gaming)๐ŸŽž๏ธ some loss is OK (media streaming)๐Ÿ“ˆ high-volume telemetry or logs๐ŸŒ no browsers (or another path for them)
โ„น๏ธ Note Apps often use both. A web video-conferencing app: TCP/HTTP for signaling and authentication, UDP/WebRTC for the audio and video streams.
๐Ÿ”ซ UDP๐Ÿด TCP
ConnectionConnectionlessConnection-oriented
ReliabilityBest-effortGuaranteed
OrderingNoneMaintains order
Flow controlNoYes
Congestion controlNoYes
Header8 bytes20โ€“60 bytes
SpeedFasterSlower (overhead)
Use casesStreaming, gaming, VoIPโญ Everything else

So: choose TCP and say nothing, or choose UDP and say why, plus what browsers get. Next: what we actually send over the connection.

๐Ÿ’ฌ What we learned from the comments

๐Ÿš€ QUIC, precisely
  • QUIC is built on UDP, and HTTP over QUIC is HTTP/3. "A better TCP" describes its role, not what it's built on (the admin said the wording was deliberate).
  • It adds reliability and encryption (TCP + TLS in one), faster setup (0-RTT), and separate streams, so one lost packet doesn't block the others the way it does in TCP.
๐Ÿ”ซ Why UDP at all? (course admin)
  • "Performance! Lower latency, higher throughput."
๐Ÿด TCP's controls, one level deeper
  • ๐Ÿšฆ Congestion control: a window of un-ACKed data starts small, doubles each round of ACKs, then grows by one. On a loss it halves and retransmits.
  • ๐Ÿšฐ Flow control uses a sliding window.
  • ๐Ÿ“ฆ A commenter asked where the IPs are in UDP's 8-byte header. It holds only ports, length and checksum; the IPs are in the IP header underneath. โž• not in the article

๐Ÿ“จ HTTP and API Styles: REST, GraphQL, gRPC

TCP gives us a reliable pipe. What goes through it? Almost always HTTP, with an API style on top. The interview question isn't "which is coolest?" but "what's the safe default, and when do I leave it?"

๐Ÿ’ก HTTP is stateless request โ†’ response. Default to REST (resources + verbs). GraphQL when the frontend needs flexibility. gRPC for fast internal calls. REST outside, gRPC inside.

โ„น๏ธ Note The application layer usually runs in user space: flexible and easy to change. The layers below run in the OS kernel: hard to change, but very efficient.

๐Ÿ“„ HTTP: the web's foundation

Clients send requests, servers send responses. HTTP is stateless: each request stands alone, and the server keeps nothing between them. โญ That's good. Keep the stateful part of your system as small as you can. Most simple HTTP servers are just a function of the request.

You can type this by hand: open a TCP connection with and send it.

Methods and status codes are standard, like enums. Know the common ones. Interviewers rarely dig in unless you're designing a RESTful API.

GETRequest data. โญ , no body
POSTSend data
PUTUpdate data
PATCHUpdate a resource partially
DELETEDelete data. โญ
โœ… 2xx200 OK ยท 201 Created (new resource)
โ†ช๏ธ 3xx302 Found (moved temporarily) ยท 301 Moved Permanently
๐Ÿ™‹ 4xx404 Not Found ยท 401 Unauthorized (needs authentication) ยท 403 Forbidden (understood, refuses to authorize) ยท 429 Too Many Requests
๐Ÿ”ฅ 5xx500 Server Error ยท 502 Bad Gateway (invalid response from )

Headers are the flexible part: free-form key/value pairs. That pragmatism is a lesson in itself.

๐Ÿท๏ธ Headers = an open slot for the future

โœ‰๏ธ Like sticky notes on the envelope: anyone can add a new one, and a post office that doesn't understand a note just ignores it. โžก๏ธ New feature = new header; old clients skip what they don't know, so nothing breaks. โž• analogy not in the article

โœ… Remember Headers show how to design an interface for unknown future uses. Content negotiation is the case study:
๐Ÿ’ป Accept-Encoding: gzip, brโ†’๐Ÿ–ฅ๏ธ Content-Encoding: br

The client says what it can handle. The server picks the most efficient one (). Old clients still work: backward compatible, degrades gracefully. ๐Ÿ”Ž The article writes "Accepts-Encoding"; the real header is Accept-Encoding.

๐Ÿ”’ HTTPS = HTTP + TLS/SSL encryption, against and attacks. A public website uses HTTPS, without exception.

โš ๏ธ Watch out Encrypted doesn't mean the request came from your client. Never trust the body without validating it.
โŒ { "userId": 42 } in the body โ†’ DB query. An attacker edits it and reads anyone's data. Ouch!
โœ… IDs in requests are fine if the server validates them. Never ask for anything you can't trust.

๐Ÿค” Why never trust the body? โž• not in the article

โœ‰๏ธ HTTPS is a sealed envelope: it proves nobody opened it on the way. It does not prove the letter inside is honest. The sender can be the attacker: they control their own browser, curl or Postman, and can type anything into the body, e.g. change 42 to 43.

๐Ÿชช So who is the user? Ask the token, not the body.

๐Ÿ”‘ log inโ†’๐Ÿ–ฅ๏ธ server issues a signed โ†’๐Ÿ“จ every request: Authorization: Bearer โ€ฆโ†’โœ… server verifies it โ†’ userId = 42

โœ‰๏ธ Like a staff badge the receptionist scans, vs someone just saying "I'm the manager". The body says what you want; the verified token says who you are.

๐Ÿท๏ธ Why a header? It rides on every request (even GET, which has no body), stays apart from the data, and one middleware checks it before any handler runs. A header can be faked too: what makes it safe is the server's signature check, not the header itself.

๐Ÿ” Then check permission: "does user 42 own order 99?" before returning it.

๐Ÿงฉ REST: simple and flexible

HTTP alone builds websites. Designs are about services talking through APIs, and there are three main paradigms: REST, GraphQL, gRPC. โญ REST is the most common.

๐Ÿ“ฆ Clients do simple operations on resources (think database tables, or files on a server). The challenge is modelling the resources. REST uses HTTP verbs plus path conventions, usually with JSON bodies (not required).

โœ… Remember Followed the Delivery Framework? Your Core Entities often map straight to your API's resources. Bonus!
GET  /users/{id}        โ†’ User
PUT  /users/{id}        โ†’ User  (update)
POST /users             โ†’ User  (no id:
                          server assigns)
GET  /users/{id}/posts  โ†’ [Post] (nested =
                          relationship)
โš ๏ธ Watch out updateUser and startGame are operations, not resources, so they're not RESTful.
โŒ updateUser ยท startGame
โœ… PUT /users/{id} ยท PATCH /games with { "status": "started" }

๐Ÿ“ Real example: Elasticsearch manages documents and indexes over REST. ๐Ÿข REST isn't the fastest for very high throughput, and JSON is inefficient to (de)serialize. But most apps aren't bottlenecked there.

โญ Like TCP, REST is your interview default. Reach for GraphQL, gRPC, SSE or WebSockets only for needs REST can't meet. ๐Ÿ”— API Design lesson.

๐Ÿ” GraphQL: ask for exactly what you need

REST's weak spot shows when a frontend team (say, a mobile app) builds a new page on top of a backend API. Facebook open-sourced GraphQL around 2015 to fix exactly this.

Three options, and "none of these are particularly good":

๐ŸŒ (a) Under-fetching: many calls, many round trips๐Ÿ“ฑ App Viewโ‡„/profile/{id}/status/{id}/group/{id1}/group/{id2}/group/{id3}โ€ฆโ‡„๐Ÿ–ฅ๏ธ Server
๐Ÿ˜ (b) Over-fetching: one huge aggregation API, hard to maintain, slow๐Ÿ“ฑ App Viewโ‡„ /everything-you-might-need (slow)๐Ÿ–ฅ๏ธ Server
๐Ÿ˜ฉ (c) A brand-new API for every page: "a nightmare"
โœ… GraphQL: one query, exactly the fields, in the shape the page needs๐Ÿ“ฑ App Viewโ‡„ one query๐Ÿ–ฅ๏ธ Server
query GetUsersWithProfilesAndGroups {
  users(limit: 10) {
    id username
    profile { fullName avatar }
    groups { name category { icon } }
    status { isActive lastActiveAt }
  }
  _metadata { totalCount hasNextPage }
}

Trimmed from the article's query: you just list the fields and nested objects you want.

โœ… Frontend iterates fast ยท less data (great for mobile) ยท sweet spot: complex clients, many teams querying overlapping data
๐Ÿ’ธ Running the queries adds backend latency and complexity, sometimes the same bespoke code we tried to avoid

๐ŸŽค In interviews its benefits are "murky": requirements are fixed, and the interviewer wants to see you optimise specific queries, where GraphQL "is frequently just in the way". โญ Bring it up when the problem is about flexibility (adapting apps fast to changing requirements) or the requirements are deliberately uncertain.

๐Ÿค” Why "murky" in an interview? โž• not in the article

GraphQL's superpower is coping with unknown future screens. An interview is the opposite: a fixed list of features, decided in the first 5 minutes. For a known screen you design the exact REST endpoint and tune its query, so GraphQL adds a layer and buys nothing. โœ‰๏ธ Like hiring a personal shopper when you already have the shopping list.

โžก๏ธ Mention it only when the prompt says many clients / many teams / screens that keep changing.

๐Ÿ“ฑ Why "great for mobile" and less for web? โž• not in the article

๐Ÿ“ถ Slow, flaky network: each round trip on 4G costs far more than on office Wi-Fi, and every extra call is one more chance to fail. One query instead of 5 calls โ†’ faster, and fewer half-loaded screens.

๐Ÿ“ฆ Data and battery: no over-fetching, so fewer bytes on a metered plan.

๐Ÿ—“๏ธ Old app versions live for months: a website updates on refresh, but users skip app updates. Each app version asks for just the fields it knows, so the backend can change without breaking old apps.

โžก๏ธ Web gets the same benefits, just smaller: fast network, always the latest code.

โšก gRPC: efficient service-to-service calls

REST and GraphQL ship JSON text. When your own services call each other constantly, text gets expensive. gRPC is Google's (the "g") RPC framework: HTTP/2 + Protocol Buffers.

๐Ÿงฌ Protocol Buffers are "JSON with a more rigid schema", which makes them smaller and faster to parse:

message User {
  string id = 1;
  string name = 2;
}

๐Ÿ“„ JSON { "id": "123", "name": "John Doe" }: 40 bytes, schema embedded

๐Ÿงฌ Protobuf: 15 bytes. Skinny tags, variable-length strings. "Less space and less CPU to parse!"

0A 03 31 32 33 12 08 6A 6F 68 6E 20 64 6F 65

๐Ÿ”Ž Nit: 6A is a lowercase "j", so these bytes spell "john doe", not "John Doe".

service UserService {
  rpc GetUser (GetUserRequest)
    returns (GetUserResponse);
}
  • ๐Ÿ› ๏ธ Definitions compile into client and server for many languages.
  • ๐Ÿงฐ Built for microservices at scale: streaming, deadlines, client-side load balancing.
  • โญ The key fact: it's binary, faster and more efficient than JSON over HTTP. Strong typing catches errors at compile time. Some benchmarks show 10x throughput.
  • ๐Ÿ”’ Use it for internal calls, when performance is critical or latency is dominated by the network, not the server's work.
  • ๐Ÿšซ Not for public APIs or clients you don't control: binary, and the tooling is less mature than JSON over HTTP.

โญ REST for public-facing APIs, gRPC for internal service-to-service, especially with binary data or when performance is critical. In many interviews, REST for both is fine. Build from there as the problem and the interviewer push.

โœ… Remember Interviewers want to see how you think and react to new constraints, not an optimal whiteboard drawing. Don't hyper-optimise your RPC protocol before handling the real bottlenecks. "Premature optimization is the root of all evil!"

So: HTTP carries it, REST shapes it, GraphQL and gRPC are for specific needs. All of them are the client asking. Next: when the server has to speak first.

๐Ÿ’ฌ What we learned from the comments

โœ๏ธ Methods, precisely
GETSafe + idempotent. No body, so parameters go in the URL: GET /config?config_id=123
POSTNot idempotent
PUTReplaces the whole resource.
PATCHPartial update. Not guaranteed idempotent
DELETE
  • So the article's "PUT to update a user" fits when you send the whole user. For a partial change, use PATCH.
  • URLs that name a command (updateUser) are RPC-style, not REST.
๐Ÿ”ฅ Whose fault?
  • 4xx: the client's request is the problem. 5xx: the server side, including a dependency behind it. A gateway that gets a bad upstream reply (502) is still a server-side failure.
  • 401 = "who are you?" (not authenticated). 403 = "I know you, but no." โž• not in the article
๐Ÿง˜ Stateless (course admin)
  • "Minimize the surface area that needs to be stateful" means: make the stateful part smaller, so more of it is stateless.
๐Ÿ” GraphQL's hidden cost
  • The N+1 problem: users { posts { comments } } for 20 users can become 1 + 20 + ~100 backend calls. You need batching, caching, custom resolvers and query limits. GraphQL moves backend work, it doesn't remove it.
โšก gRPC
  • RPC = calling a function on another server as if it were local: userService.getUser("123").
  • Write the schema once in a .proto file, then generate client and server code in many languages.
  • gRPC inside + REST outside means something has to translate between them.

๐Ÿ“ก Real-time: SSE, WebSockets, WebRTC

Everything so far is the client asking. But an auction, a chat or a video call needs the server, or another user, to speak first. gRPC can stream, but no browser supports it today. So the web has three tools, one for each shape of conversation.

๐Ÿ’ก Server โ†’ client only: SSE. Both ways, high-frequency: WebSockets (justify them!). Audio/video calls: WebRTC, peer-to-peer over UDP.

๐Ÿ“ฌ SSE: one response that never ends

Server-Sent Events is "a nice hack on top of HTTP": a spec that lets the server stream many messages, over time, in a single response.

โŒ Normal HTTP
{ "events": [
  { "id": 1, โ€ฆ },
  โ€ฆ
  { "id": 100, โ€ฆ } ] }
Wait for the whole blob, then process it.
โœ… SSE
data: {"id": 1, โ€ฆ}
data: {"id": 2, โ€ฆ}
โ€ฆ
data: {"id": 100, โ€ฆ}
Each line is its own message, handled on arrival.

โš ๏ธ "Tradeoffs!" Some nasty, misbehaving networks batch all the SSE chunks into one response, which brings back exactly what we were avoiding.

โœ… Remember Most interviewers don't know these limits and will gladly let you assume they don't exist. But anyone who has actually built SSE "has an enduring headache" from them, and may probe whether you've really used it.

๐ŸŽฏ Use it when clients should get notifications or events as soon as they happen, e.g. keeping auction bidders up to date on the current price. ๐Ÿ”— Realtime Updates covers the server side.

๐Ÿ”Œ WebSockets: both sides talk, any time

SSE pushes one way only. For real-time bidirectional traffic, WebSockets give a persistent, TCP-style connection with broad support, browsers included. The server pushes without a request, and so does the client.

โš ๏ธ Watch out A client being able to upgrade doesn't mean your infrastructure supports it. Every piece between client and server must support WebSocket connections. Anyone who's built them has fought firewalls, proxies and load balancers that don't.

๐ŸŽฏ Use them for high-frequency, persistent, bi-directional communication: real-time apps, games, anything that must send and receive the moment it happens. Just request/response, or SSE pushes are enough? Then WebSockets are overkill.

โš ๏ธ Watch out Launching into WebSockets without justifying them is "a great way to get a thumbs down". The infra is expensive, and stateful connections at scale need significant accommodations in your design. Hold off unless you really need them!

๐ŸŽฅ WebRTC: browser to browser, no server in between

The third shape: two users talking to each other, not to you. WebRTC connects browsers peer-to-peer. It's built for video and audio calls, and it's the only app protocol here that uses UDP.

๐Ÿšง Peer-to-peer is harder: most clients don't allow inbound connections, and most users sit behind a NAT (network address translation) device. Two standard workarounds:

๐Ÿชž STUN
Session Traversal Utilities for NAT
Gets each peer a publicly routable address + port, via tricks like . Hacky, but standard.
๐Ÿ” TURN
Traversal Using Relays around NAT
A relay: bounce traffic through a central server that routes it to the right peer.

๐ŸŽฏ โญ Use it for audio/video calling and conferencing. Collaborative editors? Occasionally, especially at scale. But most don't need thousands of clients and need a central server anyway, which is why the course's Google Docs design uses WebSockets. The alternative is WebRTC + , sending updates straight between clients.

โš ๏ธ Watch out WebRTC is "an absolute pain to get right". Even the best implementations lose connections, and it's a niche solution. More candidates go wildly off trail designing peer-to-peer systems than build them successfully. Most problems don't need peer-to-peer. Stick to calls and conferencing and you'll be in good shape.

So: SSE when only the server talks, WebSockets when both do, WebRTC when the users talk to each other. Each one holds connections open. Next: spreading all those connections across many servers.

๐Ÿ’ฌ What we learned from the comments

๐Ÿ“ฌ "SSE dies too soon"? (course admin)
  • A commenter: send a heartbeat (a :ping comment every 15โ€“20 s) and SSE stays open for hours behind ALB or nginx; reconnects are only for real drops (deploys, network changes).
  • Admin: "The problem is not the middle boxes you control, it's the ones you don't."
๐Ÿ”Œ Are WebSockets bad? (course admin)
  • No, they're stateful. โ‘  Each connection holds server memory for the whole session. โ‘ก Load balancers must support upgrades and sticky sessions. โ‘ข Many corporate firewalls and proxies mishandle upgrades. โ‘ฃ Disconnects and reconnects are your problem.
  • You can't "make them like SSE": SSE can't carry data from client to server.
๐ŸŽฅ STUN, TURN and ICE
  • ๐Ÿชž STUN is a "who am I?" mirror. Strict "symmetric NATs" (offices, schools) change the port for each destination and break it.
  • ๐Ÿ” TURN always works, since outbound connections are allowed. But every byte of video flows through your server: bandwidth cost and a bit more lag.
  • ๐Ÿค ICE picks the path: it gathers candidates (local IP, STUN address, TURN address) and tries direct first, TURN last.
  • Peers swap their public addresses from STUN, never their private ones.
  • โš–๏ธ Flagged: one commenter says peer-to-peer editing doesn't scale past a few users (each peer links to every other), which pulls against the article's "especially if they need to scale". The article's advice for interviews stands: WebRTC for calls.
๐Ÿ—‚๏ธ All the protocols on one card (from a commenter)
REST / HTTPRequest-response ยท client โ†’ server ยท stateless ยท web pages, APIs
GraphQLRequest-response ยท client โ†’ server ยท stateless ยท flexible queries
gRPCRPC + streaming ยท both ways ยท HTTP/2 ยท microservices
SSEServer push ยท server โ†’ client ยท persistent ยท live updates
WebSocketFull-duplex ยท both ways ยท persistent ยท chat, live data
WebRTCPeer-to-peer ยท direct ยท persistent ยท calls, file sharing

โš–๏ธ Load Balancing

We know how one client talks to one server. But one server won't hold, so we scale. The moment there are three servers, every client has the same question: which one do I talk to?

๐Ÿฝ๏ธ Think of a busy restaurant. One chef can't cook for the whole street, so you hire more chefs. Now every diner walking in asks: which chef cooks for me? This whole card is that question. โž• analogy not in the article

๐Ÿ’ก Horizontal scaling needs load balancing. Internal services: client-side (built into gRPC). Everything else: a dedicated LB. โญ L4 for WebSockets, L7 for HTTP.

๐Ÿ“ˆ Bigger servers or more servers

๐Ÿง‘โ€๐Ÿซ The author scales vertically wherever possible: modern hardware is incredibly powerful, and the days of thousands of tiny servers are over (๐Ÿ”— Numbers to Know). โญ But in interviews, horizontal scaling is the most common pattern.

๐Ÿฝ๏ธ Vertical = give your one chef a bigger stove. Horizontal = hire more chefs. A bigger stove has a ceiling, and if that chef gets sick, nobody eats. โž• analogy not in the article

Adding boxes to the whiteboard doesn't help if clients don't know which one to call.

๐Ÿ’ป Clientโ†’ โ“Server1Server2Server3

Spread the load by deciding which server handles each request. Two ways: decide on the client side, or on the server side with a dedicated load balancer.

๐Ÿงญ Client-side: the client picks

The client asks a service registry (directory) for the list of servers, then calls one directly. It polls, or gets pushed updates when servers are added or removed.

๐Ÿฝ๏ธ Diners look at a board of free chefs by the door (the registry) and walk straight to one. No one stands in the way, so it's fast. But if the board is old, a diner may walk to a chef who just went home. โž• analogy not in the article

โšก Very fast: no extra network hop on every request, just a periodic sync of the server list. Two examples:

๐Ÿ“– DNS is client-side load balancing too. Each lookup of example.com returns a rotated list of IPs (a different order, or even a different set), so different clients hit different servers.

๐Ÿ“– DNS is a phone book that lists the restaurant's numbers in a different order for each caller, so calls spread out. The catch: people keep the old page for a while (the TTL). โž• analogy not in the article

โ„น๏ธ Note DNS rotation is also how you avoid a single point of failure in the load balancer itself: run two LBs (in different data centers or regions, to be safe) and rotate between them in DNS. If one goes down, clients start trying the other.

So when does client-side work? It depends on how many clients must hear about changes, and how fast.

โณ Why "delays": update time grows with the number of clients to notify. DNS entries have a TTL (time to live), so far-flung DNS servers can cache them for their own clients, but your updates can never be faster than the TTL.

๐ŸŽค Great for internal microservices (built into gRPC). Interviewers rarely ask about the lines between your services, but if they do, mention client-side load balancing!

๐Ÿšฆ Dedicated load balancers

For everything else: clients you don't control, clients that must see changes quickly, or clients that shouldn't even know there are many servers. Put a server or hardware device in the middle.

๐Ÿฝ๏ธ A host at the door. Every diner stops there first (the extra hop), and the host seats them. Diners never see the kitchen, and the host knows right away when a chef leaves or joins. โž• analogy not in the article

๐Ÿ’ป Clientโ†’โš–๏ธ Load Balancerโ†’Server1Server2Server3 โœ“

"Load balancer decides which server to route to."

๐Ÿ’ธ One extra hop on every request
โœ… Very fast updates to the server list + fine-grained routing control

๐Ÿงฑ LBs work at different layers of the stack. Which one depends on what your app needs.

4๏ธโƒฃ Layer 4: forwards connections, never reads

  • ๐Ÿ”— Keeps persistent TCP connections between client and server.
  • โšก Fast and efficient: minimal packet inspection.
  • ๐Ÿ™ˆ Can't route on application data.
  • ๐ŸŽฏ Used when raw performance is the priority, and for WebSockets and anything that needs a persistent connection. "If you're using websockets in your interview, you probably want an L4 load balancer."

โ˜Ž๏ธ L4 is a phone switchboard: it connects your call to one line and steps away. It never listens to what you say, so it can't route on it, but it's fast. A WebSocket is a long phone call: connect once, then talk for hours. That's exactly what a switchboard is for. โž• analogy not in the article

7๏ธโƒฃ Layer 7: reads every request

  • โœ‚๏ธ Terminates incoming connections, creates new ones to the backends.
  • ๐Ÿ” Routes on request content: URL, headers, cookies.
  • ๐Ÿ”ฅ More CPU-intensive (it inspects packets).
  • ๐Ÿงฐ More flexibility and features. Best for HTTP traffic: every protocol here except WebSockets.
  • โš ๏ธ It hides TCP details, but for persistent connections to the same server you still can't ignore the connection.

๐Ÿ“จ L7 is a receptionist who opens every letter: "billing? โ†’ desk 3, support? โ†’ desk 5". Smart routing by what's inside, but reading costs time (CPU). For a long phone call there's nothing to read, so the receptionist just holds two lines open for hours. โž• analogy not in the article

4๏ธโƒฃ L47๏ธโƒฃ L7
Looks atIP + portURL, headers, cookies
ConnectionAs if client โ†” server directEnds at the LB, new one to server
CostFast, minimal inspectionMore CPU
Pick forโญ WebSockets, raw speedโญ HTTP, e.g. long polling
AWSNLBALB
โ„น๏ธ Note L4 vs L7 often comes up when discussing real-time features. Some L7 LBs explicitly support WebSockets, but generally L4 is better for WebSocket connections, while L7 offers more flexibility for HTTP-based solutions like long polling.

โ˜Ž๏ธ So: switchboard or receptionist? โž• not in the article

๐Ÿ‘€ Ask: does the LB need to read the request to decide? โžก๏ธ No (WebSockets, raw speed) โ†’ L4. Yes (route by path, header, cookie) โ†’ L7.

๐Ÿฉบ Health checks: route around failures

Balancing is half the job. The LB also watches its servers, and that automatic failover is what makes LBs essential for high availability, with no human needed.

โš–๏ธ LB checks each server on an intervalโ†’โœ… healthy: keep routing
๐Ÿ’ฅ lost power / crashedโ†’โŒ stop routing until it recovers
๐Ÿ”Œ TCP check: is it accepting new connections? Simple and efficient.
๐ŸŒ L7 check: HTTP request โ†’ 200 = healthy. 500 = internal failure, no response = crash.

๐Ÿฝ๏ธ The host peeks into each kitchen every few seconds. TCP check = "is the kitchen door open?" L7 check = "can you actually cook a dish?" Chef down โ†’ stop seating diners there until they're back. โž• analogy not in the article

๐ŸŽฒ Algorithms

A dedicated LB also lets you choose how traffic is spread.

๐Ÿ” Round RobinSequentially across servers. โญ Default
๐ŸŽฒ RandomRandomly across servers. โญ Default
๐Ÿ”— Least ConnectionsServer with the fewest active connections. โญ For SSE / WebSockets
โฑ๏ธ Least Response TimeServer with the fastest response time
#๏ธโƒฃ IP HashClient IP picks the server (session persistence)

๐Ÿƒ Round robin = dealing cards: one each, in turn. Least connections = joining the shortest checkout queue at the supermarket. IP hash = your regular waiter: same face every visit. โž• analogy not in the article

  • โญ Round robin or random suit stateless apps where no server is more popular. A new server starts getting traffic with no special config.
  • โญ Persistent connections (SSE, WebSockets) โ†’ Least Connections, so one server doesn't slowly collect all the active connections.

๐Ÿญ In the real world

๐Ÿ”ฉ Hardwareโ†’F5 Networks BIG-IP ๐Ÿ’พ Softwareโ†’HAProxy ยท NGINX ยท Envoy โ˜๏ธ Cloudโ†’AWS ELB/ALB/NLB ยท Google Cloud LB ยท Azure LB

๐Ÿš€ Enterprise hardware LBs handle 100s of millions of requests per second; software ones less. Scaling the LB itself is almost never asked in SWE interviews (except networking specialisations). If your LB throughput looks huge, mentioning hardware LBs "is a good way out".

So: client-side for services you control, a dedicated LB for everyone else; L4 to keep connections, L7 to read requests. With servers spread out, the next problems come from geography and failure.

๐Ÿ’ฌ What we learned from the comments

๐Ÿ”Œ Why L4 for WebSockets? The big thread (course admin)

โ˜Ž๏ธ Not "because it's TCP": HTTP runs on TCP too, and HTTP goes to L7. The reason: a WebSocket is one long phone call, not many letters. The switchboard (L4) connects it once and steps away. A receptionist (L7) would have nothing to read, yet hold two lines open for hours. โž• analogy not in the article

  • "Think about load balancers from a hardware perspective." L4 reads fixed offsets in a packet โ†’ higher throughput, and it keeps 1:1 client โ†” server connections.
  • A WebSocket is a thin layer over TCP. You only need the connections balanced, so there's no reason to touch the app layer and pay for it.
  • L7 terminates the connection (often doing HTTPS termination too) and opens a new one. That's how ALB can route by path.
  • A WebSocket is balanced once, at the HTTP upgrade. After that it's just a persistent connection. To rebalance, close it and let the client reconnect.
  • Many L7 LBs (Envoy, AWS ALB) do support WebSockets, but must be configured to keep them sticky. An engineer from Azure Application Gateway: long-lived connections build up memory on L7, but it's worth it if you need L7 features.
  • โžก๏ธ Takeaway: L4 by default for WebSockets; L7 when you need routing by path, host or cookie.
  • With L4 the LB only passes bytes, so TLS and auth happen in your app (or a sidecar proxy).
  • How L4 keeps a session on one server: it maps each connection's to one backend.
๐Ÿงช Quiz errata
  • L7 LBs also keep persistent connections, on both sides (pooled to the backends), and pick a backend per request. "L7 makes a new connection for each request" isn't generally true.
๐Ÿฉบ Health checks and deploys
  • AWS NLB (L4) also supports HTTP health checks. Deeper checks give a truer picture of a host.
  • An L7 LB can also monitor HTTP status codes. That's hard at L4.
  • Dedicated LBs make blue/green deploys easy: take a server out, deploy, add it back once health checks pass.
๐Ÿงญ Client-side, precisely
  • "Few clients" really means few clients you control. Pushback: gRPC client-side LB and Envoy sidecars run with huge client counts, so control matters more than count.
  • DNS TTL = the maximum staleness you accept.

๐ŸŒ Latency and Failures: Distance, Retries, Circuit Breakers

Protocols โœ“, load balancing โœ“, persistent connections โœ“, high availability โœ“. Two deep-dive favourites are left, and both come from the real world: physics makes distance slow, and networks break.

๐Ÿ’ก Two real-world problems, and the tools for each. Every tool is explained further down ๐Ÿ‘‡

๐ŸŒ 1. Distance is slow โž• plain words + analogies, not in the article

Data needs time to travel. Fix: keep it near the user (that's data locality).

๐Ÿ“ฆ CDN: a corner shop with copies of popular items, so you don't drive to the far warehouse.

๐Ÿ—บ๏ธ Regional partitioning: each region gets its own branch with its own records.

๐Ÿ’ฅ 2. Networks fail

โฑ๏ธ Timeout + retry with backoff: no answer? Call back later, waiting longer each time. Jitter: not everyone calls back on the same second.

๐Ÿ”‘ Idempotency key: an order number, so a repeated order isn't made twice.

๐Ÿ”Œ Circuit breaker: the fuse in your house. It trips so one fault doesn't spread, then tests again later.

๐ŸŒ Regionalization: physics wins

Global services put servers around the world: several data centers in one region (Amazon's "availability zones", so a broken pipe in one building doesn't take you down), repeated in cities across the globe. "A great victory for humanity", but now distance costs time.

โ„น๏ธ Note Light in fiber moves at about 2/3 of its speed in a vacuum: โ‰ˆ 200,000 km/s. New York โ†” London is about 5,600 km:
2 ร— 5,600 kmรท200,000 km/s=โญ โ‰ˆ 56 ms round trip

That's the theoretical minimum, before any processing. This is why geographic distribution is essential for low latency.

The fix, everywhere in computing: data locality. Performance is best when the data sits as close as possible to the computation.

๐Ÿ“š Data locality = keep the books you need on your desk, not in a library across town. Every trip to the library costs time, however fast you read. โž• analogy not in the article

  • ๐Ÿ“ Keep the data a query needs (a) close together and (b) close to the user.
  • ๐Ÿข User data in Los Angeles, web servers in New York โ†’ every DB query pays tens of ms, before processing.
  • ๐Ÿคท Some latency is unavoidable: if users are far apart, they're far apart. Two strategies optimise within physics ๐Ÿ‘‡

๐Ÿ“ฆ CDNs: the answer is up the road

๐Ÿ‘ค Userโ†’ โšก just up the road๐Ÿ“ Edge server
cached copy
โ€ฆ๐Ÿข Your servers
far away
  • โญ The most common way to cut latency. Content Delivery Networks have servers in hundreds or thousands of cities: edge locations.
  • ๐ŸงŠ It only works because of caching: data that doesn't change much or often. Best for static content: images, videos, assets.
  • ๐ŸŽค Use one when data is very cacheable and queried from across the globe. e.g. caching Facebook search results โ†’ lower latency and less load on the backend.

๐Ÿช A corner shop stocks copies of the popular items from the big warehouse. Milk and bread: grab it up the road. Something rare or fresh off the line: still the long drive. โž• analogy not in the article

๐Ÿ—บ๏ธ Regional partitioning: mirror the geography

Uber's key insight: a rider in Miami never wants a driver who's in New York. Millions of riders and drivers a day, but only a few thousand in any one city. So the architecture can mirror that.

๐Ÿ—ฝ "Northeast US"
nearby cities bundled
๐Ÿงฉ services โ†’ fast
๐Ÿ—„๏ธ local DB (e.g. New York) โ†’ very fast
๐ŸŒต "Southwest US"
nearby cities bundled
๐Ÿงฉ services โ†’ fast
๐Ÿ—„๏ธ local DB (e.g. Los Angeles) โ†’ very fast

Each region has its own database in that geography, with request servers co-located next to it. Booking a ride or checking status stays inside the region. "Nice and optimal!"

๐Ÿฆ Like a bank with city branches: your account lives at your branch, so everyday visits never call head office in another country. โž• analogy not in the article

๐Ÿ’ฅ Failures: plan for them

The other frequent deep dive. Servers crash, solar flares flip bits, power gets cut. The network fails too: cables get cut, routers fail, packets get dropped.

โœ… Remember "The network is reliable" is one of the most dangerous assumptions in distributed systems. Always expect network calls to fail, be delayed, or return unexpected results.

๐Ÿ” Timeouts and retries with backoff

The most elementary hygiene: expect a call to take X, set a timeout, give up and try again. A temporarily slow server will likely answer the retry. But retries are double-edged: retrying requests that keep failing makes things worse.

โณ Backoff: don't retry immediately. Wait a little, and longer after each failure, so the system can recover. ๐ŸŽฒ Jitter: add randomness, so clients don't all retry at the same moment "like a jackhammer".

๐Ÿ“ž Calling a busy friend: no answer โ†’ wait 1 min, then 2, then 4 (backoff). If 1,000 people all redial on the exact same second, the line jams again; each waiting a slightly random time (jitter) spreads the calls out. โž• analogy not in the article

๐ŸŽค โญ Interviewers often listen for the magic phrase "retry with exponential backoff". In more senior interviews, be ready to explain jitter. ๐Ÿ“– AWS: timeouts, retries and backoff with jitter.

๐Ÿ”‘ Idempotency: retry without double-charging

Retries are cool, except when they have side effects. โญ This is why idempotent APIs are the key to safe retries: calling them many times gives the same result. GET is the classic one: the content may change, but fetching it doesn't change the system. For writes, add a key ๐Ÿ‘‡

๐Ÿ”Œ Circuit breakers: stop the cascade

Senior candidates often get "what happens when this service goes down?" Sometimes "fail and retry until it's back" is fine. But picture a database that went down cold and has to boot one instance at a time. A firehose of retries and angry users can pin each instance before it starts: a thundering herd. You can't get the first one up, so the whole DB never comes back. Stuck!

๐Ÿ›๏ธ Thundering herd = a Black Friday crowd at the doors: open one door and the crush knocks the first clerk over, so the shop never manages to open. โž• analogy not in the article

โœ… Remember Anyone who's done oncall has war stories about cascading failures: one failure creating new ones (it travels from a service to its callers). It usually goes unnoticed "until it bites you at 3am", which makes it a great interview question and a screen for experience. Prepare by learning to spot these cascades and how to stop them.

What does a cascade look like in real life? Usually it starts with something slow, not something dead. ๐Ÿ‘‡ โž• example not in the article

๐Ÿš— A traffic jam: one lane is blocked, cars back up into the junction, and soon streets that never used that lane are stuck too. โž• analogy not in the article

The first tool that stops it is the circuit breaker:

Inspired by electrical circuit breakers: it stops cascading failures and gives failing services time to recover.

๐Ÿ”Œ The fuse in your house: a fault trips it, and power to that circuit stops at once (fail fast) instead of burning the wiring. After a while you try flipping it back (a few test requests); if it holds, power is back. โž• analogy not in the article

โšก Fail fast, no waiting for timeouts๐Ÿชถ Less load on a struggling service๐Ÿฉน Self-healing: tests recovery without full traffic๐Ÿ˜Š Fast fallbacks, no hanging UI๐Ÿงฑ One failure doesn't take down the system

๐ŸŽค Bring them up when the interviewer digs into reliability, failure modes or disaster recovery. That knowledge is usually "won at 3:00am battling a hardware failure when the system Just. Won't. Come. Back. Up." Put them on:

๐ŸŒ third-party API calls๐Ÿ—„๏ธ DB connections and queries๐Ÿงฉ service-to-service calls๐Ÿ‹๏ธ heavy operations that may time out๐Ÿ“ก any network call that could fail or slow down

๐Ÿ›ก๏ธ The cascade toolkit

A breaker alone isn't the whole answer. Each tool fixes one step of the cascade above. โž• bulkhead, shedding, queue: not in the article

  • โฑ๏ธ Timeout ยท fixes โ‘  Threads wait forever
    Give up after ~2 s, not 30. Hang up instead of holding the phone all day.
  • ๐Ÿ” Backoff + jitter, retry limit ยท fixes โ‘ฃ Retries pile on
    Retry a few times, waiting longer and a little randomly. Never retry forever.
  • ๐Ÿ”‘ Idempotency key ยท fixes โ‘ฃ Retry charges twice
    Same order number โ†’ the bank charges once.
  • ๐Ÿ”Œ Circuit breaker ยท fixes โ‘ก Still calling a broken service
    Stop calling after N failures, test again later. The house fuse.
  • ๐Ÿšข Bulkhead ยท fixes โ‘ค One dependency eats every thread
    A separate, capped pool per dependency. A ship's watertight rooms: one floods, the ship floats.
  • ๐Ÿšฆ Load shedding / rate limit ยท fixes Too much traffic arriving
    Turn away extra requests early (fast 503) so the ones inside finish. A bouncer at a full club.
  • ๐Ÿช‚ Fallback ยท fixes User gets nothing
    Give a lesser answer: "Order placed, payment confirming", cached results, a default list.
  • ๐Ÿ“ฌ Queue it ยท fixes Slow work blocks the user
    Accept the order now, charge from a queue. The bank's slowness no longer holds a user thread.

๐ŸŽค When they ask "what if Payment goes down?" โž• not in the article

1๏ธโƒฃ Blast radius: "Who calls Payment? Only checkout should break, not browse or login."

2๏ธโƒฃ Don't wait: "Timeouts on every call, retries with exponential backoff and jitter, and an idempotency key so a retry can't double-charge."

3๏ธโƒฃ Don't hammer: "A circuit breaker on the Payment call, with a fallback: accept the order and confirm payment later."

4๏ธโƒฃ Contain it: "A bulkhead (separate pool) for Payment calls, so the rest of the site keeps its threads."

5๏ธโƒฃ Decouple: "If payment can be async, put it on a queue and charge when the bank recovers."

๐Ÿ‘€ Saying them in the order the cascade happens shows you've seen one, which is exactly what this question is screening for.

๐Ÿ The whole lesson in four steps

1๏ธโƒฃ Basics: IP, DNS, TCP/IPโ†’2๏ธโƒฃ Protocols: TCP vs UDP, HTTP/S, WebSockets, gRPCโ†’3๏ธโƒฃ Load balancing: client-side + dedicatedโ†’4๏ธโƒฃ Reality: regions + failures

Networking choices touch latency, throughput, reliability and security. The course gives sensible defaults, but most problems have no single right answer: justify each choice from the requirements, and show the interviewer how you weigh the trade-offs.

๐Ÿงช Try it yourself: capture your own traffic in Wireshark to see the whole stack in action. Then fake a nasty cell connection (latency, packet loss) with Mac's Network Link Conditioner (via Xcode) and watch apps break.

๐Ÿ’ฌ What we learned from the comments

๐Ÿ” Backoff in numbers
  • Exponential = doubling: wait 1, 2, 4, 8 s. With jitter, one client retries after 1.7 s and another after 3.1 s, so 1,000 clients don't hit at once.
  • ๐Ÿงฎ Retry storm: if each of 5 layers makes 3 attempts, one user call becomes 3โต = 243 attempts at the bottom.
๐Ÿƒ Thundering herd
  • DB restarts โ†’ 1,000 users retry at once โ†’ it crashes again โ†’ it never recovers. The same rush happens when a cache entry expires or a lock frees up.
๐Ÿ”‘ Idempotency keys in practice
  • Store key โ†’ result (Redis or a DB table), atomically with the work. A retry with the same key returns the stored result without re-running anything.
  • Natural keys: user + order id for a payment; the unique email for sign-up (handle the unique-constraint error by returning the existing user).
  • โ“ Left open: who generates the keys, and how to stop collisions or forged keys. The article's "user + date" example is deliberately simple.
โš–๏ธ Flagged opinion
  • One engineer says circuit breakers are talked about more than used between microservices. It's an opinion, and the article's interview advice stands.