掌握Spring聲明式事務傳播機制:AOP與ThreadLocal的協同工作

聲明式事務的傳播機制是解決多個事務方法嵌套調用時,事務如何創建、復用、掛起或隔離的核心邏輯。它的實現依賴于事務管理器、事務狀態管理、線程上下文綁定等組件的協同,本質是通過一套 “規則判斷 + 狀態維護” 的邏輯,在方法調用時動態決定事務的行為。

一、傳播機制的核心目標

當一個帶有@Transactional的方法 A 調用另一個帶有@Transactional的方法 B 時,需要解決:

  • 方法 B 是否復用方法 A 的事務?
  • 方法 B 是否需要新建事務,同時掛起方法 A 的事務?
  • 如果方法 A 沒有事務,方法 B 是否必須報錯(如 MANDATORY)?

傳播機制就是通過預定義的規則(如 REQUIRED、REQUIRES_NEW 等),自動處理這些場景,避免手動控制事務的繁瑣。

二、實現的核心組件

傳播機制的實現依賴于 Spring 事務體系中的幾個核心組件,它們的協作是關鍵:

  1. TransactionDefinition
    定義了事務的 “元信息”,包括:

    • 傳播行為(propagationBehavior):如 REQUIRED、REQUIRES_NEW 等;
    • 隔離級別、超時時間、是否只讀等。
      每個@Transactional注解的方法都會被解析為一個TransactionDefinition對象,作為傳播機制的判斷依據。
  2. PlatformTransactionManager
    事務管理器的頂層接口,其中getTransaction(TransactionDefinition definition)方法是傳播機制的 “決策核心”—— 它根據當前線程的事務狀態和TransactionDefinition中的傳播行為,決定如何處理事務(創建、復用、掛起等)。

  3. TransactionStatus
    維護事務的實時狀態,包括:

    • 是否是新創建的事務(isNewTransaction ());
    • 是否掛起了外層事務(如果有);
    • 事務是否被標記為回滾(isRollbackOnly ())。
      它是事務管理器和后續操作(提交 / 回滾)的 “狀態憑證”。
  4. TransactionSynchronizationManager
    通過ThreadLocal存儲當前線程的事務上下文(如當前事務的連接、掛起的事務等),讓事務管理器能感知到 “當前線程是否已有事務”。

  5. TransactionInterceptor(AOP 攔截器)
    作為 AOP 的環繞通知,在目標方法執行前觸發事務管理器的getTransaction()方法(決策傳播行為),在方法執行后根據結果觸發commit()rollback()

三、傳播機制的實現流程

以 “方法 A 調用方法 B” 為例,拆解傳播機制的核心步驟:

步驟 1:AOP 攔截與元信息解析

當方法 B 被調用時,TransactionInterceptor先攔截調用,解析方法 B 上@Transactional注解的屬性(如傳播行為、隔離級別),生成TransactionDefinition對象。

步驟 2:判斷當前線程是否已有事務

事務管理器通過TransactionSynchronizationManagerhasResource(...)方法,檢查當前線程的ThreadLocal中是否綁定了事務資源(如數據庫連接)。

  • 如果有資源,說明當前線程已有事務(可能是方法 A 創建的);
  • 如果沒有,說明當前線程無事務。
步驟 3:根據傳播行為決策事務操作

事務管理器的getTransaction()方法根據 “當前是否有事務” 和 “傳播行為”,執行不同邏輯:

傳播行為決策邏輯(核心)
REQUIRED若當前有事務,復用當前事務(返回已有的 TransactionStatus);若沒有,新建事務。
REQUIRES_NEW無論當前是否有事務,都新建一個事務;若有當前事務,先掛起(存入 ThreadLocal)。
SUPPORTS若當前有事務,復用;若沒有,以非事務方式執行(不創建事務)。
MANDATORY若當前有事務,復用;若沒有,直接拋出異常(要求必須在事務中執行)。
步驟 4:維護事務狀態(TransactionStatus)
  • 對于新建的事務TransactionStatus會標記isNewTransaction()=true,并將事務資源(如數據庫連接)通過TransactionSynchronizationManager綁定到當前線程。
  • 對于復用的事務TransactionStatus會關聯到外層事務的狀態,同時記錄 “嵌套層級”(方便后續提交 / 回滾時判斷是否是最外層事務)。
  • 對于掛起的事務(如 REQUIRES_NEW):會將當前事務的狀態存入ThreadLocal的 “掛起隊列”,待新事務完成后恢復。
步驟 5:事務執行與后續處理

