LCN解決分布式事務原理解析+項目實戰(原創精華版)


寫在前面:

由於工作需要,公司的微服務項目需解決分布式事務的問題,且由我進行分布式事務框架搭建和整合工作。

那么借此機會好好的將解決分布式事務的內容進行整理一下。這邊公司分布式事務框架選型是LCN框架(以后肯定會升級成seata)。

我整理的大綱如下:

1 CAP定律和BASE理論

  有人問,為什么需要了解這個,這個其實是分布式事務基於的理論依據,所以需要了解一下。

1.1 CAP定律

  這個定理的內容是指的是在一個分布式系統中、Consistency(一致性)、 Availability(可用性)、Partition tolerance(分區容錯性),三者不可得兼。

(一)一致性(C

  在分布式系統中的所有數據備份,在同一時刻是否同樣的值。(等同於所有節點訪問同一份最新的數據副本)

(二)可用性(A

  在集群中一部分節點故障后,集群整體是否還能響應客戶端的讀寫請求。(對數據更新具備高可用性)

(三)分區容錯性(P

  以實際效果而言,分區相當於對通信的時限要求。系統如果不能在時限內達成數據一致性,就意味着發生了分區的情況,必須就當前操作在CA之間做出選擇。

(四)總結一下

  以上可以知道分區容錯性(P)主要代表網絡波動產生的錯誤,這是不可避免的,且這個三個模式不可兼得,所以目前就只有兩種模式:CPAP模式。

  其中CP表示遵循一致性原則,但不能保證高可用性,其中zookeeper作為注冊中心就是采用CP模式,因為zookeeper有過半節點不可以的話整個zookeeper將不可用。

  AP表示遵循於可用性原則,例如Eureka作為注冊中心用的是AP模式,因為其為去中心化,采用你中有我我中有你的相互注冊方式,只要集群中有一個節點可以使用,整個eureka服務就是可用的,但可能會出現短暫的數據不一致問題。

1.2 BASE理論

BASEBasically Available(基本可用)、Soft state(軟狀態)和 Eventually consistent(最終一致性)三個短語的縮寫。BASE理論是對CAP中一致性和可用性權衡的結果,其來源於對大規模互聯網系統分布式實踐的總結, 是基於CAP定理逐步演化而來的。BASE理論的核心思想是:即使無法做到強一致性,但每個應用都可以根據自身業務特點,采用適當的方式來使系統達到最終一致性。

(一)基本可用

  基本可用是指分布式系統在出現不可預知故障的時候,允許損失部分可用性注意,這絕不等價於系統不可用。

  比如:響應時間上的損失。正常情況下,一個在線搜索引擎需要在0.5秒之內返回給用戶相應的查詢結果,但由於出現故障,查詢結果的響應時間增加了1~2

  系統功能上的損失:正常情況下,在一個電子商務網站上進行購物的時候,消費者幾乎能夠順利完成每一筆訂單,但是在一些節日大促購物高峰的時候,由於消費者的購物行為激增,為了保護購物系統的穩定性,部分消費者可能會被引導到一個降級頁面

(二)軟狀態

  軟狀態指允許系統中的數據存在中間狀態,並認為該中間狀態的存在不會影響系統的整體可用性,即允許系統在不同節點的數據副本之間進行數據同步的過程存在延時

(三)最終一致性

  最終一致性強調的是所有的數據副本,在經過一段時間的同步之后,最終都能夠達到一個一致的狀態。因此,最終一致性的本質是需要系統保證最終數據能夠達到一致,而不需要實時保證系統數據的強一致性。

2 了解分布式事務

2.1 分布式事務產生的背景 

  在分布式產生之前,互聯網公司的項目都是傳統的單體項目,整個項目都共用了一個數據源,那么進行業務執行對數據庫進行操作的時候,不會產生這種事務不一致問題,因為是同一個數據源用的一個本地事務。

  但隨着我們架構的演變,從單體架構到分布式架構到SOA架構項目再到如今公司采用的微服務架構,我們對服務進行了業務拆分,那么數據源也被拆分,一般微服務項目是一個服務對應一個數據源。

  那么在這種架構下,每個服務都有自己獨立的數據源有自己的本地事務,從而便會產生分布式事務,可能造成服務間數據不一致問題。

2.2 不同架構體系下解決事務的問題

(一)單體架構(單數據源)

  在單體的項目中,多個不同業務邏輯都是在同一個數據源中實現事務管理,是不存在分布式事務的問題,因為同一數據源的情況下都是采用事務管理器,相當於每個事務管理器對應一個數據源。

(一)單體架構(多數據源)

  在單體的項目中,有多個不同的數據源,每個數據源中都有自己獨立的事務管理器,互不影響,那么這時候也會存在多數據源事務管理:解決方案jta+ Atomikos

(一)分布式/微服務架構

  在分布式/微服務架構,每個服務都有自己獨立的數據源和事務管理器,那么在這種情況下如果有業務要進行RPC遠程調用的時候,那就必然可能產生分布式事務。目前主要解決方案有:MQLCNSeata等方案

LCN解決分布式事務

3.1 了解LCN

3.1.1 LCN背景

  LCN框架在20176月份發布第一個版本,從開始的1.0,已經發展到了5.0版本。

  LCN名稱是由早期版本的LCN框架命名,在設計框架之初的1.0 ~ 2.0的版本時框架設計的步驟是如下,各取其首字母得來的LCN命名。

  5.0以后由於框架兼容了LCNTCCTXC三種事務模式,為了避免區分LCN模式,特此將LCN分布式事務改名為TX-LCN分布式事務框架。

3.1.2 LCN定位

TX-LCN定位於一款事務協調性框架,框架其本身並不操作事務,而是基於對事務的協調從而達到事務一致性的效果。(LCN不生產事務,它只是事務的搬運工...woc這有點像農夫山泉的文案)

3.2 LCN分布式事務原理(自己理解的,白話文通俗易懂)

(上圖來源官網) 

  1) 首先我們的lcn協調者(TM)會和lcn客戶端(TC)通過引入的netty一直保持着長連接(持續監聽)。

  2) 當請求的發起方(調用方)進入接口業務之前,會通過AOP技術進到@LcnTransaction注解中LCN協調者那邊生成注冊一個全局的事務組IdgroupId)。

  3) 當發起方(調用方)通過rpc調用參與方(被調用方)的時候,lcn重寫了Feign客戶端,會從ThreadLocal中拿到該事務組IdgroupId),並將該事務組Id設置到請求頭中。

  4) 參與方(被調用方)在請求頭中獲取到了這個groupId的時候,lcn會標識該服務為參與方並加入到該事務組,並會被lcn代理數據源,當該服務業務邏輯執行完成后,進行數據源的假關閉,並不會真正的提交或回滾當前服務的事務。

  5) 當發起方執行完全部業務邏輯的時候,如果無異常會告知lcn協調者,lcn協調者再分別告訴該請求鏈上的所有參與方可以提交了,再進行真正的提交。若發起方調用完參與方后報錯了,也會告知lcn協調者,lcn協調者再告知所有的參與方進行真正的回滾操作,這樣就解決了分布式事務的問題。

