Requirements
- Generate a personalized feed of posts ranked by relevance/recency for each user
- Supports follow relationships: see posts from users you follow
- 500M users, 10M DAU, 100K new posts/minute
- Feed load time <200ms; new posts appear in feed within 5 seconds
- Mixed content: posts, images, videos, reposts
Two Approaches: Fan-out on Write vs Fan-out on Read
Fan-out on Write (push model): when a user publishes a post, immediately write it to the feed of all followers. Feed reads are fast (pre-built). Write amplification: if a user has 1M followers, 1 post = 1M feed writes. Good for users with few followers. Bad for celebrities (Justin Bieber problem).
Fan-out on Read (pull model): when a user opens their feed, fetch recent posts from each followee and merge/rank them in real time. No write amplification. Feed generation is slow (O(followees) fetches per request). Good for power users with many followees.
Hybrid (recommended): fan-out on write for normal users ( 10K followers). On feed load: merge pre-built feed (from write fan-out) + real-time fetch of recent celebrity posts.
Data Model
Post(post_id UUID, author_id, content TEXT, media_urls[], post_type ENUM(TEXT,IMAGE,VIDEO,REPOST),
repost_of UUID, created_at, like_count, comment_count, share_count)
Follow(follower_id, followee_id, created_at)
-- Index: (follower_id, created_at DESC) for "who I follow"
-- Index: (followee_id, follower_count) for follower count
FeedItem(user_id, post_id, score FLOAT, post_created_at, source ENUM(FOLLOW,RECOMMEND))
-- Stored in Redis sorted set: key=feed:{user_id}, member=post_id, score=ranking_score
Feed Generation Service
On new post published by user U:
1. Publish to Kafka topic: new_posts
2. Fan-out workers consume from Kafka:
a. Fetch follower IDs of U (from Follow table, paginated)
b. For each follower F (if follower count of U <= 10K):
ZADD feed:{F} {score} {post_id}
ZREMRANGEBYRANK feed:{F} 0 -501 # keep top 500 only
3. Score = recency_score + engagement_score + personalization_score
The feed sorted set in Redis stores post_ids ordered by score. On feed read, ZREVRANGE feed:{user_id} 0 49 fetches the top-50 post_ids in O(log n + k). Then a batch DB lookup fetches post content for those IDs.
Ranking Score
score = 0.4 * recency + 0.3 * engagement_velocity + 0.2 * relationship_weight + 0.1 * content_type_pref recency = 1 / (1 + hours_since_post) # decays over time engagement_velocity = (likes + comments*2 + shares*3) / hours_since_post relationship_weight = close_friend ? 1.5 : 1.0 # based on interaction history content_type_pref = user_affinity_for_content_type # from ML model
Pagination and Cursor
Cursor-based pagination on the feed: the client sends last_seen_score on each request. The server fetches items with score < last_seen_score. This avoids the "shifting page" problem (offset pagination breaks when new items are inserted). Store cursor in the client; the server is stateless.
New Post Delivery (5s SLA)
Fan-out workers process Kafka messages in near-real-time. For a user with 100K followers: fan-out = 100K ZADD operations. At 1ms per Redis operation, this takes ~100 seconds sequentially. Solution: parallel fan-out workers, each handling a shard of followers. With 100 parallel workers, 100K followers → 1K per worker → ~1 second total. Kafka partition by user_id for ordering; fan-out workers scale horizontally.
Key Design Decisions
- Hybrid fan-out: write for normal users, read for celebrities — eliminates write amplification spikes
- Redis sorted set for feed — O(log n) insert, O(log n + k) range read, automatic score-based ranking
- Kafka fan-out workers — async, scalable, fan-out doesn’t block the post API
- Cursor pagination — correct behavior for real-time feeds with frequent inserts
- Score-based ranking — decoupled from storage; score can be recomputed by a re-ranking job
Meta system design is the canonical news feed interview topic. See common questions for Meta interview: news feed and content ranking system design.
Twitter system design covers feed generation and ranking. Review patterns for Twitter interview: content feed and timeline system design.
Snap system design covers content feeds and story delivery. See design patterns for Snap interview: content feed and story system design.
See also: Anthropic Interview Guide 2026: Process, Questions, and AI Safety