第 6 篇 · 共100篇|用代码丈量成长 —— 坚持写下去,就是最好的成长。
一位朋友各自在不同城市点了同一家连锁奶茶。我们有一张只能使用一次的共享优惠券,于是我给他发消息:“我现在要点单,我先用可以吧?”
但就在我们互发消息时,网络突然卡住了——消息谁也没收到。我们各自以为优惠券还没被使用,于是很默契地同时按下了“支付”按钮。
当网络恢复后,商家的系统陷入了尴尬:两个节点都认为“优惠券还未使用”,各自走完了流程,最后让同一张券被用了两次。
在我们个人的视角下,一切都看起来合理:下单顺利、支付成功、流程完整,也就是系统对我们来说是“可用”的。但如果从整个系统的视角看,状态已经出现了明显的不一致。
如果你把这个场景换成数据库写入,这其实就是分布式系统中最典型的冲突:当节点之间因为网络问题失去联系时,系统到底应该保证“大家看到的数据一致”,还是应该保证“服务继续可用”?
CAP 定理,就是为了解释这种矛盾的根源。
理解 C / A / P 的真实含义
一致性(Consistency)
一致性不是强调数据永远正确,而是强调所有节点在同一时间看到的数据必须相同。
当一个写操作提交成功后,无论用户访问哪个节点,系统必须给出同样的结果。
在没有网络故障时,这个目标很好达成。但一旦节点之间无法通信,就像奶茶故事中双方“听不到彼此状态”一样,系统需要决定下一步到底该不该继续处理请求。
可用性(Availability)
可用性强调的是另一件事:系统必须给出响应,不能沉默,也不能无限等待。哪怕处在异常场景中,系统也必须对用户“活着”。奶茶故事中,我们两个人都成功下单,这代表系统做出了“保证可用性”的选择——它没有因为不确定就拒绝请求。
分区容错性(Partition Tolerance)
现实世界中,网络不可能永远稳定:节点会宕机、链路会丢包,跨机房延迟也随时可能波动。分区容错性指的是系统在网络发生分裂时仍能继续运转,而不是直接瘫痪。 也正因为网络问题是必然而非偶然,所以 P 并不是一个可选条件,而是分布式系统必须面对的前提。
CAP 的矛盾真正出现的地方
正常情况下,C、A、P 是可以同时具备的,多数系统在大部分时间里也确实如此运行。但 CAP 讨论的不是最坏情况下的选择策略:
当节点之间失去联系时,系统无法同时保证“数据一致”并且“对外可用”。如果继续处理请求,可能会产生不一致;如果为了保持一致而停止处理请求,用户会认为系统不可用。这不是技术水平问题,而是物理条件决定的冲突。
不同业务场景下的不同选择
偏向一致性的系统(CP)
适用于“数据错误比停机更糟糕”的场景,比如:
- 金融转账
- 订单状态
- 配置元数据写入
这类系统往往宁可阻塞或拒绝请求,也不能让不同节点做出相反结果,这就是我们说强一致。
偏向可用性的系统(AP)
适用于“服务不可用带来的后果比不一致更严重”的场景,比如:
- 聊天未读数
- 点赞
- 购物车
- 分布式缓存(如 Redis)
它们愿意接受短暂不一致,只要系统持续对外可用。
为什么很少讨论“CA”?
只要系统是分布式,网络分区就一定会发生,所以 P 无法回避。因此现实中真正的取舍永远只有两种:CP 或 AP。
CAP 如何体现在真实系统里?
理解理论之后,更关键的问题是:真实系统是怎么选的,我们看看两个常用的中间件?
Zookeeper:典型的 CP
Zookeeper 常用于:
- 主从选举
- 分布式锁
- 分布式协调
这些操作要求全局状态必须保持一致,否则风险极高。当网络分区发生时,Zookeeper 会阻塞或拒绝写请求,通过“多数派写入(Quorum)”保证一致性。这意味着它宁可“停”,也不能“乱”。
Nacos:默认 AP(也支持 CP)
Nacos 的核心职责是服务发现。对于服务调用来说,请求失败通常比数据延迟更糟糕。所以它默认选择 AP —— 即便存在分区,也优先保证服务可用。
不过 Nacos 也提供 CP 模式,在需要一致性的场景(如配置管理)中可以按需切换。它比 Zookeeper更灵活,因为它面对的业务形态更多样。
| 系统 | CAP 取舍 | 适用场景 | 取舍逻辑 |
|---|---|---|---|
| Zookeeper | CP | 强一致协调 | “数据不能错” |
| Nacos | 默认 AP、可选 CP | 服务发现/配置 | “系统不能停” |
ZK 像“裁判”,必须保证秩序;
Nacos 像“服务员”,必须优先保证服务继续。
CAP 的真正价值
聊到这里你会发现,CAP 并不是故意给工程师设置障碍,它更像是在提醒我们一件朴素但常被忽略的事情:系统也跟人一样,永远有取舍。
你没办法既每天健身、又每天熬夜、还能保持皮肤状态完美;分布式系统也没办法在网络失败时既“绝对一致”,又“永远可用”。那怎么办?只能根据自己最在意的事情选一个优先级架构设计的成熟,不是追求“全都要”,而是能够坦然面对“取舍”,并清楚自己在为谁做选择、承担什么代价、换来什么收益。
你的阅读与同行,让路途更有意义
愿我们一路向前,成为更好的自己