PPrepLearn
Progress · 0/5 phases

📐 Phase 1 — Foundations of System Design (Days 1–15)

8 min read · Days 1–15 · Notion

Core insight: Before you draw a single box, write down the requirements and estimate the numbers. This is the skill that separates a junior who draws boxes from a senior who designs systems.


🧠 Why this phase exists

Most engineers who struggle with HLD interviews don't lack knowledge of systems — they lack a structured thinking process. They jump to solutions, skip estimation, and design for imaginary constraints. This phase gives you the mental operating system that every subsequent phase runs on.


📚 Topics in order

Day 1–2 — What is HLD vs LLD

  • HLD (High-Level Design): component responsibilities, data flow between services, technology choices, tradeoffs. No code.
  • LLD (Low-Level Design): class design, data structures, algorithms, API method signatures. Code-adjacent.
  • When to switch levels: start HLD, zoom into LLD on the 2–3 most critical components only
  • The five outputs of a good HLD: component diagram, API contracts, database schema choice, data flow description, failure scenarios

Day 3–4 — Requirements engineering

  • Functional requirements: what the system does. Core features only — not nice-to-haves.
  • Non-functional requirements (NFRs): availability target (99.9% vs 99.99%), latency SLO (p99 < 200ms), consistency model (strong vs eventual), durability guarantees
  • Scope constraints: what’s explicitly out of scope (saves time in interviews, prevents scope creep in production)
  • Template: “The system must [action] for [user] within [constraint] with [quality attribute]”

Day 5–6 — Back-of-envelope estimation

  • QPS calculation: DAU × requests/user/day ÷ 86,400 seconds = avg QPS. Peak = avg × 3
  • Storage sizing: writes/day × bytes/write × days retention
  • Bandwidth: QPS × payload size per request
  • Memory (cache): hot data = 20% of daily active data (80/20 rule)
  • Powers of 2 table: 10 = 1K, 20 = 1M, 30 = 1B, 40 = 1T
  • Byte sizes: char = 1B, UUID = 16B, long = 8B, timestamp = 4B

Day 7–8 — CAP theorem for designers

  • CAP: Consistency, Availability, Partition Tolerance. Partition tolerance is not optional in any distributed system.
  • CP systems: return an error when partitioned rather than serve stale data. Examples: ZooKeeper, etcd, HBase.
  • AP systems: return potentially stale data when partitioned rather than an error. Examples: Cassandra, DynamoDB (default), CouchDB.
  • PACELC extension: even without a partition, there is a latency-consistency tradeoff (L vs C)
  • Decision framework: “If this service is partitioned, is it better to show stale data or show an error?” — that’s a product decision.

Day 9–10 — Core building blocks

  • Load balancer: distributes traffic across server instances. L4 (TCP) vs L7 (HTTP). When to use each.
  • Cache: reduces latency and DB load. Redis, Memcached. When to cache, when not to.
  • Database: relational (ACID, SQL) vs NoSQL (various consistency, various models). Choose by access pattern.
  • Message queue: decouples services, enables async processing. RabbitMQ, Kafka, SQS.
  • CDN: serves static and cacheable content from the edge. Biggest ROI scaling win.
  • Object storage: S3-like. For blobs > 1MB. Never store in SQL.
  • Rule: reach for each building block only when you have a specific problem it solves.

Day 11–12 — Scalability fundamentals

  • Vertical scaling (scale-up): bigger machine. Simple. Has a ceiling. Single point of failure.
  • Horizontal scaling (scale-out): more machines. Complex. Requires stateless services.
  • Stateless vs stateful: stateless services can be horizontally scaled trivially. State must live in a shared store.
  • Shared-nothing architecture: no instance shares in-memory state with another. Scale to any number of nodes.
  • Read scaling: add read replicas. Write scaling: requires sharding or a different architecture.

Day 13 — Latency numbers every designer must know

  • L1 cache: ~1ns · L2 cache: ~4ns · RAM: ~100ns
  • SSD read 4KB: ~100µs · Read 1MB from SSD: ~1ms
  • Same datacenter network: ~0.5ms · Cross-region network: ~100ms
  • HDD seek: ~10ms · Read 1MB from network: ~10ms
  • How to use these: a design that makes 10 cross-region calls per request has 1 second of unavoidable latency.

