System Design Arena

System Design: Twitter

Handle tweet creation, fan-out, search, notifications, and moderation for hundreds of millions of users.

Functional RequirementsNon-Functional RequirementsAPI Endpoints

Case Study

Microblogging Platform

Same conversation, diagrams, and wrap-up you expectโ€”now framed with clearer scaffolding and iconography.

Prompt

Design Twitter. Tweets up to 280 chars, images/video, retweets/likes, timelines, trends, and near real-time notifications for 400M users.

Interview snapshot

  • โ€ข Topic: Microblogging Platform
  • โ€ข Expected depth: 45 - 60 minutes
  • โ€ข Focus areas: APIs, scale estimation, resilient architecture
  • โ€ข Wrap-up: risk, monitoring, disaster recovery

Key takeaways

  • โ€ข Post tweets (text, media) with hashtags, mentions.
  • โ€ข Latency: <1s to publish tweet, <300ms timeline load.
  • โ€ข POST /api/tweets - create tweet (text + media IDs).

๐ŸŽ™๏ธ Interview mode

Practice this like a real interview

Don't read the answer first. Work the framework against the bare prompt, then compare against what the interviewer expected at each step.

๐ŸŽฏ Start guided practice (free)

Scorecard

What the interviewer is evaluating

Requirements7/10
Scale estimation8/10
API design6/10
Architecture9/10
Trade-offs10/10
Failure handling6/10

Staff-level signal

The whole interview is one trade-off: fan-out-on-write vs fan-out-on-read, and the hybrid for celebrity accounts. Does the candidate get there unprompted?

๐Ÿง  Staff engineer judgment

Nobody needs their timeline to be transactionally consistent. Chasing strong consistency here costs you the design; spend it on delivery latency instead.

Calibration

The common (bad) answer

User posts tweet โ†’ DB
Follower opens app โ†’ SELECT tweets FROM followed users ORDER BY time

โŒ Why this scores poorly: The JOIN-at-read-time answer. Correct at 1K users, catastrophic at 100M โ€” computing a timeline by querying hundreds of followed accounts per refresh is the exact problem this question exists to probe.

โœ“ What a strong answer adds

  • Fan-out-on-write: push tweets into follower timeline caches at post time.
  • Then break your own design: a 100M-follower celebrity makes one post = 100M writes.
  • Hybrid: precompute for normal users, merge celebrity tweets at read time.
  • Timeline as a bounded Redis list per user โ€” old entries fall off, storage stays sane.
  • Say what is eventually consistent (timelines) and what is not (your own tweets).

Build it up

Step-by-Step Walkthrough

Twitter is the canonical read-heavy feed problem: ~10K tweets/s written, two orders of magnitude more timeline reads. The whole interview hinges on one question โ€” do you build the timeline when the tweet is written, or when the reader shows up?

1

Naive timeline: query it at read time

One API server, one relational database. POST /api/tweets inserts a row; the home timeline is a query โ€” select tweets from everyone I follow, order by time, limit 50. For a prototype with a thousand users this is completely correct.

Say the bottleneck out loud: every timeline load joins the follow graph against the tweets table. At ~500M tweets/day and users following ~200 accounts each, that join runs millions of times a second against constantly-growing tables. The read path collapses first, and it collapses hard.

?State the ratio before touching the diagram

~500M tweets/day is only ~6K writes/s average, ~10K/s peak โ€” trivially storable. But each tweet is read hundreds of times via timelines. Reads outnumber writes ~100:1, which is the number that justifies everything you build next.

2

Fan-out on write: precompute every timeline

Flip the work to the write path. When a tweet lands, publish it to Kafka; a fan-out service reads it and pushes the tweet ID into a Redis-cached timeline list for each follower. Now the home timeline API is a single cache read โ€” comfortably under the ~300ms budget.

The write amplification is real but affordable for normal users: 200 followers means ~200 cheap list pushes, on the order of ~2M fan-out operations/s platform-wide. Kafka absorbs the burst; the fan-out workers scale horizontally and can lag a few seconds without anyone noticing โ€” timelines are explicitly eventually consistent.

3

The celebrity problem forces a hybrid

Then someone with ~100M followers tweets, and your fan-out service owes ~100M cache writes for one 280-character message. Storms of these back up Kafka and delay everyone's timeline. Pure push does not survive a skewed follower distribution.

The interview-winning move is the hybrid: fan out on write for normal accounts, but for high-follower accounts, skip fan-out entirely and pull their recent tweets at read time, merging them into the reader's cached timeline. Each user pays a small merge cost for the handful of celebrities they follow โ€” bounded work on both paths.

!Interviewers will push on the threshold

Where is the push/pull cutoff? There is no magic number โ€” it is a cost curve: fan-out cost grows with followers, merge cost grows with how many pulled accounts a reader follows. Say you would tune it empirically (commonly cited in the tens of thousands of followers) and that accounts can cross the line dynamically.

4

Tweets need a home: storage, media, and search

The timeline cache holds IDs, not content. Tweet bodies go to a write-optimized wide-column store (Cassandra-style) partitioned by tweet ID โ€” billions of rows, ~250 GB/day of text, with old partitions tiered to cold storage. Media never touches this path: uploads go through a separate pipeline that transcodes and serves via CDN, with the tweet storing only media IDs.

Search and trends hang off the same Kafka stream that feeds fan-out: an indexer writes into Elasticsearch/OpenSearch for keyword queries, and a streaming aggregator counts hashtag velocity for trending topics. Nothing about search sits on the tweet-publish critical path.

5

Moderation and notifications close the design

