SDE Path

Multi-channel fan-out

Design a Notification System

Medium

Fan one event out to millions across push, SMS, and email — reliably, and without ever spamming a user.

A notification system delivers messages to users across many channels — mobile push (APNs/FCM), SMS, email, and an in-app inbox — from a single internal event. It sits behind almost every product: OTPs, order updates, social alerts, and marketing blasts all flow through it.

Three forces make it a genuine design problem:

  • Fan-out at scale — one trigger can expand to millions of recipients (a broadcast), and each recipient may want several channels.
  • Reliable delivery — external providers time out, throttle, and fail, yet an OTP must still arrive in seconds. At-least-once + idempotency is the spine.
  • Don't spam — preferences, quiet hours, dedup, and frequency caps decide whether and when to send, not just how.

The whole design is a buffered, asynchronous pipeline: ingest → policy → per-channel fan-out → workers → providers, with retries, dead-letter queues, and delivery-status tracking throughout.

Start by scoping. The interviewer wants to see you split transactional traffic (OTP, order, security — urgent, high-reliability) from bulk/marketing (deferrable, fully governed by user preferences). That split, plus the "never spam" constraint, drives every later decision.

Functional

  • Send a notification from an internal event to one user or a segment, across one or more channels.Rendered from a per-locale template with per-user data at send time.
  • Multi-channel delivery — route to push (APNs/FCM), SMS, email, and an in-app inbox.Channel selection follows the user's stored preferences.
  • User preferences — per-channel and per-category opt-in/out, quiet hours, and frequency caps.
  • Fan-out / broadcast — expand one campaign trigger to millions of recipients.
  • Reliable delivery — retry failed sends, track delivery status, and never silently drop a message.

Non-functional

  • Transactional latency — OTP/security messages delivered in seconds, targeting 99.9%+ delivery; marketing may take minutes.
  • Fan-out scale — ~2×10⁸ notifications/day; ~2k average and ~10k peak dispatch QPS across channels.
  • Burst absorption — a single broadcast can enqueue ~10⁷ messages in ~100 s and must be buffered, not sent inline.
  • Respect the user — strictly honor opt-outs, quiet hours (in the user's timezone), and per-user frequency caps.
  • Durability — an accepted notification is never lost; at-least-once delivery with a dead-letter path for the un-deliverable.

Out of scope

  • Notification content authoring / campaign UI
  • Analytics dashboards & A/B testing
  • Real-time chat / two-way messaging
  • Spam-content ML classification

Check yourself· 3 questions

Question 1

Which combination is the real crux of this system and shapes the whole pipeline?

Question 2

Why model the send API as asynchronous (accept + enqueue) rather than synchronous with the caller?

Question 3

Which is a correctly-framed non-functional requirement for this system?