分析代码:
public class UserServiceImpl implements UserService {
private UserMapper userMapper;
(rollbackFor = Exception.class)
public synchronized void isertUser(User user) {
try {
// 插入用户信息
userMapper.insertUser(user);
// 手动抛出异常
throw new SQLException("数据库异常");
} catch (Exception e) {
// 异常处理逻辑
}
}
}
问题:
1.Spring Boot 默认事务回滚前提:遇到运行异常(RuntimeException)和程序错误(Error)。如果是抛出其它的异常,事务不会回滚。
2.由于事务是AOP设计的,不能在方法里面直接try…catch,这样会导致异常被 “吃” 掉,事务无法回滚。
3.同一方法中,使用同步修饰方法(锁)以及事务注解,由于AOP的原因,事务的控制范围比锁还大,锁是无效的,如上面的实例代码。
解决方案:
- 调用Service方法之前,使用锁,使锁的范围比事务大(分布式锁或其它)