spring 事务传播问题

工作中碰到的一个小问题:

背景:

 

方法1、2 均在spring aop事务管理下

 

现执行结果: 方法2抛异常,方法2回滚,方法1也回滚了

期望结果:方法2抛异常,方法2回滚,方法1不回滚

 

 思考

spring事务什么时候会自动回滚?

Spring事务回滚机制是这样的:当所拦截的方法(@Transactional或者通过xml配置)有指定异常抛出,事务才会自动进行回滚! 

 异常抛出?

 即方法中出现的指定异常,只有在被事务管理器捕捉到以后,事务才会据此进行事务回滚

哪些异常会回滚?

默认Error与RuntimeException,不包括checkedException 如IOException

查看源码可知默认情况为这两种异常:

 有rollBackFor的情况,则根据设置的异常来定

 

由上述知识铺垫分析下问题,发现方法2抛出异常被catch住之后,正常情况下,不应该会导致方法1被回滚

 

再思考:

配置:

 

发现事务传播属性配置的

7种Propagation :

  • PROPAGATION_REQUIRED:默认事务类型,如果没有,就新建一个事务;如果有,就加入当前事务。适合绝大多数情况。
  • PROPAGATION_REQUIRES_NEW:如果没有,就新建一个事务;如果有,就将当前事务挂起。
  • PROPAGATION_NESTED:如果没有,就新建一个事务;如果有,就在当前事务中嵌套其他事务。
  • PROPAGATION_SUPPORTS:如果没有,就以非事务方式执行;如果有,就使用当前事务。
  • PROPAGATION_NOT_SUPPORTED:如果没有,就以非事务方式执行;如果有,就将当前事务挂起。即无论如何不支持事务。
  • PROPAGATION_NEVER:如果没有,就以非事务方式执行;如果有,就抛出异常。
  • PROPAGATION_MANDATORY:如果没有,就抛出异常;如果有,就使用当前事务。

由于add*方法是默认的required,所以方法2的事务应该是:

方法2的父方法有事务,故加入其事务。

当其抛出异常时,符合spring事务回滚的条件,故回滚该事务

 

结论:

如果想要达到目的,只需要将方法2的事务传播属性改为PROPAGATION_NESTED即可

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值