Spring 中一个事务方法调用另一个事务方法会怎样?

本文涉及的产品
服务治理 MSE Sentinel/OpenSergo,Agent数量 不受限
简介: 【6月更文挑战第5天】如果我们在一个包含事务的方法中,调用了另一个包含里事务的方法,那么,Spring 会创建新的事物吗?如果方法抛出异常导致事务会滚了呢?

在基于 Spring Framework 开发项目时,大多数情况下,如果一个业务需要事务管理,我们会在 Service 层的实现方法上添加 @Transactional 注解,Spring 会自动给对应的方法添加事务管理。

如果我们在一个包含事务的方法中,调用了另一个包含里事务的方法,那么,Spring 会创建新的事物吗?如果方法抛出异常导致事务会滚了呢?

这要分两种情况分析。

第一种,是在一个包含事务的方法中,通过直接使用方法名或者 this.方法名 调用了当前类中的另一个包含事务的方法,这时,Spring 不会创建新的事务,原因要从 Spring 实现事务管理的原理说起。

Spring 给添加了 @Transactional 注解的方法自动添加事务管理,是通过 AOP 实现的,Spring 通过对当前的方法进行增强,来提供了事务的开启、提交、会滚的逻辑。而 AOP 的实现,要是用到动态代理。

也就是说,在 Spring 的环境中,一个包含事务的方法被调用,其实是代理类的方法被调用了,只有这样才会被开启事务,但是在方法体中调用的同一个类中的其他方法,其调用的都是这个类本身的方法,而不是代理类的方法,因此,被调用的方法不会被增强。

所以结论就是,这种情况下,不会创建新的事务。

第二种,是在一个包含了事务的方法中,通过一个依赖的 Bean,调用了其他类的包含事务的方法。此时,因为是通过依赖的 Bean 调用的,Bean 被 Spring 的容器所管理,因此,实际调用的是增强后的代理类,会执行增强后的逻辑,但是,当前已经开启了一个事务,Spring 会如何处理呢?

此时就要提到 Spring 事务的传播特性,在 @Transactional 注解中有一个 propagation 属性,事务的传播特性可以通过它来指定。可选的值可以在 TransactionDefinition 中找到,分别是一下这些:

  • PROPAGATION_REQUIRED:当前有事务就使用当前事务,否则创建新的事务。(默认值)
  • PROPAGATION_SUPPORTS:事务不是必需的。
  • PROPAGATION_MANDATORY:如果当前没有事务则抛出异常。
  • PROPAGATION_REQUIRES_NEW:无论当前是否有事务,都创建新的事务。
  • PROPAGATION_NOT_SUPPORTED:不支持事务,按照非事务方式运行。
  • PROPAGATION_NEVER:不支持事务,如果有事务则抛出异常。
  • PROPAGATION_NESTED:如果当前有事务就在当前事务里再创建一个事务。

举个例子,当这个值为 REQUIRES_NEW 时,代表无论是否调用方(方法A)是否开启了事务,被调用方(方法B)都会开启新的事务。此时,如果方法B的事务出错发生了会滚,那么只会会滚方法B的事务,方法A的事务不受影响。

目录
相关文章
|
7天前
|
Java 开发者 Spring
spring事务类型,事务传递,隔离级别?
spring事务类型,事务传递,隔离级别?
|
11天前
|
前端开发 Java Spring
自定义 Spring MVC Controller 方法参数处理
【6月更文挑战第3天】在 Spring MVC Controller 的方法参数,Spring 会自动为我们注入一些特殊的参数值,比如 HttpServletRequest、HttpServletResponse 等对象,或者 HTTP 请求参数。
51 0
|
13天前
|
设计模式 Java 关系型数据库
Spring的配置文件,如何配置端口号,,properties,yml获取配置项等方法,外观模式及其优缺点,日志代表的信息
Spring的配置文件,如何配置端口号,,properties,yml获取配置项等方法,外观模式及其优缺点,日志代表的信息
|
13天前
|
Java Spring
面对Spring 不支持java8的改变方法
面对Spring 不支持java8的改变方法
|
15天前
|
Java 关系型数据库 MySQL
【JavaEE进阶】Spring中事务的实现
【JavaEE进阶】Spring中事务的实现
|
20天前
|
Java 关系型数据库 MySQL
Spring 事务和事务传播机制
Spring 事务和事务传播机制
Spring 事务和事务传播机制
|
10月前
|
SQL Java 数据库
第一季:8spring支持的常用数据库事务传播属性和事务隔离级别【Java面试题】
第一季:8spring支持的常用数据库事务传播属性和事务隔离级别【Java面试题】
116 0
|
1月前
|
Java 关系型数据库 MySQL
Spring事务的隔离级别介绍说明以及怎么去修改Spring事务的隔离级别
Spring事务的隔离级别介绍说明以及怎么去修改Spring事务的隔离级别
47 0
|
1月前
|
Java 数据库连接 数据库
spring的五个事务隔离级别和7个事务传播属性
spring的五个事务隔离级别和7个事务传播属性
65 0
|
11月前
|
XML Oracle Java
Spring 事务的隔离级别
Spring 事务的隔离级别
233 0