zoukankan      html  css  js  c++  java
  • spring声明式事务回滚

    spring 声明式事务

    spring声明式事务管理是通过aop实现的,使用时不用修改原有业务代码,只需要通过简单配置追加事务控制功能,同时也最符合非侵入式的理念,因此大多数用户都会选择声明式事务。

    默认Spring事务只在发生未被捕获的RuntimeException时才回滚,而发生检查异常是不会回滚的,

    checked Exception回滚

    1、注解方式

    @Transactional(rollbackFor=ClassCastException.class)

    2、xml配置方式

    <tx:method  name="update*" propagation="REQUIRED"  rollback-for="java.lang.ClassCastException/>

    捕获的RuntimeException回滚

    @Transactional
    public boolean save() {
       try {
         // 操作A
          // 操作B
       } catch (Exception e) {
          log.error("事务失败", e);
          return false;
       }
       return Boolean.TRUE;

    Spring AOP  异常捕获原理:被拦截的方法需显式抛出异常,并不能经任何处理,这样AOP 代理才能捕获到方法的异常,才能进行回滚,默认情况下aop只捕获RuntimeException的异常,但可以通过配置来捕获特定的异常并回滚  
    换句话说在service的方法中不使用try catch 或者在catch中最后加上throw new RuntimeExcetpion(),这样程序异常时才能被AOP捕获进而回滚

    解决方案: 

     方案1.例如service层处理事务,那么service中的方法中不做异常捕获,或者在catch语句中最后增加throw new RuntimeException()语句,以便让aop捕获异常再去回滚,并且在service上层(webservice客户端,view层action)要继续捕获这个异常并处理。

    @Transactional
    public boolean save() {
       try {
         // 操作A
          // 操作B
       } catch (Exception e) {
          throw new RuntimeException(message); 
          return fasle;
       }
       return Boolean.TRUE;

    但是从阿里巴巴的手册上有这么一条,避免直接抛出RuntimeException,应使用有业务含义的自定义异常。并且需要继承 RuntimeException。

    throw new UserNotFoundException("user not found"); // 用户不存在

      方案2.TransactionAspectSupport.currentTransactionStatus().setRollbackOnly(),手动回滚,这样上层就无需去处理异常(推荐)

  • 相关阅读:
    冲突域和广播域的区分
    internet 的一词多义
    大神洗礼第四讲——函数相关及编程技巧
    旋转字符串算法由浅入深
    一个交换程序的通用版本
    想起一些事情,都很遥远
    [转载]创业感想
    [转载]javascript小技巧
    [转载]在Asp.Net 2.0中应用DataFormatString
    [转载]C#的String.Format格式化举例
  • 原文地址:https://www.cnblogs.com/magic101/p/10684089.html
Copyright © 2011-2022 走看看