3.3 LCN本地環境部署

3.3.1 本地部署注冊中心

  注冊中心是微服務中最為重要的一個組件,提供了服務間在調用時需要的一些ip和端口等列表信息。

  我這邊采用nacos作為注冊中心,具體如何一分鍾快速搭建本地nacos可參見:https://nacos.io/zh-cn/docs/quick-start.html 注冊中心的部署略過不做詳細的說明。搭建好nacos后,訪問127.0.0.1:8848/nacos進行訪問(賬號密碼默認為nacos),出現如下界面即完成了nacos本地的搭建。

 

3.3.2 本地部署協調者TM環境 

  在部署TX-LCN中有遇到問題或想查看部署詳細的操作可以訪問如下地址:http://www.txlcn.org/zh-cn/docs/start.html 

  1) 我們要去github中先將tx-lcn的源碼下載下來,這邊我們選擇的是5.0.2的版本,github下載源碼地址:https://github.com/codingapi/tx-lcn/releases

  

  2) 創建相應的數據庫表,先創建MySQL數據庫, 名稱為: tx-manager,再創建數據庫表t_tx_exception

 

CREATE TABLE `t_tx_exception`  (
  `id` bigint(20) NOT NULL AUTO_INCREMENT,
  `group_id` varchar(64) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
  `unit_id` varchar(32) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
  `mod_id` varchar(128) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NULL DEFAULT NULL,
  `transaction_state` tinyint(4) NULL DEFAULT NULL,
  `registrar` tinyint(4) NULL DEFAULT NULL,
  `remark` varchar(4096) NULL DEFAULT  NULL,
  `ex_state` tinyint(4) NULL DEFAULT NULL COMMENT '0 未解決 1已解決',
  `create_time` datetime(0) NULL DEFAULT NULL,
  PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 1 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_general_ci ROW_FORMAT = Dynamic; 

  3) 打開我們下好的源碼,找到txlcn-tm模塊,修改其配置文件application.properties具體修改的內容根據自己業務而定,官方也有相應配置內容,但需要注意首次運行要將配置文件的這段設置為createspring.jpa.hibernate.ddl-auto=create

 

  4) 准備將txlcn-tm模塊打包成jar,先執行打包命令: mvn clean package -Dmaven.test.skip=true 打包完成后可以在模塊中看到出現了jar包。

  5) 開始對jar包進行運行,進入到target目錄,執行命令啟動jar包:java -jar txlcn-tm-5.0.2.RELEASE.jar

  6) 運行成功后可以看到tomcat啟動成功。

 

  7) 訪問控制台的端口為7919,默認密碼codingapi

 

 

 

  至此,TM部署並啟動完成。

3.3.3 本地配置客戶端TC環境

  TC就是我們的客戶端,也就是我們的微服務,配置相對簡單如下: 

  1) 引入相關依賴,其中一個是lcn核心包,一個是建立長連接的netty包。

<dependency>
    <groupId>com.codingapi.txlcn</groupId>
    <artifactId>txlcn-tc</artifactId>
    <version>5.0.2.RELEASE</version>
</dependency>
<dependency>
    <groupId>com.codingapi.txlcn</groupId>
    <artifactId>txlcn-txmsg-netty</artifactId>
    <version>5.0.2.RELEASE</version>
</dependency>

  2) 配置yml文件,設置服務連接到lcn服務。(注意下lcn控制台是7970,這個8070lcn通訊端口號

tx-lcn:
  client:
    manager-address: 127.0.0.1:8070
  logger:
    enabled: true

  3) 引入依賴並配置好yml文件后,在服務的啟動類上添加@EnableDistributedTransaction注解,開啟分布式事務。

  4) 在業務的方法上面添加注解@LcnTransaction@Transactional,如下圖

  5) 做好這些配置后,開始啟動項目,啟動成功項目后可以在lcn控制台看到相應的服務列表,能夠看到則說明服務已經實現了對lcn事務協調者管理器的注冊。

 

  看到服務都能夠成功注冊進TM后,便全部完成TX-LCN本地環境的搭建,后續可以開始測試自己的業務代碼是否解決了分布式事務的問題。 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM