Sticky Reads and Session Consistency: How Bounded Read Routing Works

 


A user changes their profile name from Alex to Alexander.

The write goes to the primary database and succeeds.

The next request reads the profile from a replica. If replication has not caught up yet, the user may still see Alex.

The following request may hit another replica and return Alexander.

This is where sticky reads can help.

What Are Sticky Reads?

Sticky reads temporarily associate a user's relevant reads with an appropriate database node after an operation that requires stronger read consistency.

A simple post-write flow looks like this:

Write → Primary
   ↓
Mark session as sticky
   ↓
Next reads → Primary
   ↓
Sticky period expires
   ↓
Normal replica routing

The important concept is the bounded period.

The user should not remain permanently pinned to the primary.

How Does It Work?

The application can maintain routing state such as:

Session ID → Preferred node + Expiry

Session 12345 → Primary → 3 seconds

While the sticky period is active, relevant reads from that session are routed to the preferred node.

After expiration, normal read routing resumes.

For a horizontally scaled application, this state needs to be available regardless of which application server receives the request.

It could live in a shared session store, distributed cache, or another suitable shared-state mechanism.

Why Make It Bounded?

Permanent primary routing can quickly become expensive.

Imagine thousands of users remaining pinned to the primary after a write:

  • Primary read traffic increases
  • Replicas receive less traffic
  • Read scalability is reduced

A bounded window limits how long the primary has to handle those reads.

For example:

Write
  ↓
Sticky for 3 seconds
  ↓
Primary handles relevant reads
  ↓
Expiration
  ↓
Normal replica routing

The exact duration should depend on the application's requirements rather than using an arbitrary value.

How Do You Choose the Duration?

The sticky window is a consistency vs. scalability trade-off.

Factors to consider include:

  • Typical replication lag
  • User interaction patterns
  • Frequency of reads after writes
  • Importance of immediate visibility
  • Primary database capacity
  • Replica capacity

A very short window reduces primary load but may expire while replicas are still behind.

A very long window increases the consistency window but sends more reads to the primary.

Sticky Reads ≠ Replica Freshness

This is an important distinction.

Suppose a session is pinned to Replica A:

User → Replica A

If Replica A is behind, the user can still receive stale data.

Stickiness controls routing. It does not make a replica catch up.

For post-write consistency, routing the relevant reads to the primary is often the straightforward approach.

If reads must return from replicas, the application needs an additional freshness mechanism or guarantee.

Common Mistakes

Making Stickiness Permanent

This unnecessarily increases primary read traffic and reduces the benefit of read replicas.

Assuming Stickiness Makes a Replica Fresh

It doesn't. A sticky replica can still be behind.

Choosing the Window Arbitrarily

A three-second or five-second timer is not a universal consistency guarantee. The window should reflect real application and replication behavior.

Storing State Only in Local Memory

With multiple application servers, the next request may reach another server that does not know the session is sticky.

Key Takeaway

Sticky reads are a temporary routing strategy.

They allow an application to keep relevant reads on an appropriate database node for a bounded period, then return the session to normal replica routing.

The goal is to improve user-visible consistency without permanently sacrificing read scalability.

The real design question is:

How long should the sticky window be for your application's consistency requirements and replication behavior?

What would you use in an internet-scale application — a fixed time window, replica-lag awareness, or another approach?

Share your technical perspective in the comments.

If you found this useful, follow for more practical system-design and distributed-systems content, and subscribe for future deep dives on my Linkedin and Subsstack.

Previous Post Next Post