Pub/Sub, Queues & Leaderboards

5.Announcements Everyone Hears at Once

M

In this chapter

We'll meet Redis Pub/Sub and Queues as genuinely different tools, build a real order-confirmation queue and a live leaderboard, and see where Streams fit between them.

9–11 min

The Problem in Real Life

Two more real problems show up as the flash sale keeps climbing. First: GreenMart wants every open storefront tab to show "Only 3 left!" the instant stock actually changes — not a few seconds later, on the next refresh. Second: order confirmations are piling up faster than the email service can send them, and losing one because it arrived while the service was briefly overloaded isn't acceptable.

Two different problems. Sarah reaches for two genuinely different tools, on purpose.

S

One of these needs to shout it out right now. The other needs to hold onto it until someone's ready.

Sarah

Broadcast Now vs. Hold Until Ready

Pub/Sub broadcasts, stores nothing

Every currently-subscribed client hears a published message instantly — a client that wasn't listening simply misses it, by design.

Queues hold work until it's handled

LPUSH adds work, RPOP claims the oldest — nothing is lost just because a consumer was briefly unavailable.

Leaderboards stay sorted automatically

A Sorted Set's ZRANGE always returns score order, with no separate sort step, however often scores change.

Streams sit between the two

A durable, replayable log — multiple independent readers, each tracking their own position, nothing dropped.

Pub/Sub, Queues & Leaderboards

Pub/Sub (publish/subscribe) is Redis's live broadcast mechanism: a client PUBLISHes a message to a named channel, and every client currently SUBSCRIBEd to that channel receives it immediately. Nothing is stored — a client that wasn't listening at that exact moment simply never gets that message. That's not a limitation to work around; it's the entire point for something like "stock just changed, update the number on screen right now" — a client that opens the page a minute later just fetches the current stock directly, it doesn't need yesterday's announcements replayed to it.

A Queue is the opposite shape on purpose: messages wait until a consumer is ready for them, and nothing gets silently dropped just because nobody happened to be listening at the moment it arrived.

LPUSH adds each new order confirmation to one end of the list; RPOP (from a worker process, running whenever it's ready) removes and returns the oldest one still waiting. Nothing is lost if the email service is briefly overloaded — the queue simply grows until it catches up, instead of dropping messages nobody was listening for.

A Queue — Order Confirmations, Held Until Processed
LPUSH email:queue "order-4471"
LPUSH email:queue "order-4472"
RPOP email:queue
RPOP email:queue

The same Sorted Set from a couple chapters back, now doing real leaderboard work: ZADDing a new score for a member that already exists replaces its old score rather than adding a second entry — sel-01's score becomes 15, not 12 plus 15. ZRANGE ... WITHSCORES always comes back in score order, with zero separate sorting step, no matter how often scores change underneath it.

A Leaderboard — Live, Always Sorted
ZADD today:top-sellers 12 "sel-01"
ZADD today:top-sellers 7 "sel-02"
ZADD today:top-sellers 15 "sel-01"
ZRANGE today:top-sellers 0 -1 WITHSCORES

This is exactly where the Stream from a couple chapters ago earns its place: it's built to be what Pub/Sub is missing on purpose — a durable, replayable log — while still supporting something close to a live broadcast, since a consumer can keep reading new entries as they arrive. Where a Queue is consumed once and gone, and Pub/Sub is heard only by whoever's listening right now, a Stream can be both: multiple independent readers, each replaying from wherever they left off, with nothing disappearing just because a consumer was briefly offline.

Redis giving GreenMart both Pub/Sub and Queues, as genuinely different tools rather than one blurred "messaging" feature, matters because picking the wrong one has a real cost: a live stock update queued instead of broadcast would show up late; an order confirmation broadcast instead of queued would vanish the moment nobody happened to be listening.

Key Takeaway

Pub/Sub broadcasts to whoever's listening right now, with nothing stored. A Queue holds messages until a consumer is ready. Picking the wrong one for a given problem has a real, concrete cost — late updates, or lost messages.

Why This Matters

Real-time features across GreenMart's storefront — live stock counts, order status updates, notifications — all come down to this same choice: does this need to reach everyone listening right now, or does it need to be held until someone's ready to handle it? Getting that choice right, early, avoids building the wrong kind of "real-time" feature entirely.

GreenMart's flash sale can broadcast live changes and hold onto work that has to be processed eventually, without losing either kind. One real risk is still sitting there, though — everything this Act has built lives in memory, and memory doesn't survive on its own if Redis itself ever restarts.

Next