Spring事务与涉及两个DAO的遗留代码

10 浏览
0 Comments

Spring事务与涉及两个DAO的遗留代码

我正在处理一些遗留代码,其中所有的Spring DAO都带有@Transactional注解。

现在,我有一个业务需求,在我的服务层中需要调用两个不同的DAO,并且如果在任何地方失败,需要回滚事务。

在Spring 5中,如何实现这一点,而不删除DAO中的@Transactional注解,并仍然可以从服务层使用它们。我认为下面的代码不会起作用,因为每个DAO中的事务将是独立的。

非常感谢。

0
0 Comments

在使用Spring事务处理与涉及两个DAO的旧代码时,出现了以下问题:

- 目标是确保当抛出未经检查的异常时,事务将回滚通过两个dao调用所做的更改。

- 希望保留dao层中的事务注解。

解决方法:

- 可以在服务层中保留事务注解,并从dao方法中删除它们。Spring的事务可以是类级别或方法级别的,因此可以只在调用两个dao方法的方法上使用事务注解。

- 如果两个dao处理两个不同的数据源,可以使用Spring数据的ChainedTransactionManager来处理多个数据源的事务。具体可以参考https://docs.spring.io/spring-data/commons/docs/current/api/org/springframework/data/transaction/ChainedTransactionManager.html

0
0 Comments

问题的出现原因:由于在第二个方法中使用了默认的Propagation.REQUIRED传播行为,因此它会使用当前的事务,最终只会有一个事务。

解决方法:

为了解决这个问题,可以考虑将第二个方法的传播行为设置为Propagation.REQUIRES_NEW,这样就会创建一个新的事务。这样在第一个方法的事务提交之前,第二个方法的事务就会独立于第一个方法的事务进行提交。

代码示例:

@Transactional(propagation = Propagation.REQUIRED)
public void method1() {
    // 执行业务逻辑
    dao1.save(data1);
    method2();
}
@Transactional(propagation = Propagation.REQUIRES_NEW)
public void method2() {
    // 执行业务逻辑
    dao2.save(data2);
}

在上面的代码示例中,我们在第一个方法method1()上添加了@Transactional注解,并设置了传播行为为Propagation.REQUIRED。在第二个方法method2()上也添加了@Transactional注解,并设置了传播行为为Propagation.REQUIRES_NEW。

这样,当method1()方法执行时,会创建一个事务,并在调用method2()方法时继续使用该事务。而method2()方法在执行时,会创建一个新的事务,与method1()方法的事务相互独立。

通过这种方式,我们可以解决在使用两个DAO对象时,需要分别使用不同的事务的问题。

0
0 Comments

Spring事务与涉及两个DAO的旧代码(Spring transaction with legacy code involving two DAOs)

在这篇文章中,我们将讨论Spring事务管理中的一个问题,即涉及两个DAO(数据访问对象)的旧代码。我们将探讨该问题的原因以及可能的解决方法。

问题的原因是两个默认配置。首先,@Transactional注解的默认传播类型是Propagation.REQUIRED。这意味着如果当前存在事务,则支持该事务;如果不存在事务,则创建一个新的事务。其次,默认情况下,@Transactional注解的默认回滚行为是只在RuntimeException和Error发生时回滚,而不在检查异常(业务异常)发生时回滚。

这两个默认配置确保在同一个service方法中通过相同的事务处理fooDao.action1()和barDao.action2()方法,并且在服务层中出现RuntimeException或自定义回滚配置时进行回滚。

以下是一个示例代码:

public class TestServiceImpl implements TestService {
    public void callDaoMethods() {
        fooDao.action1();
        barDao.action2();
    }
}

这个问题的解决方法是将两个DAO方法的调用放在一个新的事务中。为此,我们可以在service方法上添加@Transactional注解,并在调用DAO方法之前使用@Transactional注解的propagation属性将传播类型设置为Propagation.REQUIRES_NEW。这将在每个DAO方法调用之前创建一个新的事务,并确保它们在任何异常发生时都可以回滚。

下面是修改后的代码:

public class TestServiceImpl implements TestService {
    @Transactional(propagation = Propagation.REQUIRES_NEW)
    public void callDaoMethods() {
        fooDao.action1();
        barDao.action2();
    }
}

通过这种方式,我们可以解决涉及两个DAO的旧代码中的事务管理问题。

参考链接:

- 默认传播类型:https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/transaction/annotation/Transactional.html#propagation--

- 默认回滚行为:https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/transaction/annotation/Transactional.html#rollbackFor--

0