The famous feed debate — build it at write time or read time — is usually argued on speed. LinkedIn switched approaches for a reason nobody mentions: their old design made it nearly impossible to experiment with relevance.
LinkedIn's earlier feed used fan-out-on-write, which is great for fast reads. But improving the feed means constantly A/B-testing new relevance models — and in a write-time design, re-scoring everyone's feed meant rewriting an enormous amount of precomputed data ("grandfathering"), an IO-intensive slog that throttled the pace of experimentation.
There are two moments you can build someone's feed. Fan-out-on-write: the instant someone posts, copy that post into the timeline of every follower. Reads are then instant (the timeline is pre-built), but a single post by a popular account triggers millions of writes. Fan-out-on-read: store posts once, and when a user opens the app, gather the latest from everyone they follow and assemble the feed on the spot. Writes are cheap; reads do more work.
The textbook trade-off is 'write-heavy vs read-heavy.' LinkedIn's real driver was different: how easily can you change how the feed is ranked?
LinkedIn rebuilt the feed (FollowFeed) around fan-out-on-read. The store is keyed by (entity + content type) with the value a reverse-chronological list of that entity's records, held in an over-partitioned in-memory index for speed. When you load your feed, the system pulls recent records from the entities you follow and scores relevance on the fly, rather than serving pre-baked scores.
The guiding principle was "bring computation closer to data": keep the raw records ready and compute ranking at query time. That single change is what made relevance experimentation cheap — a new model just changes the scoring step at read time, instead of forcing a rewrite of every materialised timeline.
Worth knowing
Most explanations of fan-out stop at "write-time = fast reads, read-time = cheap writes." LinkedIn's case adds the dimension that actually decides it for a ranked feed: iteration speed on relevance. If the feed is chronological, pre-materialising it is fine. If it's a constantly-tuned ML ranking, you want scoring at read time so experiments don't require rewriting history. Pick the strategy by what you'll change most often.
The gap it reveals
Candidates recite the fan-out trade-off as a static speed comparison. The senior realisation is that for a ranked, ML-driven feed, the dominant cost is the ability to re-score and experiment — which fan-out-on-write makes brutal (grandfathering) and fan-out-on-read makes cheap. Choosing based on iteration velocity, not just read/write ratio, is the insight.
In the interview room
"Design a news feed" is a canonical question, and most candidates parrot the fan-out trade-off. Stand out by adding: "if ranking is chronological I'd fan out on write; if it's a frequently-retuned relevance model I'd fan out on read so I can re-score at query time without rewriting everyone's timeline." Tying the choice to experimentation cost shows product-aware system thinking.
The reframe
The right architecture depends on what you'll change most. A design optimised for fast reads can quietly be terrible for the thing you actually do every week — ship a new ranking model. LinkedIn chose the architecture that made their core ongoing activity cheap, even though it asked more of each read. Optimise for the operation you'll repeat a thousand times, not the one that looks fastest on a diagram.
Don't optimise the feed for reading. Optimise it for the thing your team does daily: changing the ranking.
Primary source →
engineering.linkedin.com — FollowFeed: LinkedIn's Feed Made Faster and Smarter