SpringBoot声明式事务

本文介绍了SpringBoot中的声明式事务管理,包括事务的基础知识如propagation、isolation、timeout、readOnly等属性,以及实战中如何使用@Transactional注解进行异常回滚和不回滚的配置。示例代码展示了在MyBatis环境下,如何通过SpringBoot自动配置实现事务管理。
摘要由CSDN通过智能技术生成

所有数据访问技术都有事务机制,这些技术提供了API来开启事务、提交事务完成数据操作,或者在发生错误的时候回滚数据。

Spring采用统一的机制来处理不同的数据访问技术的事务, Spring的事务提供一个PlatformTransactionManager的接口,不同的数据访问技术使用不同的接口实现。

Data Tech 实现
JDBC DataSourceTransactionManager
JPA JPATransactionManager
Hibernate HibernateTransactionManager
JDO JDOTransactionManager
分布式事务 JtaTransactionManager

Mybatis-Spring依赖于 DataSourceTransactionManager ,没有自己实现 PlatformTransactionManager。

而得益于SpringBoot的自动配置机制,为我们自动开启了声明式事务支持, 我们无需添加注解@EnableTransactionManagement

事务基础

Spring提供一个@EnableTransactionManagement注解在配置类上开启声明式事务支持, 自动扫描加了@Transactional注解的类和方法,加入事务支持。

@Transactional的配置项:

配置项 含义 备注
value 定义事务管理器 它是 SpringIOC 容器的一个Bean id,这个Bean需要实现接口 PlatformTransactionManager
transactionManager 定义事务管理器 它是 SpringIOC 容器的一个Bean id,这个Bean需要实现接口 PlatformTransactionManager
isolation 隔离级别 这是一个数据库在多个事务同时存在时的概念。默认值是数据库默认隔离级别
propagation 传播行为 传播行为是方法之间调用的问题。默认值为Progation.REQUIRED
timeout 超时时间 单位为秒,当超时时,会引发异常,默认会导致事务回滚
readOnly 是否开启只读事务 默认 false
rollbackFor 回滚事务的异常类定义 只有当方法产生所定义的异常时,才会回滚事务,否则提交事务
rollbackForClassName 回滚事务的异常类名定义 同 rollbackFor,只是使用类名称定义
noRollbackFor 当产生哪些异常不回滚事务 当产生所定义异常时,Spring将继续提交事务
noRollbackForClassName 当产生哪些异常不回滚事务 同 noRollbackFor,只是使用类名称定义
propagation

事务的传播机制,主要有以下几种,默认是 REQUIRED:

  1. REQUIRED - 方法A调用时候没有事务新建一个事务,在方法A中调用方法B,将使用相同的事务,如果方法B发生异常需要回滚,整个事务回滚。
  2. REQUIRES_NEW - 方法A调用方法B时,无论是否存在事务都开启一个新事务,这样B方法异常不会导致A的数据回滚。
  3. NESTED - 和REQUIRES_NEW类似,但是只支持JDBC,不支持JPA或Hibernate
  4. SUPPORTS - 方法调用时有事务就用事务,没事务就不用事务
  5. NOT_SUPPORTED - 强制方法不在事务中执行,若有事务,在方法调用到结束阶段先挂起事务。
  6. NEVER - 强制不能有事务,若有事务就抛出异常
  7. MANDATORY - 强制必须有事务,如果没有事务就抛出异常
isolation

事务的隔离级别,决定了事务的完整性,主要一下几种,默认是DEFAULT:

  1. READ_UNCOMMITTED - A事务修改记录但没提交,B事务可读取到修改后的值。可导致脏读、不可重复读、幻读。
  2. READ_COMMITTED - A事务修改并提交后,B事务才能读取到修改后的值,阻止了脏读,但可能导致不可重复读和幻读。
  3. REPEATABLE_READ - A事务读取了一条记录,B事务将不能修改这条记录,阻止脏读和不可重复读,但是可能出现幻读。
  4. SERIALIZABLE - 事务是顺序执行的,可避免所有缺陷,但是开销很大。
  5. DEFAULT - 使用当前数据库默认隔离级别,入Oracle、SQL Server是READ_COMMITTED,MySQL是REPEATABLE_READ
timeout

事务过期时间,默认是当前数据库默认事务过期时间。

readOnly

指定是否为只读事务,默认是false。

如果你一次执行单条查询语句,则没有必要启用事务支持,数据库默认支持SQL执行期间的读一致性。

如果你一次执行多条查询语句,例如统计查询,报表查询,在这种场景下,多条查询SQL必须保证整体的读一致性, 否则,在前条SQL查询之后,后条SQL查询之前,数据被其他用户改变,则该次整体的统计查询将会出现读数据不一致的状态, 此时,应该启用只读事务支持。

只读事务与读写事务区别:

对于只读查询,可以指定事务类型为 readonly,即只读事务。由于只读事务不存在数据的修改, 因此数据库将会为只读事务提供一些优化手段,例如Oracle对于只读事务,不启动回滚段,不记录回滚log。

rollbackFor

指定哪些异常可以导致事务回滚,默认是 Throwable 的子类。

noRollbackFor

执行哪些异常不可用引起事务回滚,默认是 Throwable 的子类。

实战篇

实际项目中,使用SpringBoot的默认配置就已经足够满足我们的需求了。 本篇将通过几个例子来演示如何使用@Transactional注解,在出现异常时候回滚或不回滚数据。

使用的DAO技术是MyBatis进行数据访问,使用druid数据库连接池, 另外配合mybatis-plus,实现数据访问层。

引入依赖:

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
    <groupId>mysql</groupId>
    <artifactId
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值