经常在网络上看见有人介绍TCC时,都提一句,”TCC是两阶段提交的一种”。其理由是TCC将业务逻辑分成try、confirm/cancel在两个不同的阶段中执行。其实这个说法,是不正确的。可能是因为既不太了解两阶段提交机制、也不太了解TCC机制的缘故,于是将两阶段提交机制的prepare、commit两个事务提交阶段和TCC机制的try、confirm/cancel两个业务执行阶段互相混淆,才有了这种说法。
两阶段提交(Two Phase Commit,下文简称2PC),简单的说,是将事务的提交操作分成了prepare、commit两个阶段。其事务处理方式为:
1、 在全局事务决定提交时,a)逐个向RM发送prepare请求;b)若所有RM都返回OK,则逐个发送commit请求最终提交事务;否则,逐个发送rollback请求来回滚事务;
2、 在全局事务决定回滚时,直接逐个发送rollback请求即可,不必分阶段。
* 需要注意的是:2PC机制需要RM提供底层支持(一般是兼容XA),而TCC机制则不需要。
TCC(Try-Confirm-Cancel),则是将业务逻辑分成try、confirm/cancel两个阶段执行,具体介绍见TCC事务机制简介。其事务处理方式为:
1、 在全局事务决定提交时,调用与try业务逻辑相对应的confirm业务逻辑;
2、 在全局事务决定回滚时,调用与try业务逻辑相对应的cancel业务逻辑。
可见,TCC在事务处理方式上,是很简单的:要么调用confirm业务逻辑,要么调用cancel逻辑。这里为什么没有提到try业务逻辑呢?因为try逻辑与全局事务处理无关。
当讨论2PC时,我们只专注于事务处理阶段,因而只讨论prepare和commit,所以,可能很多人都忘了,使用2PC事务管理机制时也是有业务逻辑阶段的。正是因为业务逻辑的执行,发起了全局事务,这才有其后的事务处理阶段。实际上,使用2PC机制时————以提交为例————一个完整的事务生命周期是:begin -> 业务逻辑 -> prepare -> commit。
再看TCC,也不外乎如此。我们要发起全局事务,同样也必须通过执行一段业务逻辑来实现。该业务逻辑一来通过执行触发TCC全局事务的创建;二来也需要执行部分数据写操作;此外,还要通过执行来向TCC全局事务注册自己,以便后续TCC全局事务commit/rollback时回调其相应的confirm/cancel业务逻辑。所以,使用TCC机制时————以提交为例————一个完整的事务生命周期是:begin -> 业务逻辑(try业务) -> commit(comfirm业务)。
综上,我们可以从执行的阶段上将二者一一对应起来:
1、 2PC机制的业务阶段 等价于 TCC机制的try业务阶段;
2、 2PC机制的提交阶段(prepare & commit) 等价于 TCC机制的提交阶段(confirm);
3、 2PC机制的回滚阶段(rollback) 等价于 TCC机制的回滚阶段(cancel)。