跳转到内容

一致性问题域与 CAP/BASE

用途:判断“这个场景到底需不需要分布式事务”时先读这一页

单个数据库事务能解决同一资源内的一致性(ACID)。一旦业务操作跨越多个资源——多个库、消息中间件、外部系统——就不存在一个统一提交点,事务保证随之失效。此时可选的性质只有三类:强一致(阻塞换取一致)、最终一致(允许短暂不一致)、放弃(接受不一致并靠对账发现)。

CAP 指分布式存储在网络分区(P)必然发生的前提下,只能在一致性(C)与可用性(A)之间取舍。

误读点:

  1. CAP 描述的是分区发生时的行为,不是常态。没分区时既可以提供强一致也可以高可用。
  2. 这里的 C 指线性一致,与 ACID 的 C(业务约束不被破坏)不是同一个概念。
  3. CAP 是存储层结论,不能直接推导“业务系统该怎么设计”。

实际工程更常用 PACELC 的补充视角:有分区时牺牲 C 或 A,没分区时也要在延迟(L)与一致性(C)之间取舍——这才是跨机房、跨库读写延迟问题的真实来源。

Basically Available(基本可用)、Soft state(软状态,允许中间态)、Eventually consistent(最终一致)。落地形式就是:主流程本地事务提交,次要影响异步完成,配合重试、幂等与对账收敛。

“基本可用”的具体形态:功能降级、响应时间变长、部分用户被排队——不是“随便挂”。

问题 若是 建议
是否跨多个独立数据源? 否 单库事务即可,别引入分布式事务
不一致是否会造成资金/合规损失? 是 强一致方案(同库、XA/TCC)或改为同一聚合
能否接受秒级到分钟级不一致? 是 本地消息表/事务消息 + 幂等消费 + 对账
参与方是否包含不可控外部系统? 是 最大努力通知 + 主动查询 + 对账
流程是否长、跨天、含人工环节? 是 Saga(补偿型),避免长时间持锁

最有价值的一步往往是消除事务需求本身:把强一致的部分收进同一个聚合与同一个库,剩下的用最终一致处理。跨库强一致方案的复杂度通常高于“重新划分边界”的成本。

任何异步一致性方案都必须同时具备:

  1. 幂等:重复投递不产生重复效果(业务幂等键,而非消息 ID)。
  2. 重试与死信:失败可重放,且有人负责处理堆积。
  3. 对账:定期比对两侧状态,发现并修复偏差;对账是“最终一致”唯一的证据来源。
误区 修正
用 CAP 论证“我们选 AP 所以可以不一致” 明确业务能容忍的不一致窗口与后果,再选方案
认为消息中间件保证恰好一次 端到端只能靠生产可靠 + 消费幂等逼近
只上“事务消息”就宣布一致 没有对账,就没有证据
把补偿逻辑当可选项 Saga/TCC 的失败率高于正向流程,补偿必须与正向同等严谨
  • Eric Brewer 关于 CAP 的原始论述与 later clarifications
  • Martin Kleppmann《数据密集型应用系统设计》第 8、9 章(一致性与共识)
  • Chris Richardson《微服务架构设计模式》第 4、8、9 章(Saga、事件驱动与一致性)
  • Pat Helland《Life beyond Distributed Transactions》