TransactionSynchronizationManager事务同步器的使用

目录

TransactionSynchronizationManager

TransactionSynchronizationManager#registerSynchronization

TransactionSynchronization

TransactionSynchronizationAdapter

使用示例 


TransactionSynchronizationManager

有些业务场景涉及到一些操作需要绑定到事务上,比如在事务提交前或事务提交后做一些关联性的操作,这种场景可以使用到org.springframework.transaction.support包路径下的的TransactionSynchronizationManager所支持的同步器实现功能。

实现方式是 在事务方法中调用TransactionSynchronizationManager的registerSynchronization方法注入一个TransactionSynchronization接口实例,通常是使用TransactionSynchronizationAdapter适配器类,然后重写其beforeCommit()或者afterCommit()方法,实现在事务提交前或后执行对应的逻辑。

TransactionSynchronizationManager#registerSynchronization

registerSynchronization()方法入参是一个TransactionSynchronization接口实例,该方法会先判断synchronizations中是否有数据,因为Spring在开启数据库事务时会向其中写入一个实例。

所以这个方法调用必须在事务中执行,否则抛出Transaction synchronization is not active异常

校验通过后就将入参synchronization添加到synchronizations 中。但是注入的synchronization接口实例(TransactionSynchronizationAdapter)中的方法不会立刻执行,而是等到事务执行到一定阶段时才会被调用。

TransactionSynchronization

TransactionSynchronization接口是可以注册到事务处理过程中用于在事务不同状态节点实现同步回调的接口。当事务处理的某些规定时点发生时,会调用TransactionSynchronization上的一些方法来执行相应的回调逻辑,如在事务完成后清理相应的系统资源等操作。

但是TransactionSynchronization接口中没有afterRollback()。所以如果需要在事务回滚后做某些处理,需要在afterCompletion(int status)方法中判断入参的值,然后再做处理。

TransactionSynchronizationAdapter

TransactionSynchronizationAdapter是上面说的TransactionSynchronization接口的一个实例,并为每一个接口方法提供了一个空的实现。其实这种思路跟抽象类有点类似,有了这个空实现的适配器,我们就可以有选择的重写需要处理的回调方法,而不用在业务类中实现接口所有的方法。

使用示例 

首先测试一下TransactionSynchronization接口回调方法的执行时机

 TransactionSynchronizationManager.registerSynchronization(new TransactionSynchronizationAdapter() {
          @Override
          public void afterCommit() {
              log.error("================afterCommit============");
          }
          @Override
          public void beforeCommit(boolean readOnly) {
              log.error("================beforeCommit============");
          }
          @Override
          public void flush() {
              log.error("================flush============");
          }
          @Override
          public void beforeCompletion() {
              log.error("================beforeCompletion============");
          }
          @Override
          public void afterCompletion(int status) {
              if(TransactionSynchronization.STATUS_COMMITTED == status){
                log.error("=========afterCompletion======事务提交==============");
              }else if(TransactionSynchronization.STATUS_ROLLED_BACK == status){
                  log.error("========afterCompletion=========事务回滚============");
              }
          }
      });

事务正常提交时执行结果如下,afterCommit方法会被执行

BusinessServiceImpl.java:150) - ================beforeCommit============
BusinessServiceImpl.java:158) - ================beforeCompletion============
BusinessServiceImpl.java:146) - ================afterCommit============
BusinessServiceImpl.java:163) - =========afterCompletion======事务提交==============

当事务发生回滚时结果如下,afterCommit方法不会被执行

BusinessServiceImpl.java:158) - ================beforeCompletion============
BusinessServiceImpl.java:165) - ========afterCompletion=========事务回滚============

下面的代码,方法逻辑是带有事务的更新操作,使用TransactionSynchronizationManager注册一个TransactionSynchronization实例,重写afterCommit方法。可以实现在事务提交后执行afterCommit中发送MQ消息的操作。

@Transactional(rollbackFor = Exception.class)
    public void changeStock(Stock stock) {
       //事务操作
       stockMapper.updateByid(stock);
        TransactionSynchronizationManager.registerSynchronization(new TransactionSynchronizationAdapter() {
            @Override
            public void afterCommit() {
                 producer.sendMessageAync(NOTIFY, vo.getShopMdCode());
            }
        });
    }
  • 10
    点赞
  • 25
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

WannaRunning

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值