方法 B 執行完成后,TransactionInterceptor會根據執行結果(正常 / 異常)和TransactionStatus決定提交或回滾:

  • 若方法 B 是新建事務(如 REQUIRES_NEW 或 REQUIRED 且無外層事務):直接提交或回滾,并解綁線程資源;
  • 若方法 B 是復用外層事務(如 REQUIRED 且有外層事務):僅標記事務狀態(如異常時標記rollbackOnly),最終由最外層事務統一提交 / 回滾;
  • 若方法 B掛起了外層事務(如 REQUIRES_NEW):提交 / 回滾新事務后,從ThreadLocal中恢復被掛起的外層事務,繼續執行外層邏輯。

四、關鍵細節:嵌套事務的狀態管理

傳播機制的核心難點是 “嵌套事務的狀態同步”,例如:

  • 當內層方法(REQUIRED)拋出異常時,會將外層事務的TransactionStatus標記為rollbackOnly,外層方法執行到最后會發現這個標記,從而觸發整體回滾;
  • 當內層方法使用 REQUIRES_NEW 時,它的事務獨立于外層,內層提交 / 回滾不會影響外層(但外層可以捕獲內層異常后繼續執行)。

這一切都依賴TransactionStatus對狀態的精準記錄,以及TransactionSynchronizationManager對線程上下文的維護 —— 確保事務狀態在嵌套調用中不混亂。

總結

聲明式事務傳播機制的實現,本質是:


通過 AOP 攔截事務方法,解析傳播規則,結合線程本地存儲(ThreadLocal)感知當前事務狀態,由事務管理器動態決策事務的創建、復用或掛起,并通過事務狀態(TransactionStatus)維護嵌套關系,最終實現多個事務方法嵌套時的自動化事務管理

理解傳播機制的關鍵,在于把握 “當前線程事務狀態” 與 “傳播行為規則” 的對應關系,以及TransactionStatus如何串聯起整個事務的生命周期。

如果這篇文章對大家有幫助可以點贊關注,你的支持就是我的動力😊!

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/90610.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/90610.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/90610.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

@Transactional事務注解的批量回滾機制

