CAP Theorem and Consistency Models, Explained Plainly

The CAP theorem in plain English — what consistency, availability and partition tolerance really mean, PACELC, strong vs eventual consistency, quorums, and how to apply it in real designs.

By Danyal Ahmed - Data Scientist · · 5 min read

The CAP theorem is one of the most quoted and most misunderstood ideas in distributed systems. "Pick two of three" is a catchy summary but a misleading one. This guide explains what CAP actually says, the more useful PACELC extension, and how consistency choices play out in real systems.

Key takeaways

  • CAP applies to distributed data systems during a network partition: you must choose between consistency (every read sees the latest write) and availability (every request gets a non-error response).
  • Partitions aren't optional in real networks, so "CA" isn't a real choice for distributed systems. The choice is CP or AP when a partition happens.
  • PACELC adds: even without partitions, you trade latency against consistency.
  • Consistency is a spectrum: strong, linearizable, sequential, causal, read-your-writes, eventual.
  • Choose consistency per operation, based on what goes wrong if data is stale.

The three properties (precisely)

  • Consistency (C): in CAP, this means linearizability. Every read returns the most recent write, as if there were a single copy of the data. (Not the "C" in ACID, which is about integrity constraints.)
  • Availability (A): every request to a non-failing node receives a (non-error) response, without guaranteeing it reflects the latest write.
  • Partition tolerance (P): the system keeps operating even when network messages between nodes are lost or delayed.

What CAP actually says

Imagine two database replicas, one in each data center, and the link between them fails:

text   Client A ─▶ [Replica 1]   ✖ network partition ✖   [Replica 2] ◀─ Client B
               balance=100                           balance=100

Client A writes balance = 50 to Replica 1. Client B reads from Replica 2. The replicas can't talk. Replica 2 must either:

  • Refuse or delay the read until it can confirm the latest value → consistent, not available (CP), or
  • Return 100, possibly stale → available, not consistent (AP).

That's the whole theorem: during a partition, you can't have both linearizable consistency and full availability. When the network is healthy, you can have both.

Why "CA" isn't really an option

A single-node database is "CA" only because it's not distributed. Once data is replicated across machines, networks will partition: switch failures, misconfigurations, cloud zone issues, garbage-collection pauses that look like partitions. So distributed systems choose how to behave when that happens.

PACELC: the everyday trade-off

CAP only describes partition behavior. PACELC extends it:

If there's a Partition, choose Availability or Consistency; Else (normal operation), choose Latency or Consistency.

Even with a healthy network, strong consistency requires coordination: waiting for replicas to acknowledge writes, or reading from a leader. That adds latency, especially across regions (latency numbers every engineer should know). Many systems relax consistency not for partitions, but to be fast every day.

The consistency spectrum

Model Guarantee Example use
Linearizable (strong) Reads see the latest write, globally ordered Balances, inventory reservations, locks, leader election
Sequential All nodes see operations in the same order Replicated state machines
Causal Causally related operations are seen in order Comments appear after the post they reply to
Read-your-writes A user always sees their own updates Profile edits, settings
Monotonic reads You never see data go "back in time" Feeds, dashboards
Eventual Replicas converge if writes stop Like counts, view counts, search indexes

Many products need only read-your-writes and monotonic reads for a good user experience, which is much cheaper than global strong consistency.

Quorums: tunable consistency

Leaderless replicated stores (in the style of Dynamo and Cassandra) use quorums. With N replicas, writes wait for W acknowledgments and reads query R replicas:

textIf R + W > N  → reads overlap with the latest write (stronger consistency)
N=3, W=2, R=2 → tolerates one node failure with overlapping quorums
N=3, W=1, R=1 → fastest, most available, eventually consistent

Quorum overlap improves consistency but doesn't by itself guarantee linearizability in every failure scenario. Details like sloppy quorums and concurrent writes matter.

Real systems, roughly categorized

These are tendencies with default configurations; most systems are tunable:

  • Single-leader relational databases (with synchronous replication or reads from the leader): prioritize consistency; during failover, writes may be briefly unavailable.
  • Asynchronous read replicas: reads from replicas can be stale (replication lag). That's an AP-style trade-off on the read path (database scaling: replication and sharding).
  • Consensus-based stores (etcd, ZooKeeper, distributed SQL built on Raft/Paxos): CP. They need a majority to make progress.
  • Dynamo-style stores: AP-leaning by default, tunable per request.
  • Caches and CDNs: favor availability and latency; staleness is bounded by TTLs (caching strategies).

Applying it: choose per operation

Ask for each operation: what's the cost of a stale read, and what's the cost of an error?

Operation Stale read cost Unavailability cost Choose
Deduct account balance Double spending User retries later Consistency
Reserve last concert ticket Overselling Brief error Consistency
Show like count Negligible Annoying Availability
Load social feed Minor Bad UX Availability + read-your-writes
Update search index Minor delay Search degraded Eventual consistency

Patterns that help:

  • Route reads-after-writes to the primary (or use session consistency) for the user who just wrote.
  • Use conditional writes / optimistic concurrency (version numbers) to prevent lost updates.
  • Compensate instead of coordinating: accept an order and reconcile later (sagas) when strict coordination is too costly (event-driven architecture).

Common misconceptions

  • "NoSQL is AP, SQL is CP." Too simplistic. Behavior depends on configuration and deployment.
  • "CAP means you can only ever have two properties." Only during partitions, and even then it's about linearizability versus total availability, not all-or-nothing.
  • "Eventual consistency means inconsistent forever." Replicas converge; the questions are how quickly and what users see in the meantime.

FAQ

Is the CAP theorem still relevant?

Yes, as a foundation for reasoning about trade-offs in replicated systems. In practice, PACELC and specific consistency models are more useful for day-to-day design decisions.

What does eventual consistency mean for users?

Users may briefly see slightly outdated data, such as a like count lagging by a second or a new post appearing in search a bit later. Good design hides this with read-your-writes guarantees and optimistic UI updates.

Can a system be both highly available and strongly consistent?

When there's no partition, yes, at some latency cost. Consensus-based systems stay available as long as a majority of nodes can communicate, which covers many failure scenarios, but they sacrifice availability on the minority side of a partition.

How does CAP relate to ACID?

They use "consistency" differently. ACID consistency means transactions preserve database invariants. CAP consistency means all nodes agree on the latest value. A distributed database can offer ACID transactions and still face CAP trade-offs across replicas.