CAP定理
- C:一致性
- A:可用性
- P:容错性
在分布式系统里面,任何数据库设计,一个web应用最多只能支持上面两个属性。
2PC XA 事务
是一个两阶段的提交协议
- 第一阶段,事务协调器要求每个涉及到事务的数据库预提交,并且反映是否可以提交
- 第二阶段,事务协调器要求每个数据库提交数据
如果有任何一个数据库否决此次提交,那么所有数据库都会被要求回滚他们在此事务中的那部分信息。
存在的问题
- 同步阻塞,所有事务参与者在等待其他参与者响应的时候都是处于同步阻塞的状态,无法进行其他操作;
- 单点问题,协调器在2PC中起到非常大的作用,但是如果协调器发生故障会产生很大的影响,特别是在第二阶段的时候,所有参与者会一直在等待状态,无法完成其他操作
- 数据不一致,在第二阶段,如果协调器发送了部分提交消息,然后网络异常,那么只有部分事务参与者提交事务了,就导致了数据不一致
- 太过保守,一个节点失败,所有事务全部回归,容错机制不够
TCC补偿事务
TCC就是采用的补偿机制,核心就是针对每个操作,都注册一个与其对应的确认和补偿操作,分为三个阶段
- try阶段,主要是对业务系统做检测以及资源预留
- confirm阶段,主要是对业务系统做确认提交,try阶段执行成功就开始执行confirm阶段,默认confirm阶段是不会出错的,只要try成功,confirm一定成功
- cancel阶段,主要是在业务执行错误,需要回滚的状态下,执行业务取消,预留资源释放
转账举例
- 首先在try阶段,调用接口把转账人和被转账人的钱冻结起来
- 在confirm阶段,调用远程转账接口,转账成功并进行解冻
- cancel阶段,转账执行失败,还原转账数据,调用远程冻结接口将钱解冻。
优点在于跟2PC比起来,实现以及流程都相对简单一些,但是数据的一致性也比2PC要差一些
缺点在于2和3阶段都有可能失败,TCC本质上属于应用层的一种补偿方式,需要在代码里写很多补偿的代码,在一些场景里面。TCC不太好定义和处理
本地消息表 异步确保
本地消息表与业务数据表处于同一个数据库中,这样就能利用本地事务来保证这两个表的数据一致,然后再使用消息队列保证最终一致。分为三个阶段
- 在分布式事务操作的一方完成写数据之后,向本地消息表发送一个消息,本地事务可以保证这个消息一定能写入本地消息表中
- 之后将本地消息表中的消息转发到消息队列,如果转发成功就将消息从本地删除,否则继续转发
- 在分布式事务操作的另一方从消息队列中读取一个消息,并执行消息中的操作
优点在于是一种非常经典的实现,避免了分布式事务,实现了最终一致性
缺点在于消息表会耦合到业务系统中,如果没有好的解决方案,会有很多杂活需要处理