`
shaohan126448
  • 浏览: 116645 次
  • 来自: 北京
社区版块
存档分类
最新评论

Spring异常抛出触发事务回滚策略

 
阅读更多

Spring、EJB的声明式事务默认情况下都是在抛出unchecked exception后才会触发事务的回滚 

测试用业务逻辑方法: 

 


整个包裹起来,则这个业务方法也就等于脱离了spring事务的管理,因为没有任何异常会从业务方法中抛出!全被捕获并吞掉,导致spring异常抛出触发事务回滚策略失效。 
不过,如果在catch代码块中采用页面硬编码的方式使用spring api对事务做显式的回滚,这样写也未尝不可。 

Java代码  收藏代码
  1. /** 
  2.  * 如果在spring事务配置中不为切入点(如这里的切入点可以定义成test*)配置事务在什么情况下回滚(格式:-引起回滚的异常类型) 
  3.  * 则spring默认只会在service方法抛出unchecked exception才会触发回滚 
  4.  */  
  5. public class TestServiceImpl extends Service implements TestService {  
  6.   
  7.     /** 
  8.      * 测试spring异常触发事务回滚的service方法 
  9.      */  
  10.     public void testAddPerson(String name) throws Exception {  
  11.         TestPerson p = new TestPerson();  
  12.         p.setName(name);  
  13.         this.getHibernateGenericController().save(p);  
  14.           
  15.         /* 
  16.          * 制造RuntimeException 
  17.          * 在spring默认的异常回滚策略下,该异常的抛出会触发事务的回滚,数据不会被插入 
  18.          */  
  19.         throw new RuntimeException("抛出个运行时异常");  
  20.           
  21.         /** 
  22.          * 同样是unchecked exception,spring默认的异常回滚策略下Error的抛出也会触发事务的回滚,数据不会被插入 
  23.          */  
  24. //      throw new Error();  
  25.           
  26.         /** 
  27.          * 即使是在spring默认的异常触发事务回滚策略(unchecked exception触发回滚)下, 
  28.          * 如果使用try-catch捕获抛出的unchecked异常后没有在catch块中采用页面硬编码的方式使用spring api对事务做显式的回滚,则事务不会回滚,数据被插入 
  29.          * “将异常捕获,并且在catch块中不对事务做显式提交=生吞掉异常” 
  30.          */  
  31. //      try {  
  32. //          throw new RuntimeException("这个抛出的运行时异常会被try-catch捕获");  
  33. //      } catch(Exception e) {  
  34. //          System.out.println("捕获到异常: " + e.getMessage());  
  35. //      }  
  36.           
  37.         /** 
  38.          * 因为Exception类是个checked exception,所以这里抛出的异常不会触发事务的回滚,数据被插入 
  39.          */  
  40. //      throw new Exception("a Exception instance");  
  41.           
  42.         /** 
  43.          * 该BaseException继承自Exception,也为checked exception,抛出它后: 
  44.          * spring默认的回滚策略下,事务未回滚, 数据被插入; 
  45.          * 在TransactionProxyFactoryBean的transactionAttributes中配置 
  46.                     <prop key="test*"> 
  47.                         ... ...,-BaseException 
  48.                     </prop> 
  49.             后,事务回滚,数据未被插入 
  50.          */  
  51. //      throw new BaseException("一个BaseException");  
  52.     }  
  53.   
  54. }  


关于TransactionProxyFactoryBean的transactionAttributes中字符串的值(定义自TransactionAttributeEditor): 
is a transaction attribute descriptors that parsed via TransactionAttributeEditor 
见本博客:http://wuaner.iteye.com/admin/blogs/567792 

单元测试代码: 

Java代码  收藏代码
  1. public class TestSpringDefaultRollback extends TestCase {  
  2.   
  3.     private static ApplicationContext context = new ClassPathXmlApplicationContext("resource/xxx/applicationContext.xml");  
  4.     public void testDefaultRollback() throws Exception{  
  5.         TestService testServiceImpl = (TestService)context.getBean("testService");  
  6.         testServiceImpl.testAddPerson("张三");  
  7.     }  
  8. }  




将异常捕获,并且在catch块中不对事务做显式提交(或其他应该做的操作如关闭资源等)=生吞掉异常 

spring的事务边界是在调用业务方法之前开始的,业务方法执行完毕之后来执行commit or rollback(Spring默认取决于是否抛出runtime异常). 
如果抛出runtime exception 并在你的业务方法中没有catch到的话,事务会回滚。 
一般不需要在业务方法中catch异常,如果非要catch,在做完你想做的工作后(比如关闭文件等)一定要抛出runtime exception,否则spring会将你的操作commit,这样就会产生脏数据.所以你的catch代码是画蛇添足。 
由此可以推知,在spring中如果某个业务方法被一个 

Java代码  收藏代码
  1. try {  
  2.     //bisiness logic code  
  3. catch(Exception e) {  
  4.     //handle the exception  
  5. }  
分享到:
评论

相关推荐

    spring 简单实例 事务回滚

    4. 异常处理:为了触发事务回滚,方法内通常会抛出未检查异常(继承自`RuntimeException`的异常)或显式指定需要回滚的检查异常。Spring默认只在遇到未检查异常时自动回滚事务,如果需要在特定检查异常下回滚,可以...

    Spring中@Transactional事务回滚(含实例

    如果方法执行过程中发生异常,代理对象会触发事务回滚。 五、事务回滚的局限性 需要注意的是,`@Transactional`注解只能对Spring管理的bean起作用,对于非Spring管理的对象(如静态方法或第三方库的代码),`@...

    子线程任务发生异常,主线程事务如何回滚

    其中,Callable 接口的 call 方法可以抛出异常,而 Runnable 接口的 run 方法不能抛出异常。因此,如果我们想捕获子线程的执行结果或异常,就应该使用 Callable 接口。 二、线程池的使用 在 Java 中,我们可以使用...

    Spring中的@Transactional事物回滚实例源码

    在这个例子中,`createUser`方法被标记为事务性的,如果在方法内部抛出未捕获的异常,Spring会自动回滚事务,确保数据一致性。 Spring事务管理的工作流程大致如下: 1. **AOP代理**:Spring使用AOP(面向切面编程)...

    spring事务异常回滚实例解析

    首先,Spring 默认只有在遇到未捕获的 `RuntimeException` 或其子类时才会触发事务回滚。这意味着,如果在业务代码中对异常进行了捕获并处理,而没有再抛出异常,那么事务将不会自动回滚。例如,在提供的代码实例中...

    Spring事务管理只对出现运行期异常进行回滚

    Spring的事务管理默认策略是,只有当方法抛出运行时异常时,事务才会被回滚。这是因为运行时异常被认为是不可预见的,程序不应该继续执行。而如果抛出的是检查异常,Spring默认假设这是业务逻辑的一部分,因此不会...

    Java Spring 事务回滚详解

    如果方法中抛出了未被捕获的异常,Spring会自动回滚事务;反之,如果方法正常结束,事务会被提交。 在Spring中,事务回滚规则基于异常类型。默认情况下,只有未检查异常(RuntimeException及其子类)会导致事务回滚...

    跟我学Spring3(9.3)Spring的事务之编程式事

    6. **事务的回滚规则**:编程式事务中,可以通过抛出特定异常或者调用TransactionManager的rollback方法来触发事务回滚。Spring对异常进行了分类,只有特定的异常类型会触发事务回滚。 7. **实战应用**:在实际项目...

    SpringBoot的事务使用和回滚功能讲解.docx

    因此,为了确保事务回滚,你需要在`catch`块中重新抛出异常,或者在`finally`块中显式调用手动回滚的方法。特别要注意,如果`try-catch`块包含在`finally`中且在`finally`中有返回操作,那么catch中的异常会被返回...

    spring 事务基于注解模式

    - NEVER:如果存在事务,则抛出异常;否则,非事务环境运行。 - NESTED:如果当前存在事务,则在嵌套事务内执行;若无,则按REQUIRED行为处理。 #### 2.3 事务隔离级别 事务隔离级别是指并发事务间如何共享数据。...

    spring事务总结.docx

    1. **未被捕获的异常**:如果事务中的代码抛出了未被捕获的异常,Spring将自动回滚事务。 2. **显式回滚**:开发者可以在事务代码中显式调用`TransactionStatus.setRollbackOnly()`方法来强制回滚事务。 3. **特定...

    spring几种事务配置详解【精】

    - 默认情况下,如果事务中的任何方法抛出了未检查异常(继承自`RuntimeException`的异常)或`Error`,事务会被回滚。 - 如果你希望特定的受检异常(非`RuntimeException`的异常)也触发回滚,可以在`@...

    SpringJDBC注解事务.zip

    - 默认情况下,只有运行时异常(继承自`RuntimeException`的异常)会导致事务回滚,非运行时异常(受检查的异常)不会导致回滚。 - 通过`rollbackFor`和`noRollbackFor`属性可以自定义哪些异常需要或不需要触发...

    Hibernate编程式事务与Spring Aop的声明式事务(spring与hibernate集成)

    4. **异常处理**: 声明式事务管理基于异常驱动,当方法抛出未检查异常(继承自`RuntimeException`)或`Error`时,事务会自动回滚;而检查异常(非`RuntimeException`)则不会触发回滚,除非在注解中指定了`rollback...

    Spring Boot的事务控制.docx

    // 手动抛出运行时异常以触发事务回滚 } return null; } @Override @Transactional(rollbackFor = Exception.class) public Long addBook(Book book) { try { Long result = bookRepository.addBook(book)...

    spring.net oracle 事务控制

    例如,可以定义一个全局的异常拦截器,当检测到特定类型的异常时,自动触发事务回滚,防止脏数据的产生。在Spring.NET中,我们可以利用AOP来实现这个功能,创建一个切面,该切面会在方法执行前后进行拦截,如果方法...

    spring JDBC事务管理

    例如,可以通过`JdbcTemplate`的`execute()`方法执行包含事务的SQL语句,并通过抛出异常来触发事务回滚。 **源码分析**:深入理解Spring JDBC事务管理的源码,可以帮助开发者更好地定制和优化事务处理。关键类如`...

    Spring.NET学习笔记16——事务管理Demo源码

    5. **回滚规则**:在声明式事务管理中,可以通过`&lt;tx:method&gt;`的`no-rollback-for`和`rollback-for`属性定义哪些异常应该触发事务回滚,哪些异常不应触发回滚。 通过Spring.NET的事务管理,我们可以编写出更健壮、...

    spring-transaction-demo.rar_DEMO_springboot_wash1vw

    虽然Controller层通常不直接处理事务,但可以通过抛出异常来触发事务回滚。 6. **异常处理**:在Spring Boot中,我们可以自定义`@ControllerAdvice`类来处理全局异常,这有助于控制事务回滚逻辑。例如,当出现运行...

    Spring Boot数据库事务控制.zip

    3. **事务回滚规则**:默认情况下,如果在@Transactional注解的方法中抛出未检查异常(继承自RuntimeException的异常)或者Error,Spring会自动回滚事务。对于受检查异常(非RuntimeException),需要显式地声明需要...

Global site tag (gtag.js) - Google Analytics