關鍵機制說明:1.??事務注解生效??:Transactional(rollbackFor Exception.class)Override Transactional(rollbackFor Exception.class) public Boolean saveUser(UserDTO userDto) {SysUser sysUser new SysUser();BeanUtils.copyProperties(user…

飛算 JavaAI 深度體驗:開啟 Java 開發智能化新紀元

個人主頁:?喜歡做夢 歡迎 👍點贊 ?關注 ??收藏 💬評論 目錄 一、引言 二、飛算 JavaAI 初印象與功能概覽 (一)初識飛算 JavaAI (二)核心功能模塊概覽 三、智能代碼生成功能深度體…

pandas銷售數據分析

pandas銷售數據分析 數據保存在data目錄 消費者數據:customers.csv商品數據:products.csv交易數據:transactions.csv customers.csv數據結構:字段描述customer_id客戶IDgender性別age年齡region地區membership_date會員日期produc…

訪問Windows服務器備份SQL SERVER數據庫

以前沒有直接訪問過Windows服務器,今天剛一看到的是時候有點懵,竟然下意識的使用SecureCRT遠程工具去連了一下,然后領導說,看一下用戶名,突然意識到,跟我們平時遠程桌面是一樣的。 一、 win + R 打開命令窗口 二、 輸入 mstsc 三、 輸入遠程地址 四、點擊連接,如果有彈…

C++ 面向對象 - 對象定義方法匯總

C對象定義方法匯總 1. 棧上定義方式 1.1 調用無參構造函數的定義方式 無參構造函數有兩種: 默認無參構造函數Demo(){}默認值列表構造函數。Demo():a{1},b{2}{} // 使用初始化列表實現對象定義方式: Demo d; Demo d1{}; // 以下定義方式還調用了拷貝構造…

指尖上的魔法:優雅高效的Linux命令手冊

一、Linux基礎指令 1. ls ls:對于目錄,列出該目錄下的所有子目錄與文件,對于文件,將列出文件名以及其他信息。 -a:列出目錄下的所有文件,包含以.開頭的隱藏文件 -l:列出文件的詳細信息 -d:將目錄…

《磁力下載工具實測:資源搜索+高速下載一站式解決方案》

嘿,朋友們!我是阿燦,今天給大家帶來一個超實用的看片神器,特別適合老司機們使用,保證讓你眼前一亮!推薦一款比某雷更好用的下載工具,搭配資源搜索神器,輕松獲取資源不限速。超強磁力…

Go網絡編程基礎:網絡模型與協議棧概述 - 從理論到實踐的完整指南

1. 引言 在當今的互聯網時代,網絡編程已經成為后端開發的核心技能。Go語言以其出色的并發性能和簡潔的語法,在網絡編程領域展現出了強大的優勢。從Docker、Kubernetes到眾多微服務框架,Go已經成為構建高性能網絡應用的首選語言之一。 你是否…

Web攻防-SSTI服務端模版注入利用分類語言引擎數據渲染項目工具挖掘思路

知識點: 1、WEB攻防-SSTI-利用分類&功能點 2、WEB攻防-SSTI-利用項目&挖掘思路 SSTI(Server Side Template Injection) 服務器模板注入, 服務端接收了用戶的輸入,將其作為 Web 應用模板內容的一部分,在進行目標編譯渲染的過程中&…

李沐動手學深度學習Pytorch-v2筆記【07自動求導代碼實現】

文章目錄前言自動求導實現非標量變量的反向傳播分離計算Python控制流的梯度計算前言 關于走動求導的理論知識個人有點難以理解,推薦大家去看https://blog.csdn.net/weixin_42831564/article/details/135658138這篇文章,講的很好。 自動求導實現 impor…

strchr 與 strstr 函數詳解

一.strchr - 字符查找函數1.函數原型char *strchr(const char *str, int c);2.核心功能在字符串中查找特定字符的第一次出現位置3.參數說明參數 類型 說明str const char* 要搜索的字符串c int 要查找的字符(自動轉換為char)4.返回值…

jakes信道模型

Jakes 模型 前面我們介紹了多徑信道合成信號可表示為: r(t)Re{∑i0N(t)?1ai(t)u(t?τi(t))ej2πfc(t?τi(t))?Di(t)} r(t)Re \left\{\sum_{i0}^{N(t)-1}a_{i}(t)u(t-\tau_{i}(t))e^{j2\pi f_{c}(t-\tau_{i}(t))\phi_{D_{i}}(t)} \right\} r(t)…

JVM類加載機制解析

什么是類加載器? 類加載器是JVM的核心組件之一,負責將Java字節碼文件(.class文件)加載到JVM內存中。由于JVM只能執行二進制字節碼,類加載器的作用就是將編譯后的.class文件轉換為JVM可以理解和執行的格式,使…

用Python和OpenCV從零搭建一個完整的雙目視覺系統(二)

本系列文章旨在系統性地闡述如何利用 Python 與 OpenCV 庫,從零開始構建一個完整的雙目立體視覺系統。 本項目github地址:https://github.com/present-cjn/stereo-vision-python.git 項目架構設計:藍圖、分工與工作流 在上一篇文章中&#…

億級流量下的緩存架構設計:Redis+Caffeine多級緩存實戰

億級流量下的緩存架構設計:RedisCaffeine多級緩存實戰 一、為什么需要多級緩存? 在億級流量場景下,單純依賴Redis會遇到三大瓶頸:網絡延遲:Redis遠程訪問通常需要1-5ms,QPS超過10萬時成為瓶頸資源成本&…

AI基建還能投多久?高盛:2-3年不是問題,回報窗口才剛開啟

高盛表示,盡管AI商業化變現仍處早期階段,但基于成本削減的第一階段回報已經顯現。預測到2030年AI自動化可為財富500強企業節省約9350億美元成本。分析師認為,這一早期收益足以支撐當前AI基礎設施投資水平,盡管增長率可能放緩。雖然…

【mac】快捷鍵使用指南

在Mac上,根據選擇對象的不同,在選擇時移動的方法也有所不同,以下是具體介紹: 移動文件或文件夾:可通過拖放操作移動。打開“訪達”(Finder),找到要移動的文件或文件夾,按…

CS144 lab2 tcp_receiver

1. 實驗目的 lab2 的目的是實現tcp的接收端。 主要包括兩方面 (1) 從發送端接收消息,使用Reassembler聚合字節流(Bytestream) (2)將確認號(ackno)和window size發回對端 …

【論文筆記】A Deep Reinforcement Learning Based Real-Time Solution Policy for the TSP

《基于 DRL 和 DCNN 的實時 TSP 求解策略》IEEE TRANSACTIONS ON INTELLIGENT TRANSPORTATION SYSTEMS, VOL. 24, NO. 6, JUNE 2023一段話總結本文提出了一種基于深度強化學習(DRL) 和深度卷積神經網絡(DCNN) 的實時旅行商問題&am…

MMaDA:多模態大型擴散語言模型

集眾家之所長,成大一統。普林斯頓大學、北京大學、清華大學、字節跳動的研究者將“文本推理、多模態分析、圖像生成”三大方向融合在一個單一擴散模型里,并用恰當的優化策略來提升模型在各個方向的性能。 研究動機 研究人員致力于開發一個能夠處理多種模…