Spring的@Transactional注解的失效场景?

背景
  1. @Transactional放在类上面和放在方法上面的优先级。注解放在方法上面会覆盖放在类上面。

  2. @Transactional注解的属性的含义:事务传播?事务隔离级别?是否只读?

  3. 失效的场景有哪些?

    a) 内部方法调用

    b) try…catch

    c) 默认是RuntimeException级别的,那么Exception级别的异常框架就感知不到

过程
  • 内部方法调用

    场景描述:一个方法没有事务,但是调用了一个有事务的方法,此事务失效。

    测试代码

    1. 设计两个方法。methodA(), methodB()
    2. methodA是没有事务注解的。
    3. methodB是有事务注解的。
    4. 测试methodA去调用methodB。
    5. 此时methodB方法中,先执行更新数据库,然后出现异常,未捕获。

    测试结果

    事务失效。数据被更新到数据库中。

    虽然代码报错了,但是数据库的更新操作,依然发生了。

    本意是要保证事务,当代码抛出异常了,那么事务就回滚了。但是,由于方法间的调用关系,导致了事务失效。

  • try…catch

    方法中出现了异常,且未捕获。Spring的默认异常感知级别是RuntimeException,因此如果是Exception级别的异常,Spring是无法感知的。此时如果数据已经更新到数据库了,发生了Exception级别的异常,则不会回滚。事务失效

    如果出现了异常,但是捕获了。数据库中的数据最终会被更新。事务失效

  • 默认是RuntimeException级别的,那么Exception级别的异常框架就感知不到

  1. 在测试try catch的时候,如果捕获了异常,则数据最终被更新到数据库中。事务失效,因为捕获了异常,并处理了异常。
  2. 如果没有捕获异常,则框架感知到异常发生的级别是RuntimeException,如果代码抛出了Exception级别的异常,则事务依然失效。
小结
  1. 遇到异常检测不回滚

    原因:默认RuntimeException级别才回滚。如果是Exception级别的异常需要手动添加@Transactional(rollbackFor=Exeception.class)。

  2. 主动捕获异常导致框架无法捕获,从而导致事务失效

  3. 一个合理实践是这样的

    a, 业务service层,直接抛出异常,让Controller层捕获异常并处理。

    b,这样实践后,当service层发生了异常情况。而业务层的异常被框架感知到了,因此事务是有效的。这里的框架就是Spring的事务。

    c, 注意:非常重要。一定要注意级别:rollbackFor=Exeception.class

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值