之前网上看到很多写分布式事务的文章,不过大多都是将分布式事务各种技术方案简单介绍一下。很多朋友看了还是不知道分布式事务到底怎么回事,在项目里到底如何使用。
所以这篇文章,就用大白话+手工绘图,并结合一个电商系统的案例实践,来给大家讲清楚到底什么是 TCC 分布式事务。
首先说一下,这里可能会牵扯到一些 Spring Cloud 的原理,如果有不太清楚的同学,可以参考之前的文章:[《拜托,面试请不要再问我Spring Cloud底层原理!》](https://www.cnblogs.com/jajian/p/9973555.html)。
业务场景介绍[\#](https://www.cnblogs.com/jajian/p/10014145.html#%E4%B8%9A%E5%8A%A1%E5%9C%BA%E6%99%AF%E4%BB%8B%E7%BB%8D)
=================================================================================================================
咱们先来看看业务场景,假设你现在有一个电商系统,里面有一个支付订单的场景。
[![](96E42F6FC58A8C82FC3156F7B6CAD800.png)](https://img2018.cnblogs.com/blog/1162587/201811/1162587-20181124221344003-1003664855.png)
那对一个订单支付之后,我们需要做下面的步骤:
* 更改订单的状 态为“已支付”
* 扣减商品库存
* 给会员增加积分
* 创建销售出库单通知仓库发货
这是一系列比较真实的步骤,无论大家有没有做过电商系统,应该都能理解。
进一步思考[\#](https://www.cnblogs.com/jajian/p/10014145.html#%E8%BF%9B%E4%B8%80%E6%AD%A5%E6%80%9D%E8%80%83)
=======================================================================================================
好,业务场景有了,现在我们要更进一步,实现一个 TCC 分布式事务的效果。
什么意思呢?也就是说,[1] 订单服务-修改订单状态,[2] 库存服务-扣减库存,[3] 积分服务-增加积分,[4] 仓储服务-创建销售出库单。
上述这几个步骤,要么一起成功,要么一起失败,必须是一个整体性的事务。
举个例子,现在订单的状态都修改为“已支付”了,结果库存服务扣减库存失败。那个商品的库存原来是 100 件,现在卖掉了 2 件,本来应该是 98 件了。
结果呢?由于库存服务操作数据库异常,导致库存数量还是 100。这不是在坑人么,当然不能允许这种情况发生了!
但是如果你不用 TCC 分布式事务方案的话,就用个 Spring Cloud 开发这么一个微服务系统,很有可能会干出这种事儿来。
我们来看看下面的这个图,直观的表达了上述的过程:
[![](62A4E28B2C3CF36BCD6595A6E577F8BA.png)](https://img2018.cnblogs.com/blog/1162587/201811/1162587-20181124221516538-2117168183.png)
所以说,我们有必要使用 TCC 分布式事务机制来保证各个服务形成一个整体性的事务。
上面那几个步骤,要么全部成功,如果任何一个服务的操作失败了,就全部一起回滚,撤销已经完成的操作。
比如说库存服务要是扣减库存失败了,那么订单服务就得撤销那个修改订单状态的操作,然后得停止执行增加积分和通知出库两个操作。
说了那么多,老规矩,给大家上一张图,大伙儿顺着图来直观的感受一下:
[![](6D178E52B1698083F310018B0C09366D.png)](https://img2018.cnblogs.com/blog/1162587/201811/1162587-20181124221639782-279567864.png)
落地实现 TCC 分布式事务[\#](https://www.cnblogs.com/jajian/p/10014145.html#%E8%90%BD%E5%9C%B0%E5%AE%9E%E7%8E%B0-tcc-%E5%88%86%E5%B8%83%E5%BC%8F%E4%BA%8B%E5%8A%A1)
=========================================================================================================================================================
那么现在到底要如何来实现一个 TCC 分布式事务,使得各个服务,要么一起成功?要么一起失败呢?
大家稍安勿躁,我们这就来一步一步的分析一下。咱们就以一个 Spring Cloud 开发系统作为背景来解释。
TCC 实现阶段一:Try[\#](https://www.cnblogs.com/jajian/p/10014145.html#tcc-%E5%AE%9E%E7%8E%B0%E9%98%B6%E6%AE%B5%E4%B8%80%EF%BC%9Atry)
-------------------------------------------------------------------------------------------------------------------------------
首先,订单服务那儿,它的代码大致来说应该是这样子的: