Spring中事务失效的原因详细解析

1、自调用问题

原因:Spring 的事务管理是基于 AOP 实现的,通过代理对象来织入事务增强逻辑。在同一个类内部,一个方法直接调用另一个带有 @Transactional 注解的方法时,调用的是对象的实际方法 ,而不是通过代理对象调用,因此事务增强逻辑不会被触发,导致事务失效。

示例代码:

java 复制代码
@Service
public class UserService {
    public void outerMethod() {
        // 自调用 innerMethod,事务失效
        this.innerMethod();
    }

    @Transactional
    public void innerMethod() {
        // 数据库操作
    }
}

2、方法访问权限问题

原因:@Transactional 注解只能应用在 public 方法上。如果将其应用在 private、protected 或默认访问权限(即没有修饰符)的方法上,Spring 不会为该方法创建事务代理,事务会失效。

示例代码:

java 复制代码
@Service
public class UserService {
    @Transactional
    private void privateMethod() {
        // 数据库操作
    }
}

3、异常类型不匹配问题

原因:@Transactional 注解默认只对 RuntimeException 及其子类和 Error 类型的异常进行回滚。如果方法中抛出的是受检查异常(如 IOException、SQLException 等),且没有在 @Transactional 注解中指定 rollbackFor 属性,事务不会回滚。

示例代码:

java 复制代码
@Service
public class UserService {
    @Transactional
    public void insertUser() throws Exception {
        // 数据库操作
        throw new Exception("业务异常"); // 不会触发事务回滚
    }
}

解决办法:

可以通过设置 rollbackFor 属性来指定需要回滚的异常类型,例如 @Transactional(rollbackFor = Exception.class)。

4、未正确配置事务管理器

原因:Spring 的事务管理需要配置相应的事务管理器。如果没有正确配置事务管理器,或者在使用 @Transactional 注解时没有指定正确的事务管理器,事务将无法正常工作。

示例代码(Spring Boot):

java 复制代码
// 没有正确配置事务管理器
@Service
public class UserService {
    @Transactional
    public void insertUser() {
        // 数据库操作
    }
}

5、多线程问题

原因:Spring 的事务是基于线程绑定的,每个线程都有自己独立的事务上下文。如果在一个带有事务的方法中开启了新的线程进行数据库操作,新线程中的操作不会参与到原线程的事务中,即使原线程的事务出现异常回滚,新线程中的操作也不会回滚。

示例代码:

java 复制代码
@Service
public class UserService {
    @Transactional
    public void insertUserWithThread() {
        new Thread(() -> {
            // 数据库操作,不会参与原线程的事务
        }).start();
        // 原线程的数据库操作
    }
}

6、注解未被正确扫描

原因:如果 Spring 没有正确扫描到带有 @Transactional 注解的类,事务注解将不会生效。在 Spring Boot 中,通常会自动扫描 @Service、@Repository 等注解标注的类,但如果配置不正确,可能会导致扫描失败。

解决办法:

确保 @SpringBootApplication 注解所在的类位于正确的包路径下,或者手动配置组件扫描路径,例如 @ComponentScan(basePackages = "com.example.service")。

相关推荐
唠点键盘之外的9 分钟前
26 向量数据库实战:从 0 搭一条能用的检索链路(pgvector + Spring AI)
数据库·人工智能·spring
鬼手点金1 小时前
opencode-rules 插件
java·开发语言·前端·人工智能·chrome·git·github
paopaokaka_luck2 小时前
滑雪场管理系统(AI智能助手流式对话,ECharts 运营数据分析、教练、雪具与场地一体化预约,钱包支付退款、订单核销与服务评价)
java·人工智能·spring boot·网络协议·数据分析·echarts
考虑考虑2 小时前
@JsonInclude注解使用
spring boot·后端·spring
Wang's Blog3 小时前
Java 项目实战: 交友项目 - Dubbo 的内部结构与一次调用的完整链路
java·dubbo
Wang's Blog3 小时前
Java 项目实战: 交友项目 - Dubbo 入门引导
java·dubbo·交友
蜗牛互联网3 小时前
Python Agent工具调用的白名单、参数校验与审批门禁
java·服务器·前端·人工智能·后端·python
SL_staff3 小时前
当规则引擎开始‘懂业务’:JVS-Rules金融风控四大原生能力拆解
java·python·全栈
Shaoshing4 小时前
前缀和与差分
java·数据结构·算法·前缀和·差分
dd聊技术4 小时前
Prompt 从代码常量搬进数据库:改一句话,不用再发一次版
java·后端