Spring中的Service方法如果声明了事务,例如@Transactional(propagation = Propagation.REQUIRED),那么调用的时候,Spring会自动管理事务,遇到Exception,会rollback回滚,但是可能会遇到这种情况:同一个Service类中的方法,要调用本类中的其他方法(尽管这个方法也声明了事务),会发现调用的那个方法没有开启事务。
Spring开启事务,需要两个条件
- 首先需要方法声明是public的
- 声明事务,可以是在Service上加@Transactional或者方法上加@Transactional
- 需要从其他类中调用(不能是本类直接调用)
解决办法
- 方式1
在本Service里,内部用注解加一个自身的的service
@Service("systemService") @Transactional(readOnly = false) @Repository public class SystemServiceImpl implements ISystemService { @Resource(name = "systemService") ISystemService selfReference; private void doSomeAndThenMore() { // 这样做实现事务管理 selfReference.doSometingTransaction(); // 如果要让里面的方法实现事务处理,不能这样直接调用:this.doSometingTransaction() } @Transactional(propagation = Propagation.REQUIRES_NEW) public void doSometingTransaction() { // 一些处理逻辑以及数据库操作等,可能涉及到事务 } }
- 方式2
在同一个service中,调用的时候,使用applicationContext.getBean(this.getClass()).someMethod(),如下:
@Service @Transactional(propagation = Propagation.REQUIRED) public class TransactionServiceDemo { @Autowired private ApplicationContext applicationContext; private TransactionServiceDemo getSpringProxy() { return applicationContext.getBean(this.getClass()); } private void doSomeAndThenMore() { // 这样做实现事务管理 getSpringProxy().doSometingTransaction(); // 如果要让里面的方法实现事务处理,不能这样直接调用:this.doSometingTransaction() } @Transactional(propagation = Propagation.REQUIRES_NEW) public void doSometingTransaction() { // 一些处理逻辑以及数据库操作等,可能涉及到事务 } }
文章评论