文章目录
事务的基本概念
事务是数据库操作中不可分割的工作单元,具备 ACID 四个特性:
- 原子性(Atomicity):事务中的所有操作要么全部成功,要么全部失败回滚。以银行转账为例,从一个账户扣款和向另一个账户存款这两个操作必须同时完成或者同时失败。
- 一致性(Consistency):事务执行前后,数据库从一个一致性状态转换到另一个一致性状态。如转账前后,两个账户的总金额应保持不变。
- 隔离性(Isolation):多个事务并发执行时,一个事务的执行不应该影响其他事务的执行。例如多个用户同时进行转账操作,彼此之间不应相互干扰。
- 持久性(Durability):事务一旦提交,其对数据库的改变就是永久性的,即使系统崩溃也不会丢失。
Spring Boot 中事务的配置与使用
1. 添加依赖
若使用 Maven,在 pom.xml
里添加 Spring Boot Starter Data JPA 依赖:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
2. 配置数据库
在 application.properties
或者 application.yml
中配置数据库连接信息:
spring.datasource.url=jdbc:mysql://localhost:3306/testdb
spring.datasource.username=root
spring.datasource.password=password
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.jpa.hibernate.ddl-auto=update
spring.jpa.show-sql=true
3. 启用事务管理
在主应用类上添加 @EnableTransactionManagement
注解来开启事务管理:
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.transaction.annotation.EnableTransactionManagement;
@SpringBootApplication
@EnableTransactionManagement
public class YourApplication {
public static void main(String[] args) {
SpringApplication.run(YourApplication.class, args);
}
}
4. 使用 @Transactional
注解
在需要事务管理的方法或者类上添加 @Transactional
注解:
事务传播行为和隔离级别
事务传播行为
事务传播行为用于定义在嵌套事务场景下,新事务与现有事务之间的关系。Spring 提供了 7 种事务传播行为:
- REQUIRED(默认):若当前存在事务,就加入该事务;若不存在,则创建一个新事务。
- SUPPORTS:若当前存在事务,就加入该事务;若不存在,则以非事务方式执行。
- MANDATORY:若当前存在事务,就加入该事务;若不存在,则抛出异常。
- REQUIRES_NEW:无论当前是否存在事务,都会创建一个新事务,并且挂起当前事务。
- NOT_SUPPORTED:以非事务方式执行操作,若当前存在事务,则挂起该事务。
- NEVER:以非事务方式执行操作,若当前存在事务,则抛出异常。
- NESTED:若当前存在事务,则在嵌套事务内执行;若不存在,则创建一个新事务。
事务隔离级别
事务隔离级别用于控制多个事务并发访问时的相互影响程度。Spring 定义了 5 种事务隔离级别:
- DEFAULT:使用数据库默认的隔离级别。
- READ_UNCOMMITTED:允许读取尚未提交的数据变更,可能会导致脏读、不可重复读和幻读问题。
- READ_COMMITTED:只允许读取已经提交的数据,避免了脏读,但可能会出现不可重复读和幻读问题。
- REPEATABLE_READ:确保在同一个事务中多次读取同一数据的结果是一致的,避免了脏读和不可重复读,但可能会出现幻读问题。
- SERIALIZABLE:最高的隔离级别,完全串行化事务执行,避免了脏读、不可重复读和幻读问题,但会降低并发性能。
在 @Transactional
注解中,可以通过 propagation
和 isolation
属性来指定事务传播行为和隔离级别:
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Isolation;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
@Service
public class UserService {
private final UserRepository userRepository;
public UserService(UserRepository userRepository) {
this.userRepository = userRepository;
}
@Transactional(propagation = Propagation.REQUIRES_NEW, isolation = Isolation.READ_COMMITTED)
public void createUser(User user) {
userRepository.save(user);
}
}
Spring Boot 中编程式事务管理
在 Spring Boot 里,除了声明式事务管理,还能使用编程式事务管理,它能让开发者依据具体的业务逻辑精准地控制事务的边界。
1. 添加依赖
同声明式事务管理,若使用 Maven,需在 pom.xml
里添加 Spring Boot Starter Data JPA 依赖。
2. 配置数据库
同样在 application.properties
或者 application.yml
中配置数据库连接信息。
3. 使用 TransactionTemplate
进行编程式事务管理
TransactionTemplate
是 Spring 提供的一个模板类,可用于编程式事务管理。以下是具体的使用示例:
事务注解总结
@Transactional
这是 Spring 中最常用的事务注解,可应用于类或方法上。当应用于类时,该类的所有公共方法都会启用事务;若应用于方法,则仅该方法启用事务。其常见属性有 propagation
(指定事务传播行为)、isolation
(指定事务隔离级别)、timeout
(指定事务超时时间)、readOnly
(指定事务是否为只读事务)、rollbackFor
(指定哪些异常会导致事务回滚)和 noRollbackFor
(指定哪些异常不会导致事务回滚)。
@EnableTransactionManagement
此注解用于启用 Spring 的声明式事务管理功能。通常将其添加到 Spring Boot 的主应用类上,这样 Spring 就能识别 @Transactional
注解并进行相应的事务管理。
通过以上内容,我们全面了解了 Spring Boot 事务管理的基本概念、配置使用、传播行为、隔离级别、编程式事务管理以及相关注解,开发者可以根据具体业务需求灵活运用这些知识来实现高效可靠的事务处理。