Spring 框架中事务传播行为的定义
这个 Propagation
枚举是 Spring 框架中事务传播行为的定义,它用于指定事务方法在调用另一个事务方法时,事务应该如何传播。这是在 Spring 的 @Transactional
注解中使用的关键配置之一。
事务传播行为详解
以下是每种传播行为的详细解释:
1. REQUIRED
(0) - 必需(默认值)
行为:如果当前存在事务,则加入该事务;如果当前没有事务,则创建一个新的事务。
使用场景:最常用的传播行为,适用于大多数业务操作。
2. SUPPORTS
(1) - 支持
行为:如果当前存在事务,则加入该事务;如果当前没有事务,则以非事务的方式继续运行。
使用场景:适用于那些不需要事务但可以在有事务时参与事务的方法,如查询操作。
3. MANDATORY
(2) - 强制
行为:如果当前存在事务,则加入该事务;如果当前没有事务,则抛出异常。
使用场景:要求必须在已有事务中执行的方法,如果不是在事务中调用则会报错。
4. REQUIRES_NEW
(3) - 新建
行为:创建一个新的事务,如果当前存在事务,则把当前事务挂起。
使用场景:需要独立事务的操作,不受外部事务回滚的影响(如日志记录)。
5. NOT_SUPPORTED
(4) - 不支持
行为:以非事务方式执行操作,如果当前存在事务,则把当前事务挂起。
使用场景:需要在非事务环境下执行的操作,不希望受到事务管理的影响。
6. NEVER
(5) - 从不
行为:以非事务方式执行,如果当前存在事务,则抛出异常。
使用场景:明确要求不能在事务中执行的操作。
7. NESTED
(6) - 嵌套
注意事项
这个 Propagation
枚举是 Spring 事务管理的核心组成部分,它提供了灵活的事务边界控制能力,帮助开发者构建健壮的应用程序
行为:如果当前存在事务,则在嵌套事务内执行;如果当前没有事务,则创建一个新的事务。
使用场景:复杂业务中需要部分回滚的场景,嵌套事务可以独立回滚而不影响外部事务。
@Service public class UserService {@Autowiredprivate UserRepository userRepository;@Autowiredprivate LogService logService;// 默认使用 REQUIRED 传播行为@Transactionalpublic void createUser(User user) {userRepository.save(user);}// 明确指定传播行为@Transactional(propagation = Propagation.REQUIRES_NEW)public void updateUserWithNewTransaction(User user) {userRepository.update(user);}// 组合使用不同传播行为的方法@Transactional(propagation = Propagation.REQUIRED)public void complexOperation(User user) {userRepository.save(user); // 参与当前事务// 创建一个独立的新事务,不受当前事务回滚影响logService.auditLog("User created: " + user.getName());} }@Service public class LogService {@Transactional(propagation = Propagation.REQUIRES_NEW)public void auditLog(String message) {// 这个操作会在独立事务中执行// 即使调用方事务回滚,这个日志记录也会被提交} }
实际应用场景
资金转账:使用
REQUIRED
确保扣款和加款在同一个事务中操作日志记录:使用
REQUIRES_NEW
确保即使业务操作失败,日志也能被记录数据校验:使用
SUPPORTS
或NOT_SUPPORTED
进行不需要事务的简单查询批量处理:使用
NESTED
实现部分失败部分成功的复杂业务逻辑默认的传播行为是
REQUIRED
,这也是最常用的选项NESTED
传播行为需要底层数据库支持保存点(Savepoint)传播行为的选择会影响应用的性能和数据一致性
理解不同传播行为的区别对于设计正确的事务边界至关重要