本地消息表其实也是借助消息来实现分布式事务的。
这个方案的主要思想是将分布式事务拆分为本地事务和消息事务两个部分,本地事务在本地数据库中进行提交或回滚,而消息事务则将消息写入消息中间件中,以实现消息的可靠投递和顺序性。
一般来说的做法是,在发送消息之前,先创建一条本地消息,并且保证写本地业务数据的操作,和,写本地消息记录的操作在同一个事务中。这样就能确保只要业务操作成功,本地消息一定可以写成功。
然后再基于本地消息,调用MQ发送远程消息。
消息发出去之后,等待消费者消费,在消费者端,接收到消息之后,做业务处理,处理成功后再修改本地消息表的状态。
这个过程中,可能有几个步骤都可能发生失败,那么如果失败了怎么办呢?
1、2如果失败,因为在同一个事务中,所以事务会回滚,3及以后的步骤都不会执行。数据是一致的。
3如果失败,那么就需要有一个定时任务,不断的扫描本地消息数据,对于未成功的消息进行重新投递。
4、5如果失败,则依靠消息的重投机制,不断地重试。
6、7如果失败,那么就相当于两个分布式系统中的业务数据已经一致了,但是本地消息表的状态还是错的。这种情况也可以借助定时任务继续重投消息,让下游幂等消费再重新更改消息状态,或者本系统也可以通过定时任务去查询下游系统的状态,如果已经成功了,则直接推进消息状态即可。
优点:
缺点: