本篇主要讨论下面几点获取【下载地址】  :

一: Spring 事务的传递性介绍

二: 第三方调用含有事务的Service抛异常方法探讨

一: Spring 事务的传递性介绍

事务传播行为,所谓事务的传播行为是指,如果在开始当前事务之前,一个事务上下文已经存在,此时有若干选项可以指定一个事务性方法的执行行为。在TransactionDefinition定义中包括了如下几个表示传播行为的常量:

TransactionDefinition.PROPAGATION_REQUIRED:如果当前存在事务,则加入该事务;如果当前没有事务,则创建一个新的事务。

TransactionDefinition.PROPAGATION_REQUIRES_NEW:创建一个新的事务,如果当前存在事务,则把当前事务挂起。

TransactionDefinition.PROPAGATION_SUPPORTS:如果当前存在事务,则加入该事务;如果当前没有事务,则以非事务的方式继续运行。

TransactionDefinition.PROPAGATION_NOT_SUPPORTED:以非事务方式运行,如果当前存在事务,则把当前事务挂起。

TransactionDefinition.PROPAGATION_NEVER:以非事务方式运行,如果当前存在事务,则抛出异常。

TransactionDefinition.PROPAGATION_MANDATORY:如果当前存在事务,则加入该事务;如果当前没有事务,则抛出异常。

TransactionDefinition.PROPAGATION_NESTED:如果当前存在事务,则创建一个事务作为当前事务的嵌套事务来运行;如果当前没有事务,则该取值等价TransactionDefinition.PROPAGATION_REQUIRED。

这里需要指出的是,前面的六种事务传播行为是 Spring 从 EJB 中引入的,他们共享相同的概念。而 PROPAGATION_NESTED是 Spring 所特有的。以 PROPAGATION_NESTED 启动的事务内嵌于外部事务中(如果存在外部事务的话),此时,内嵌事务并不是一个独立的事务,它依赖于外部事务的存在,只有通过外部的事务提交,才能引起内部事务的提交,嵌套的子事务不能单独提交。如果熟悉 JDBC 中的保存点(SavePoint)的概念,那嵌套事务就很容易理解了,其实嵌套的子事务就是保存点的一个应用,一个事务中可以包括多个保存点,每一个嵌套子事务。另外,外部事务的回滚也会导致嵌套子事务的回滚。

二: 第三方调用含有事务的Service抛异常方法探讨

    假设术语如下:调用方Conumer,  调用Service的methodA, methodA调用Service的 methodB

a)methodA 传播属性为required, methodB传播属性为required, 代码如下

  1. public void methodA() {
  2. try {
  3. methodB();
  4. } catch(Exception e) {
  5. process();
  6. }
  7. otherOperation;
  8. }
    假设MethodB抛出异常,则Consumer调用MethodA会发生怎样的情形?

发现Consumer调用MethodA的时候出现了运行时异常,UnexpectedRollbackException: “Transaction rolled back because it has been marked as rollback-only”。这是为什么呢?

网上搜索了下,终于发现了一个合理的解释。当MethodA调用MethodB的时候,且两个方法都为required属性,则methodA和methodB共享一个事务,当methodB抛出了异常,则共享事务回滚,但是被MethodA catch了,而MethodA又没有及时抛出异常,则MethodA正常执行到最后的时候,则会做提交事务的操作,但是事务已经被回滚了,所以才出现了上面的异常。

既然这样,小弟就开始YY了一下,哪些情况会使调用方没有这个异常呢?经过与小伙伴们的思维碰撞,发现有一下几个方法。

b) MethodA 不加事务,所以执行到最后就不会commit,SUPPORTS和NOT_SUPPORTED都可以实现这种功能。

c) MethodB 设置不共享事务,拥有自己单独的事务。验证发现,REQUIRES_NEW可以实现这种功能。

然后又YY了下,既然一个回滚的事务不能提交了,那么这个回滚的事务可以重复回滚吗?

d) MethodA 调用MethodB,如果MethodA不catch MethodB,则调用方会怎么样?很简单当然直接捕获到MethodB的异常了,但是感觉这个场景不能完全反应初回滚的事务是否可以重复回滚。代码如下:

  1. public void methodA() {
  2. methodB();
  3. otherOperation;
  4. }

e) 还有什么场景可以模拟回滚的事务是否可以再回滚呢?看,代码如下:

  1. public void methodA() {
  2. try {
  3. methodB();
  4. } catch(Exception e) {
  5. process();
  6. }
  7. try {
  8. methodB();
  9. } catch(Exception e) {
  10. process();
  11. }
  12. System.out.println("**************");
  13. otherOperation;
  14. }

第一个MethodB已经回滚了共享的事务,第二个MethodB同样会抛出异常回滚共享的事务,如果执行了后面的System.out,则说明事务可以多次回滚。测试发现打印出来了后面的SysOut的内容,所以猜测可能是这样回滚事务的时候如果发现事务已经回滚,则直接跳过。

