仅仅告诉你用 @Transactional
注解来注解你的类,在你的配置中添加 @EnableTransactionManagement
,并期望你能理解这一切是如何运作的,这是不够的。为了提供更深入的理解,本节将在事务相关问题的背景下解释 Spring 框架的声明式事务基础设施的内部运作。
关于 Spring 框架的声明性事务支持,最重要的概念是这种支持是通过 AOP 代理 实现的,而且事务 advice 是由元数据(目前是基于 XML 或注解)驱动的。AOP 与事务元数据的结合产生了一个 AOP 代理,它使用 TransactionInterceptor 与适当的 TransactionManager 实现来驱动围绕方法调用的事务。
Spring Framework 的 TransactionInterceptor 为命令式和反应式编程模型提供事务管理。拦截器通过检查方法的返回类型来检测所需的事务管理类型。返回反应式类型的方法,如 Publisher 或 Kotlin Flow(或其子类型),有资格进行反应式事务管理。所有其他的返回类型,包括 void,都使用指令性事务管理的代码路径。
事务管理的味道会影响到需要哪个事务管理器。强制性事务需要 PlatformTransactionManager,而反应性事务使用 ReactiveTransactionManager 的实现。
:::info @Transactional 通常与 PlatformTransactionManager 管理的线程绑定的事务一起工作,将一个事务暴露给当前执行线程内的所有数据访问操作。注意:这不会传播到方法内新启动的线程。
由 ReactiveTransactionManager 管理的反应式事务使用 Reactor 上下文而不是线程本地属性。因此,所有参与的数据访问操作都需要在同一反应式管道中的同一 Reactor 上下文中执行。 :::
下图显示了在事务代理上调用方法的概念性视图: