当前位置: 首页 > 面试题库 >

了解Spring事务-当事务方法调用另一个事务方法时会发生什么?

壤驷志学
2023-03-14
问题内容

为了了解Spring事务的工作原理,我想知道在以下情况下会发生什么情况,其中一种方法标记为,而@Transactional另一种方法标记为@Transactional

假设配置使用所有默认设置。

@Service("myService")
@Transactional
public MyService{
   public void myServiceMethod(){
      myDAO.getSomeDBObjects();
   }
}

@Repository("myDAO")
@Transactional
public MyDAOWithUsesBeyondMyService{
   public void getSomeDBObjects(){...}
}

现在,如果我要输入MyService.myServiceMethod(),显然可以开始交易。然后,钻进去myDAO.getSomeDBObjects()会发生什么?事务已经存在的事实会导致没有新的事务诞生,还是我在这里创建两个事务?

关于传播的文档(在下面引用)似乎涵盖了这一点,但是我想验证一下我的理解,这对于我的处女大脑来说可以一次理解所有知识。

传播
:通常,在事务范围内执行的所有代码都将在该事务中运行。但是,您可以选择在已经存在事务上下文的情况下执行事务方法时指定行为。例如,代码可以在现有事务中继续运行(常见情况);或者可以暂停现有交易并创建新交易。Spring提供了EJB
CMT熟悉的所有事务传播选项。要了解有关Spring中事务传播的语义的信息,请参见第10.5.7节“事务传播”。


问题答案:

两个答案:

a)不要这样做。使用@Transactional在服务层或DAO层,但不能同时(服务层是通常的选择,因为你可能希望每一个服务方法一个交易)

b)如果这样做,会发生什么情况取决于注释的propagation属性,@Transactional并在本节中进行描述:10.5.7事务传播。基本上:PROPAGATION_REQUIRED意味着同一事务将用于两种方法,同时PROPAGATION_REQUIRES_NEW开始新事务。

关于您的评论:

当然,我不断阅读并意识到,当我使用代理时,第二种方法将不会由事务代理管理,因此就像其他任何方法调用一样。

在您的情况下,这是不正确的(仅当两个方法都在同一类中时)。

如果一个bean有方法ab,和a电话b,然后b叫上实际的方法,而不是代理,因为它是从代理中调用(豆不知道它是代理到外面的世界)。

proxy      bean  
a() -->    a()
            |
            V  
b() -->    b()

但是,根据您的情况,服务将具有注入的dao对象,该对象本身就是代理,因此您将遇到以下情况:

           proxy      bean
service    a() -->    a()
                       |
             /---------/
             |                 
             V
dao        b() -->    b()


 类似资料:
  • 问题内容: 为了了解Spring事务的工作原理,我想知道在以下情况下发生的情况:如果一种方法标记为,而另一种方法标记为。 假设配置使用所有默认设置。 现在,如果我要输入,显然可以开始交易。然后,钻进去会发生什么?交易已经存在的事实会导致没有新的交易诞生,还是我在这里创建两个交易? 关于Propagation的文档(在下面引用)似乎涵盖了这一点,但是我想验证一下我的理解 Propagation:通常

  • 我有两项服务。一个从数据库加载数据,修改它们并调用另一个服务来保留修改后的数据: 使用这样的代码,每次调用CalledService.persistData时都会创建一个新的事务。然而,如果我删除了标有“##”的行,那么整个流程只创建了一个事务,允许在发生任何异常时回滚。 这是预期的Spring行为吗? 有没有办法保持被叫服务事务性,并避免在从调用方服务转到被叫服务时创建新事务? 请注意,我确实尝

  • 我正在从非事务类try块(由另一个EJB类调用)调用事务方法a,该块将引发RuntimeException 然后在catch块中,事务方法b将处理exp。 令人惊讶的是,我必须用“REQUIRES\u NEW”注释方法B,否则程序将出现“Transaction is not active”异常。(stacktrace与此类似) 这是否是因为方法A的事务(标记为RuntimeException的回滚

  • 我正在尝试创建一个事务方法,该方法调用其他几个事务方法以保存一些相互依赖的db实体。如果任何调用失败,我希望事务完全回滚。但是,这不是观察到的行为。这是我的代码: 也有and,但是当事务在第二次调用时失败时,第一个被提交。

  • 我正在查看一些现有的代码,并想知道在下面的场景中使用Spring的@Transactional注释会发生什么?考虑以下示例: 下面的updateDataBaseItem()方法是常见的,可以从其他非事务性方法和上面的方法调用:

  • 问题内容: 在Spring中,带有注释的方法 将获得一个新的事务(如果还没有),但是我注意到,如果从非事务处理方法调用事务方法,则不会获得任何事务。这是代码。 是一个常规方法,该方法调用是事务性的,但不会保留任何更改。 我正在使用Spring 3和Hibernate3。在这里我做错了什么?谢谢。 问题答案: 这是Springs AOP的局限性之一。因为dao bean实际上是在spring时创建的