Day 14–15 — The HLD interview framework: RESHADED

  • R — Requirements: clarify functional + non-functional. Never skip.
  • E — Estimation: QPS, storage, bandwidth. Takes 3 minutes. Constrains every decision.
  • S — Storage: which database(s), why, what schema shape
  • H — High-level design: boxes and arrows at component level
  • A — APIs: REST/gRPC endpoints, request/response shape
  • D — Detailed design: deep dive on 2–3 critical components
  • E — Evaluate: failure scenarios, bottlenecks, SPOFs
  • D — Distinguish: what makes your design better than the obvious approach

🔨 Projects

Project 1 — URL Shortener requirements doc (constraints only)

Deliverable: A written constraints document — no architecture yet.

Answer in writing before designing anything:

  • Who are the users? Read-heavy or write-heavy? What ratio?
  • What’s the peak QPS for reads? For writes?
  • How long do links live? What’s the storage requirement over 5 years?
  • What’s the latency SLO for redirects? (Hint: should be < 10ms)
  • Consistency requirement: is it OK to redirect to an old URL for 1 second after update?
  • What’s explicitly out of scope for v1?

Why: Every system design mistake traces back to a missing or wrong requirement. Building this muscle now prevents 80% of bad designs later.

Project 2 — Estimation calculator

Stack: Any spreadsheet or simple CLI tool

Build a reusable estimation template. Inputs: DAU, requests per user per day, data size per request, read:write ratio, retention days. Outputs: average QPS, peak QPS, storage per year, daily bandwidth, cache memory needed (20% of hot data).

Run it for: Twitter (500M DAU), WhatsApp (2B DAU), a startup (100K DAU). See how the architecture must change at each scale.

Project 3 — Three architecture case studies

Deliverable: One A4 page per system

Read the following engineering blog posts and write a 1-page summary for each: (1) Uber’s architecture evolution, (2) Discord’s message storage migration from MongoDB to Cassandra to ScyllaDB, (3) Slack’s job queue system.

For each, answer: What was the original design? What broke at scale? What did they change? What was the core tradeoff they made?


⚠️ Common mistakes

Mistake 1

❌ Jumping to architecture before writing requirements.

You design a complex distributed system, then the interviewer says “oh, this only needs to handle 1K users.” 20 minutes wasted.

✅ Correct approach: Spend the first 5 minutes only on requirements and estimation. Ask: “Before I start designing, let me confirm the scale and core constraints.” This also signals seniority.

Mistake 2

❌ Treating NFRs as vague aspirations (‘fast and reliable’).

‘Fast’ could mean 1ms or 1 second depending on the system. ‘Reliable’ could mean 99% or 99.999% uptime.

✅ Correct approach: Every NFR must be a number: “99.9% availability (43 min downtime/month), p99 latency < 200ms, RPO < 1 hour, RTO < 10 minutes.” Numbers drive architecture. Adjectives don’t.

Mistake 3

❌ Memorising specific system designs to regurgitate.

Interviewers change one requirement and the memorised design collapses completely.

✅ Correct approach: Learn WHY Twitter chose fan-out-on-write, not just THAT they did. The why (write-heavy tradeoff for read-heavy users) generalises to every feed system. Principles transfer; facts don’t.

Mistake 4

❌ Treating CAP theorem as a theoretical checkbox.

Everyone mentions CAP, almost nobody uses it to actually make a design decision.

✅ Correct approach: When choosing a database, explicitly state your CAP choice and justify it. “We need AP because showing a slightly stale cart is better than showing an error page” is a real architectural decision backed by CAP reasoning.


🏢 How real companies solved this

Amazon (2002 — Bezos’s API mandate): Every team must expose data only through service interfaces. No direct database access between teams. This single requirements decision — made before any architecture — created AWS. Requirements shape architectures for decades.

Google — Jeff Dean’s latency table: The “Numbers Every Engineer Should Know” document originated inside Google and became the foundation of how every large-scale system at the company is reasoned about. Back-of-envelope estimation is a first-class engineering skill there.

Netflix — CAP decision for recommendations: They explicitly chose AP. If the recommendation service is partitioned, users get slightly stale suggestions — not an error page. This was a deliberate product decision that preceded the architecture, not the other way around.


📖 Resources

  • System Design Interview Vol. 1 & 2 — Alex Xu (use as reference, not scripture)
  • Designing Data-Intensive Applications — Kleppmann (Ch. 1–2 for foundations)
  • ByteByteGo newsletter — weekly system design breakdowns
  • High Scalability blog: highscalability.com (real architecture case studies)
  • Jeff Dean’s ‘Building Large-Scale Internet Services’ talk (YouTube)

Related