Spring事务传递性探讨的更多相关文章

  1. Spring事务控制和传递性理解

    1.在同一类方法间相互调用,如果调用方无事务控制,被调用方有事务控制,则被调用方也无事务 原因:外部经过spring容器调用service的方法事务才生效,service类内部方法间相互调用事务不生效 ...

  2. JDK动态代理给Spring事务埋下的坑!

    一.场景分析 最近做项目遇到了一个很奇怪的问题,大致的业务场景是这样的:我们首先设定两个事务,事务parent和事务child,在Controller里边同时调用这两个方法,示例代码如下: 1.场景A ...

  3. (转)面试必备技能:JDK动态代理给Spring事务埋下的坑!

    一.场景分析 最近做项目遇到了一个很奇怪的问题,大致的业务场景是这样的:我们首先设定两个事务,事务parent和事务child,在Controller里边同时调用这两个方法,示例代码如下: 1.场景A ...

  4. Spring事务管理——回滚(rollback-for)控制

    探讨Spring事务控制中,异常触发事务回滚原理.文章进行了6种情况下的Spring事务是否回滚. 以下代码都是基于Spring与Mybatis整合,使用Spring声明式事务配置事务方法. 1.不捕 ...

  5. 事务特性,事务的隔离级别,并发事务可能出现的问题,spring事务 数据库锁

    1.0 事务特性(ACID) Atomicity:原子性,一个事务不可以被拆分 Consistency:一致性,在事务执行前数据库的数据处于正确的状态,而事务执行完成后数据库的数据还是处于正确的状态, ...

  6. 本人遇到的spring事务之UnexpectedRollbackException异常解决笔记

    本人最近在使用spring事务管理的过程中遇到如下异常,导致服务端抛出500给前端,让搞前端的哥们抱怨我心里着实不爽,前前后后折腾了近半个小时才得于解决,今天就做个笔记,以免日后又犯这个错误.好了,错 ...

  7. Spring事务管理之几种方式实现事务

    1.事务认识 大家所了解的事务Transaction,它是一些列严密操作动作,要么都操作完成,要么都回滚撤销.Spring事务管理基于底层数据库本身的事务处理机制.数据库事务的基础,是掌握Spring ...

  8. 一文带你深入浅出Spring 事务原理

    Spring事务的基本原理 Spring事务的本质其实就是数据库对事务的支持,没有数据库的事务支持,spring是无法提供事务功能的.对于纯JDBC操作数据库,想要用到事务,可以按照以下步骤进行: 获 ...

  9. Spring事务方法上增加synchronized真的有效果吗?

    此文转载,Spring事务本身是一个非常复制的问题,再加上线程并发处理就更加要主要了,由于再开发中有很多朋友会范与下文同样的错误,因分享给大家. 前言 Spring事务的一个奇怪的问题. 朋友问了我一 ...

随机推荐

  1. text输入框中按下enter键时阻止刷新页面

    1.在js中加入一个方法: function judge_enter(){ if(window.event.keyCode==13){ return false;//阻止页面刷新的作用 } } 2.然 ...

  2. javascript第三方组件

    一.一个javascript文件上传组件.转载:http://www.cnblogs.com/fumj/archive/2012/12/07/2806673.html http://fineuploa ...

  3. 记一次Time-Wait导致的问题

    去年(2014年)公司决定服务框架改用Finagle(后续文章详细介绍),but 公司业务系统大部分是C#写的,然后 finagle只提供了 scala/java 的Client 于是 只能自己动手丰 ...

  4. 10 个实用的 jQuery 表单操作代码片段

    jQuery 绝对是一个伟大的开源JavaScript类库,是帮助我们快速和高效开发前端应用的利器.可能大家在日常的开发过程中常常会处理表单相关的 JavaScript,在今天这篇代码片段分享文章中, ...

  5. Codeforces Gym 100531I Instruction 构造

    Problem I. Instruction 题目连接: http://codeforces.com/gym/100531/attachments Description Ingrid is a he ...

  6. 有用好看的CSS+JS+table 导航

    预览效果图 watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQv/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dis ...

  7. qt creator中使用qwt插件

    前提:我用mingw编译的qwt. 将qwt插件集成到qt designer非常easy.仅仅要把qwt编译的qwt_designer_plugin.dll复制到C:\Qt\Qt5.3.1\5.3\m ...

  8. HDOJ 1914 The Stable Marriage Problem

    rt 稳定婚姻匹配问题 The Stable Marriage Problem Time Limit: 5000/1000 MS (Java/Others)    Memory Limit: 6553 ...

  9. Visual Studio Code 1.0.1 for python

    1. 安 F1健 ext install python E:\test\.vscode下的三个文件 2.launch.json { "version": "0.1.0&q ...

  10. 在Dropbox上搭建私有的Git仓库的教程

    导读 Git版本控制系统需要一个服务器端,而GitHub上要想创建私有的Git服务器端仓库则触及到收费项目,于是这里我们利用Dropbox的免费空间,来看一下在Dropbox上搭建私有的Git仓库的教 ...