SDSystem design
Start learning free

LESSON 96 OF 140 · PRACTICE PROBLEMS

Live Sports Scores

Read the written walkthrough

SYSTEM DESIGN · INTERVIEW WALKTHROUGH

Design a Live Sports Scores App: System Design Interview Practice

The problem

"Design a live sports scores app." Fans follow their favorite matches and see every goal within a second or two, even when millions follow a final. The scores don't come from users: a sports data company's feed sends each match's goals, cards and clock, one trusted source per match.

This practice problem reuses the pattern of Design Live Comments: open streams to connection servers, each update sent to everyone following. Four things are new: fans follow several matches at once, the clock changes every second, a fan back online must see the right score, and a goal should reach closed apps. Park chat and betting odds.

The numbers

From the interviewer: on a busy Saturday, 10 million fans have the app open, each following about 3 of the 1,000 live matches. Say each match sends an update (a goal, a card, a corner) about once every 10 seconds.

what         working                          result
from feed    1,000 matches × 1 every 10 s     100 a second
per fan      3 matches × 1 every 10 s         0.3 a second
to fans      10 million × 0.3                 3 million a second
servers      10 million ÷ 100,000             100 connection servers
per server   3 million ÷ 100                  30,000 a second

Two common slips: 100 a second forgets that each update goes to every follower, and 300 million multiplies by the 10 seconds instead of dividing. Next to Live Comments, where 2,000 comments a second had to be cut down to 10 per viewer, this is small: every fan gets every update. The cost is holding 10 million open streams.

Many matches: a channel per match

Ben follows m7, m12 and m40. His app opens one server-sent events stream that names its matches, such as GET /stream?matches=m7,m12,m40. The scores service publishes each update once to its match's channel in a pub/sub system. Each connection server subscribes to a match's channel while it holds a fan of that match, and writes each copy into those fans' streams. Following a fourth match is one message on that stream.

One channel for all 1,000 matches would send every app 100 updates a second instead of 0.3: 1 billion messages a second, over 300 times as many, nearly all thrown away on the phone. One stream per followed match would triple the connections to 30 million, 300 servers instead of 100.

Each update carries the match's whole small state, not just the change: the score, the clock and a version number that goes up with every update. A lost or repeated message can't leave a wrong score behind.

The clock: sent when it starts or stops

data: {"match": "m7", "score": [2, 1],
       "clock": {"at": "67:00", "running": true, "since": "15:42:10"}}

Sending the clock every second would be 30 million messages a second (10 million fans × 3 matches), 10 times all the real updates. Instead an update says where the clock stood and since when, and at 15:42:22 the app shows 67:12 by itself. When the clock stops, one update says so. Counting from kickoff alone fails: after the 15-minute half-time break the second half starts at 45:00, while an app counting from kickoff would show 60:00. The stream also sends the server's time, so a phone whose own clock is off still counts right.

Catching up: the latest state, not every update

Ben's train spends 10 minutes in a tunnel. Meanwhile his 3 matches send 180 updates (3 × 600 s ÷ 10 s), two of them goals: Reds 1–1 Blues became 2–1, and Golds 2–2 Blacks became 3–2. Back online, his app needs the scores as they are now, not the steps that led there.

The scores service keeps each live match's latest state in memory: 1,000 matches × about 500 bytes = 500 KB. On reconnect, Ben's server sends him 3 snapshots. Order matters: subscribe to the 3 channels first, then read the snapshots. Read first, and a goal published in between is lost; subscribe first, and it may arrive twice, which the version number handles: the app ignores anything older than what it has.

Replaying all 180 updates would need a log per match and each fan's place in it. Doing nothing, as Live Comments does for a missed comment, leaves Ben's app on 1–1 until m7's next update, minutes away at half time.

Closed apps: pushes for goals

A closed app has no stream; only a push notification through Apple's or Google's push service reaches it. That's the Notification System design: the scores service hands one event, "goal in m7", to the notification system, whose queue and workers send a push to each of m7's followers.

Push only what's worth a buzz: goals, kickoff and the final whistle, a handful per match. Corners, substitutions and stats stay on the open stream: dozens of buzzes a match make people turn notifications off. A push may arrive seconds late, fine for a closed app; opening the app brings the latest state.

Same pattern as Live Comments

Connection servers holding about 100,000 server-sent events streams each, and a pub/sub channel copying each update once per subscribed server, then once per fan: all of it carries over. What changes is the traffic: one trusted writer per match instead of millions of posters, so no rate limit per poster and nothing to pick; tiny updates; and a score that must always be right, hence the snapshot on reconnect.

Summary

  • Scope: follow matches, every update in a second or two, catch up, goal pushes.
  • Data: a small state per match (score, clock, version), the latest kept in memory.
  • API: one server-sent events stream per app, naming its matches.
  • Numbers: about 3 million updates a second to 10 million fans.
  • Scale: a pub/sub channel per match.
  • Clock: sent when it starts or stops; apps tick it.
  • Catching up: subscribe, then the latest state; versions drop repeats.
  • Closed apps: pushes for goals, kickoff and the final whistle.
Keep going with system designInteractive lessons from the building blocks to Twitter, Uber and payments, the way interviews ask. Free to start.
Start learning free