A moderation service consumes the tweet stream too: ML models score every tweet for spam and abuse, high-confidence cases are actioned automatically, and the ambiguous middle flows to a human review tool. Every action lands in an audit log โ€” GDPR deletes and provenance requirements make this non-optional, and raising it unprompted reads as senior.

Notifications (~50K events/s for likes, replies, mentions) are one more Kafka consumer feeding a push service that fronts APNs/FCM. The finished shape is one durable event stream with independent consumers โ€” fan-out, search, moderation, notifications โ€” each of which can lag or fail without touching tweet publish latency.

?The closing move

Re-state the guarantees: publish in under a second, timelines under ~300ms from cache, everything downstream eventually consistent by design. One event stream, many consumers โ€” that sentence is the architecture.

Blueprint

Architecture Diagram

The narrated components above, laid out as an actual flow โ€” so you can see how a request moves through the system, not just read a list of pieces.

Tweet ingest

1

Tweet ingest

2

metadata DB (Cassandra) + search index

metadata DB (Cassandra) + search index (Elastic)

Fan-out service reads

1

Fan-out service reads tweets from Kafka

Fan-out service reads tweets from Kafka, writes to timeline caches

Home timeline API

1

Home timeline API merges cached fan-out

2

on-demand fetch for missing users

Media pipeline handles

1

Media pipeline handles uploads

Media pipeline handles uploads, transcoding, CDN distribution

Moderation service consumes

1

Moderation service consumes tweet stream

Moderation service consumes tweet stream, ML inference, human review tool

Flow Diagram

How the API maps to this flow

  1. 1POST /api/tweetsโ€” create tweet (text + media IDs).
  2. 2GET /api/timelines/homeโ€” returns personalized timeline.
  3. 3POST /api/tweets/{id}/like or /retweetโ€” engagement actions.
  4. 4GET /api/search?q=โ€” keyword search (Elastic/OpenSearch).
  5. 5POST /api/moderation/flagsโ€” report tweet/user.

?But why does this actually hold up at scale?

Tweets: 500M/day ~ 5.8K/s average, 10K/s peak. Storage: 500M * 500 bytes = 250 GB/day -> 90 TB/year (before media).

Video walkthrough

Design Twitter โ€” System Design Interview

NeetCode ยท 26 min

The fan-out-on-write vs fan-out-on-read decision, which is the whole interview for this question.

Work the prompt yourself first โ€” guided practice grades your own answer step by step. Watching someone else design it feels like progress and teaches you far less.

Interview flow

Dialogue timeline

Interviewer

Where do you start?

Candidate

Core flows: post tweet, home timeline, notifications, search/trends, moderation. Need write throughput ~10K tweets/s, read fan-out 100x that.

Interviewer

Discuss timeline architecture.

Candidate

Hybrid push/pull. Fan-out to home timelines for high-follower accounts asynchronously (Kafka + Redis). On-demand merge for long-tail following lists.

Interviewer

Moderation/governance?

Candidate

ML + rules flag tweets; human review pipeline. Need audit log of actions, tooling to shadow-ban or remove content quickly.

Scoping

Requirements & trade-offs

Functional Requirements

  • โ€”Post tweets (text, media) with hashtags, mentions.
  • โ€”Home timeline sorted by recency/relevance.
  • โ€”Engagement: likes, retweets, replies, quote tweets.
  • โ€”Notifications, DMs, search, trending topics, lists.
  • โ€”Moderation + rate limiting for spam/bots.

Non-Functional Requirements

  • โ€”Latency: <1s to publish tweet, <300ms timeline load.
  • โ€”Availability 99.95%; eventual consistency acceptable for timelines.
  • โ€”Storage: billions of tweets (cold storage tiering).
  • โ€”Compliance: GDPR delete, audit logs, content provenance.

Blueprint

Architecture modules

Module 1

API Endpoints

  • โ€ขPOST /api/tweets - create tweet (text + media IDs).
  • โ€ขGET /api/timelines/home - returns personalized timeline.
  • โ€ขPOST /api/tweets/{id}/like or /retweet - engagement actions.
  • โ€ขGET /api/search?q= - keyword search (Elastic/OpenSearch).
  • โ€ขPOST /api/moderation/flags - report tweet/user.

Module 2

Back-of-the-Envelope

  • โ€ขTweets: 500M/day ~ 5.8K/s average, 10K/s peak. Storage: 500M * 500 bytes = 250 GB/day -> 90 TB/year (before media).
  • โ€ขHome timeline fan-out: assume avg user follows 200 accounts, tweet fan-out per second ~2M operations; use Kafka + Redis.
  • โ€ขMedia: images/video served via CDN; 5 PB storage live, with lifecycle policies.
  • โ€ขNotifications: 50K events/s -> push service + APNs/FCM.

Module 3

System Diagram Notes

  • โ€ขTweet ingest -> metadata DB (Cassandra) + search index (Elastic).
  • โ€ขFan-out service reads tweets from Kafka, writes to timeline caches.
  • โ€ขHome timeline API merges cached fan-out + on-demand fetch for missing users.
  • โ€ขMedia pipeline handles uploads, transcoding, CDN distribution.
  • โ€ขModeration service consumes tweet stream, ML inference, human review tool.

Module 4

Design Playbook

  • โ€ขClarify fan-out strategy, caching, eventual consistency.
  • โ€ขExplain tweet storage (hot vs cold) and search indexing.
  • โ€ขCover spam detection, rate limiting, abuse tooling.
  • โ€ขDiscuss observability: tweet latency, dropped fan-outs, trending detection.
  • โ€ขMention disaster recovery, data privacy obligations.