Media & Streaming
Design Live Streaming Platform
01
The problem
The problem
Build a platform where anyone can broadcast live video and anyone else can watch it, in the style of Twitch, Kick or YouTube Live. Creators send one high quality stream from software like OBS. Viewers pick a channel and get smooth playback at whatever quality their network allows, plus a live chat. When a broadcast ends, it is kept as a replay for a while.
What makes this hard is the combination of three pressures. Video is expensive to process: every incoming stream needs real-time encoding into four or five renditions. Delivery is enormously asymmetric: one input becomes millions of outputs, and the popularity of channels is extremely skewed. And everything is on a clock, because a stream that falls ten seconds behind feels broken when chat is reacting to something the viewer has not seen yet.
Say what you are leaving for later: payments and subscriptions, ads, clips, moderation tooling and recommendations. Keep ingest, transcoding, delivery, chat and replay in scope. That is already a full hour.
02
What the platform must do
What the platform must do
- A creator authenticates with a stream key and pushes video over RTMP or SRT.
- Viewers watch any live channel with adaptive quality from 160p up to the source resolution.
- Each channel has a chat room where messages appear for everyone within about a second.
- A directory lists live channels by category and current viewer count.
- Finished broadcasts are saved and playable as replays for 14 days.
- Creators see live health stats: incoming bitrate, dropped frames, viewer count.
- Glass-to-glass latency, camera to viewer screen, under 4 seconds in low latency mode, under 10 in normal mode.
- Rebuffering under 0.5 percent of watch time.
- A single channel can grow from a few hundred to over a million viewers without anyone else's stream suffering.
- If an ingest server or transcoder fails, the stream recovers in a few seconds without the creator restarting.
- Chat favours availability over perfect ordering: losing an occasional message is better than freezing the room.
Ask what latency the product needs. "Under 4 seconds" works with HTTP segments and a CDN. "Under 500 milliseconds" means WebRTC and a completely different, far more expensive delivery tier. Most streaming platforms choose the first and offer the second only for special cases such as auctions or betting.
03
Sizing the load
Sizing the load
Take a peak evening with 90,000 channels live at once and 9 million concurrent viewers. Assume creators send 1080p60 at 6 Mbps and viewers average 3.5 Mbps across the ladder. Chat is busiest in the largest channels.
| Quantity | Working | Result |
|---|---|---|
| Ingest bandwidth | 90K x 6 Mbps | 540 Gbps into our edge |
| Egress bandwidth | 9M x 3.5 Mbps | about 31.5 Tbps, almost all from CDN |
| Fan-out ratio | 31.5 Tbps / 540 Gbps | about 58 out for every bit in |
| Transcoded channels | channels with 5+ viewers, about 40% | 36,000 full ladders |
| Transcode compute | one ladder about 8 vCPU on software x264 | about 290K vCPU, or a few thousand GPU sessions |
| Segments created | 36K ladders x 5 renditions / 2 s parts | about 90K objects / s |
| Origin requests after CDN | two tier cache, 99.5% hit ratio | a few thousand / s per region |
| Replay storage per day | 90K x 3 h average x 6 Mbps source only | about 730 TB, kept 14 days |
| Chat messages | 9M viewers, about 2% typing, 1 message every 20 s | about 9,000 / s in |
| Chat deliveries | skewed to big rooms | tens of millions / s out |
Ingest and transcoding grow with the number of channels. Delivery and chat grow with the number of viewers, and mostly with the viewers of a few huge channels. You cannot serve 31 Tbps from your own origin, so the design is really about producing segments once and letting a CDN multiply them.
Most live channels have almost no viewers. Pass their source through untouched and only start transcoding once a channel crosses a viewer threshold. That alone cuts transcode spend by more than half.
04
API and protocols
API and protocols
The application API hands out a manifest URL and a chat address, and then gets out of the way. Every video byte flows from ingest to transcoder to origin to CDN to player, on infrastructure built for that, never through the same servers that answer directory requests.
05
Architecture overview
Architecture overview
flowchart LR
OBS["Creator encoder"] --> IN["Regional ingest PoP"]
IN --> AU["Stream key auth"]
IN --> TR["Transcoder: ladder and packager"]
TR --> OR[("Origin segment store")]
TR --> AR[("Replay archive")]
OR --> SH["Origin shield"]
SH --> CDN["CDN edges"]
CDN --> P["Viewer player"]
P --> API["Playback API"]
P <--> CH["Chat edge servers"]
CH <--> PS[["Room pub/sub"]]
TR --> ST["Stream state service"]
ST --> DIR["Directory and counts"]A creator's encoder connects to the nearest ingest point of presence, picked by DNS or anycast. Ingest servers are thin: they check the stream key, accept the RTMP or SRT session and forward the raw stream over the provider's backbone to a transcoding cluster in the same region. Keeping the first hop short matters because packet loss on the creator's last mile is the most common source of stutter.
The transcoder decodes the source and re-encodes it into a ladder, perhaps 1080p60, 720p60, 480p, 360p and 160p, all aligned on the same keyframe boundaries so the player can switch between them cleanly. A packager cuts each rendition into short CMAF segments and partial segments, writes them to an origin store, and updates the playlists. A copy of the source rendition goes to the replay archive.
Viewers never touch the origin directly. Their players fetch playlists and segments from CDN edges, which fall back to a regional origin shield on a miss, which falls back to the origin. Chat is a separate system that shares nothing with the video path except the channel ID.
Dozens of small sites near creators. Stateless apart from the open connection, so a creator who reconnects can land on any server and the broadcast ID stays the same.
GPU or dedicated encoder hosts with a scheduler that places each channel on a slot. Popular channels get a hot standby on a second host.
Segments live in memory and on fast disk for a few minutes, since nobody asks for a live segment from an hour ago. The shield collapses requests so each segment leaves the origin once per region.
WebSocket edge servers hold viewer connections and subscribe to the rooms their clients are in. A pub/sub tier routes each message to the edges that care.
06
Deep dive: from webcam to a million screens
Deep dive: from webcam to a million screens
Glass-to-glass delay is the sum of many small waits: encoding at the creator, the network to ingest, transcoding, waiting for a segment to finish, CDN propagation, and the player's buffer. The single biggest number is usually the segment length multiplied by how many segments the player buffers.
flowchart LR A["Camera frame"] --> B["Encoder, about 100 ms"] B --> C["Network to ingest, 50 to 150 ms"] C --> D["Decode and re-encode, 300 to 600 ms"] D --> E["Packager writes 0.5 s part"] E --> F["Origin to edge, 100 to 300 ms"] F --> G["Player buffer, 3 parts"] G --> H["Frame on screen"]
The transcode ladder
A viewer on hotel Wi-Fi cannot sustain 6 Mbps, so you encode the same picture several times at different sizes and let the player choose. A sensible ladder is the source at 1080p60, then 720p60 at about 3.5 Mbps, 480p at 1.5 Mbps, 360p at 0.8 Mbps and an audio-heavy 160p for poor connections. Every rendition must put keyframes at exactly the same timestamps, typically every two seconds, because the player can only switch rendition at a keyframe.
Transcoding in real time is the main compute bill. Software x264 at a fast preset gives good quality per bit but needs a lot of CPU for 1080p60. Hardware encoders on GPUs or dedicated chips are far cheaper per stream with slightly worse compression. Large platforms often mix both: hardware for the long tail, careful software encodes for the biggest channels where every saved bit multiplies across a million viewers.
To avoid paying for ladders nobody watches, start every new broadcast in passthrough mode where viewers get only the source. When the viewer count crosses a threshold, perhaps five, the scheduler assigns a transcoder slot and the master playlist gains extra renditions on its next refresh.
From a continuous stream to cacheable files
CDNs are excellent at serving files, so we turn video into files. The packager cuts each rendition into fixed-length segments in CMAF (fragmented MP4) and writes a playlist that lists the most recent few. Players poll the playlist, download new segments and play them in order. The playlist is the only object that changes; the segments are immutable and can be cached with long lifetimes.
With classic 6-second segments and a three-segment buffer, latency lands near 20 seconds. Shorter segments help, but a 1-second segment means a keyframe every second, which hurts compression. Low-Latency HLS solves this by publishing partial segments of about half a second as they are produced, while full segments keep their two-second keyframe interval. The playlist advertises the next part before it exists, and the player issues a blocking request that the edge holds open until the part arrives. With three parts buffered, the player sits around 1.5 seconds behind the live edge.
Fanning out through the CDN
When a big channel goes live, hundreds of thousands of players ask for the same new part within the same half second. Without care, each CDN edge misses and asks the origin at once. Two mechanisms stop that. Request collapsing at the edge sends one upstream fetch per object and parks the other requests on it. An origin shield per region adds a second layer, so the origin sees a handful of requests per segment, not one per edge.
Playlists need a short TTL, about half the part duration, while segments can be cached for minutes. For the very largest events you can pre-position by pushing segments to edges instead of waiting to be pulled, or spread the load across two CDN providers with a traffic steering layer that shifts viewers when one degrades.
Chat beside the video
Viewers connect to a WebSocket edge, which subscribes to the room on a pub/sub tier. When someone sends a message, the edge validates it, applies rate limits and moderation filters, and publishes it to the room. Every edge holding members of that room receives one copy and writes it to each local socket. A room of 500,000 people spread over 400 edges costs 400 internal deliveries per message, not 500,000.
Huge rooms produce more text than anyone can read. Past a few hundred messages per second, the edge samples or batches, sending a bundle every 200 milliseconds. Nobody notices a dropped "LUL" among thousands; everybody notices a frozen chat.
If video is 4 seconds behind and chat is 300 ms behind, chat spoils what is about to happen. Players know their own latency, so they can delay rendering chat messages to match the video position, using the server timestamp on each message.
07
Decisions and what they cost
Decisions and what they cost
Two to four seconds of delay, works in every browser and phone, and rides on commodity CDN capacity measured in tens of terabits. The cost is a more complex packager and players that support blocking playlist reloads.
Default deliverySub-second delay, ideal for auctions or co-streaming. But each viewer needs a stateful session on a media server, so delivering 9 million streams means building your own global CDN for real-time media.
Only for special featuresKeyframes every two seconds keep compression efficient, while parts let the player stay close to the live edge. Edges and origin handle about four times more requests than with plain segments.
BalancedFewer requests, higher cache efficiency and better quality per bit, with 15 to 25 seconds of delay. Fine for broadcast events where nobody is chatting, poor for interactive streams.
Normal latency modeMost channels never pay for a ladder. The small cost is that the first few viewers of a new stream may only get the source rendition, which can be heavy on mobile.
Big cost savingSimple and uniform, but it more than doubles the transcode fleet to serve channels watched by nobody.
WastefulOne internal message per edge per room keeps internal traffic proportional to the number of servers, not viewers. Ordering is per publisher only, which chat tolerates.
Scales with roomsGives a perfect, ordered history, but puts a database write on the hot path of millions of deliveries. Write to a log asynchronously instead, for moderation and replays.
Too slow at peak08
Failure modes
Failure modes
Home upload links flicker. If the platform treats every disconnect as the end of a broadcast, viewers get an "offline" screen and the replay splits in two.
Hold the broadcast open for a grace period of about 30 seconds, show a "reconnecting" slate in the playlist, and resume the same broadcast ID when the encoder returns, on any ingest server.Every channel on that host stops producing segments. Players hit the end of the playlist and start buffering.
The scheduler sees missed heartbeats within two seconds and moves the channel to a spare slot. For channels above a viewer threshold, run a hot standby transcoder that the packager can switch to without a gap.A channel goes from zero to 1.5 million viewers in ten minutes. Edges in one country saturate and the origin shield sees a burst of misses for each new part.
Request collapsing and shields keep origin load flat. Steer part of the audience to a second CDN, and let players drop a rung on the ladder automatically when they see slow downloads.A raid or a big play sends 20,000 messages a second into one room. Edges spend their CPU serialising text and sockets start to lag behind.
Switch the room to slow mode automatically, batch deliveries every 200 ms, and sample messages above what a person can read. Rate limits per user keep spam bots in check.A creator shows their key on screen. Someone else connects and broadcasts on their channel.
Allow one active session per key and alert the owner on a takeover attempt, offer one-click rotation, and keep keys hidden by default in the dashboard.After a few stalls, a player is twelve seconds behind and chat makes no sense to that viewer.
Players compare their position with the program date time in the playlist and catch up by playing slightly faster, or jump to the live edge if they fall more than a set distance behind.09
How to handle the interview
How to handle the interview
Split the problem into ingest, process, deliver and chat. Each has a different bottleneck, and saying that early gives the interview a clear structure.
Compute the fan-out ratio. Showing that egress is fifty times ingest explains why the CDN is the system and the origin should be protected at all costs.
Build a latency budget. List each stage with milliseconds attached and show which knob, mostly segment and part length, moves the total.
Know why keyframes must align across renditions. It is a short detail that proves you understand adaptive bitrate rather than reciting acronyms.
Raise the transcode cost yourself. Point out that most channels have few viewers and propose transcoding on demand. Interviewers like candidates who notice money.
Answer the thundering herd question with layers. Edge collapsing, origin shield, multi-CDN. Then mention players stepping down the ladder.
Treat chat as a separate design. Show that edge-level fan-out makes room size cheap, and that sampling is acceptable in huge rooms.
Explain when you would choose WebRTC. Name the use case (sub-second interaction) and the cost (stateful media servers per viewer), and keep it out of the default path.
10
Growing the design in stages
Growing the design in stages
An open source media server accepts RTMP and writes HLS to local disk, served by a web server. Latency is about 15 seconds and there is no transcoding. Enough to prove the product.
Segments move to an origin store and a CDN serves viewers. Chat moves to its own WebSocket service with a simple pub/sub.
Ingest PoPs open near creators, and a scheduler places channels on GPU transcoder slots with on-demand ladders. Viewers finally get adaptive quality.
Partial segments bring delay under four seconds. Origin shields and request collapsing protect the origin, and the single-origin delivery model is retired.
Traffic steering spreads viewers across CDNs, and the largest platforms place their own caches inside ISPs to cut transit costs.
Watch and read
Further watching and reading
Try next
Free to read · better with landed
Whiteboard this with landed
landed runs it as a live system design round on the whiteboard and grades your trade-offs.

