TCC-Transaction 解析系列(1):dubbo-sample

分布式服務(wù)

分布式服務(wù)框架是大型互聯(lián)網(wǎng)架構(gòu)的基礎(chǔ)組件之一蒸播,目標(biāo)是能讓各個(gè)業(yè)務(wù)服務(wù)化睡榆,并且在服務(wù)化框架的管理下能夠?qū)崿F(xiàn)基本的 RPC 功能萍肆,以及必要的服務(wù)發(fā)現(xiàn)、服務(wù)治理胀屿、熔斷塘揣、限流等高級(jí)功能。Dubbo 是阿里開(kāi)源的比較知名的分布式服務(wù)化框架宿崭。

服務(wù)化的好處顯而易見(jiàn)亲铡,能讓各個(gè)系統(tǒng)解耦,便于系統(tǒng)拆分葡兑,服務(wù)之間的調(diào)用能很好的被管理起來(lái)奖蔓,無(wú)狀態(tài)的服務(wù)可以部署多個(gè)實(shí)例,提升系統(tǒng)的處理能力讹堤。但是系統(tǒng)拆分過(guò)后吆鹤,會(huì)有一個(gè)明顯的問(wèn)題要解決,即分布式事務(wù)的問(wèn)題洲守。比如一次請(qǐng)求需要對(duì)兩個(gè)服務(wù)分別執(zhí)行一次寫(xiě)操作檀头,當(dāng)一個(gè)服務(wù)的寫(xiě)操作失敗后,另一個(gè)服務(wù)的已經(jīng)持久化的寫(xiě)操作如何有效地進(jìn)行回滾岖沛,是一個(gè)很關(guān)鍵的問(wèn)題暑始,回滾不到位的話(huà),就會(huì)產(chǎn)生臟數(shù)據(jù)婴削。

分布式事務(wù)的基本原理本質(zhì)上都是兩階段提交協(xié)議(2PC)廊镜,TCC (try-confirm-cancel)其實(shí)也是一種 2PC,只不過(guò) TCC 規(guī)定了在服務(wù)層面實(shí)現(xiàn)的具體細(xì)節(jié)唉俗,即參與分布式事務(wù)的服務(wù)方和調(diào)用方至少要實(shí)現(xiàn)三個(gè)方法:try 方法嗤朴、confirm 方法、cancel 方法虫溜。

服務(wù)調(diào)用方( Consumer )在 try 階段調(diào)用提供方( Provider )的 try 方法雹姊,真整個(gè) try 階段一旦成功,接下來(lái)就相繼調(diào)用各個(gè)服務(wù)參與者的 confirm 方法衡楞,而 try 階段一旦失敗吱雏,就立即相繼調(diào)用各個(gè)服務(wù)參與者的 cancel 方法,保證整個(gè)事務(wù)的最終一致性瘾境。而一旦進(jìn)入 confirm 或者 cancel 階段歧杏,就會(huì)一直 confirm 或者 cancel 下去,系統(tǒng)應(yīng)該提供恢復(fù)機(jī)制迷守,即使在 confirm 階段出錯(cuò)時(shí)犬绒,也能夠保證立即或者定時(shí) confirm,直到全部的服務(wù) confirm 成功兑凿。

TCC-Transaction 是一種開(kāi)源的 TCC 型事務(wù)的實(shí)現(xiàn)凯力,源代碼在 Github 可以找到茵瘾,內(nèi)部提供一個(gè)基于 dubbo 的例子。事實(shí)上咐鹤,TCC-Transaction 并不依賴(lài)具體的 RPC 框架拗秘,用 dubbo 只是為演示例子的方便。

Dubbo-sample 整體流程

TCC-Transaction 的源碼用 maven 管理慷暂,其中有一個(gè) tcc-transaction-dubbo-sample 的子模塊,跑 demo 之前需要提前執(zhí)行在 src/main/dbscripts 中的數(shù)據(jù)庫(kù)腳本晨雳。dubbo-sample 模擬的是一個(gè)經(jīng)典的訂單購(gòu)物扣款的例子行瑞,其中包含的服務(wù)有:

  • order 服務(wù):負(fù)責(zé)發(fā)起下單操作
  • capital 服務(wù):管理用戶(hù)的資金賬戶(hù),對(duì)外提供資金扣款的操作
  • redpacket 服務(wù) : 管理用戶(hù)的紅包賬戶(hù)餐禁,對(duì)外提供紅包扣款的操作

整個(gè)流程是這樣的:order 服務(wù)創(chuàng)建訂單血久,然后調(diào)用 capital 服務(wù)請(qǐng)求扣除資金賬戶(hù)金額,再調(diào)用 redpacket 服務(wù)請(qǐng)求扣除紅包賬戶(hù)余額帮非,當(dāng)資金賬戶(hù)和紅包賬戶(hù)余額在 try 階段都成功后氧吐,order 服務(wù)開(kāi)始執(zhí)行 confirm 方法把訂單置為成功,同時(shí)調(diào)用 capital 和 redpakcet 服務(wù)把轉(zhuǎn)賬訂單置為成功末盔。

Zookeeper 與 Dubbo

dubbo 的啟動(dòng)需要一個(gè)注冊(cè)中心筑舅,源碼中的例子中使用 zookeeper 作為注冊(cè)中心,所以在啟動(dòng)例子之前需要先下載并啟動(dòng) zookeeper . zookeeper 可以在 Apache 官網(wǎng)下載下來(lái)陨舱,解壓之后將 confg 下的 zoo_sample.cfg 重命名為 zoo.cfg 后(即使用默認(rèn)配置)翠拣,通過(guò)啟動(dòng)腳本 bin/zkServer.sh start 啟動(dòng) zookeeper 即可。由于 zookeeper 默認(rèn)監(jiān)聽(tīng) 2181 端口游盲,要保證此端口不被其他程序占用误墓。

之后需要在 IDE 中配置三個(gè)Tomcat,分別啟動(dòng) tcc-transaction-dubbo-capital益缎、tcc-transaction-dubbo-redpacket谜慌、tcc-transaction-dubbo-order .

啟動(dòng)后可按提示模擬支付請(qǐng)求,比如如下界面莺奔,可輸入具體金額然后執(zhí)行相應(yīng)的支付流程:

源碼導(dǎo)讀

在 order 的 controller 層接受頁(yè)面上用戶(hù)發(fā)起的下單和支付請(qǐng)求欣范,發(fā)起 TCC 事務(wù)的代碼為makePayment

paymentService.makePayment(order, redPacketPayAmount, order.getTotalAmount().subtract(redPacketPayAmount));

在 makePayment 方法內(nèi)部是 TCC 的實(shí)現(xiàn)邏輯,包括 try令哟、confirm熙卡、cancel 方法,并通過(guò) @Compensable 注解的形式告訴 TCC-Transaction 框架如何找到這三個(gè)方法:

@Compensable(confirmMethod = "confirmMakePayment", cancelMethod = "cancelMakePayment")
@Transactional
public void makePayment(Order order, BigDecimal redPacketPayAmount, BigDecimal capitalPayAmount) {
    System.out.println("order try make payment called.time seq:" + DateFormatUtils.format(Calendar.getInstance(), "yyyy-MM-dd HH:mm:ss"));

    order.pay(redPacketPayAmount, capitalPayAmount);
    orderRepository.updateOrder(order);

    String result = capitalTradeOrderService.record(buildCapitalTradeOrderDto(order));
    String result2 = redPacketTradeOrderService.record(buildRedPacketTradeOrderDto(order));
}

同理励饵,在 capital 和 redpacket 服務(wù)中出現(xiàn) @Compensable 注解的地方同樣實(shí)現(xiàn)了 try驳癌、confirm、cancel方法役听。通過(guò)斷點(diǎn)調(diào)試的方法颓鲜,可以觀(guān)察出三個(gè)服務(wù)的執(zhí)行順序表窘。

總結(jié)

通過(guò) tcc-transaction 中的例子,可以初步體驗(yàn) TCC 型事務(wù)的實(shí)現(xiàn)邏輯甜滨,作為使用方需要通過(guò) tcc-transaction 提供的注解來(lái)標(biāo)記相應(yīng)的 try乐严、confirm、cancel 方法衣摩。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末昂验,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子艾扮,更是在濱河造成了極大的恐慌既琴,老刑警劉巖,帶你破解...
    沈念sama閱讀 217,542評(píng)論 6 504
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件泡嘴,死亡現(xiàn)場(chǎng)離奇詭異甫恩,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī)酌予,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,822評(píng)論 3 394
  • 文/潘曉璐 我一進(jìn)店門(mén)磺箕,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人抛虫,你說(shuō)我怎么就攤上這事松靡。” “怎么了建椰?”我有些...
    開(kāi)封第一講書(shū)人閱讀 163,912評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵击困,是天一觀(guān)的道長(zhǎng)。 經(jīng)常有香客問(wèn)我广凸,道長(zhǎng)阅茶,這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,449評(píng)論 1 293
  • 正文 為了忘掉前任谅海,我火速辦了婚禮脸哀,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘扭吁。我一直安慰自己撞蜂,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,500評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布侥袜。 她就那樣靜靜地躺著蝌诡,像睡著了一般。 火紅的嫁衣襯著肌膚如雪枫吧。 梳的紋絲不亂的頭發(fā)上浦旱,一...
    開(kāi)封第一講書(shū)人閱讀 51,370評(píng)論 1 302
  • 那天,我揣著相機(jī)與錄音九杂,去河邊找鬼颁湖。 笑死宣蠕,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的甥捺。 我是一名探鬼主播抢蚀,決...
    沈念sama閱讀 40,193評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼镰禾!你這毒婦竟也來(lái)了皿曲?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 39,074評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤吴侦,失蹤者是張志新(化名)和其女友劉穎屋休,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體妈倔,經(jīng)...
    沈念sama閱讀 45,505評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡博投,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,722評(píng)論 3 335
  • 正文 我和宋清朗相戀三年绸贡,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了盯蝴。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 39,841評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡听怕,死狀恐怖捧挺,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情尿瞭,我是刑警寧澤闽烙,帶...
    沈念sama閱讀 35,569評(píng)論 5 345
  • 正文 年R本政府宣布,位于F島的核電站声搁,受9級(jí)特大地震影響黑竞,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜疏旨,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,168評(píng)論 3 328
  • 文/蒙蒙 一很魂、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧檐涝,春花似錦遏匆、人聲如沸。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,783評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)。三九已至窃植,卻和暖如春帝蒿,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背巷怜。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 32,918評(píng)論 1 269
  • 我被黑心中介騙來(lái)泰國(guó)打工陵叽, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留狞尔,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 47,962評(píng)論 2 370
  • 正文 我出身青樓巩掺,卻偏偏與公主長(zhǎng)得像偏序,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子胖替,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,781評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容

  • 通過(guò)之前的幾篇文章我相信您已經(jīng)搭建好了運(yùn)行環(huán)境研儒,本次的項(xiàng)目實(shí)戰(zhàn)是依照happylifeplat-tcc-demo項(xiàng)...
    dromara閱讀 1,092評(píng)論 0 3
  • 本人最近學(xué)習(xí)了一下微服務(wù)下數(shù)據(jù)一致性的特點(diǎn),總結(jié)了下目前的保障微服務(wù)下數(shù)據(jù)一致性的幾種實(shí)現(xiàn)方式如下独令,以備后查端朵。此篇...
    SawyerZhou閱讀 31,957評(píng)論 11 66
  • Spring Cloud為開(kāi)發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見(jiàn)模式的工具(例如配置管理,服務(wù)發(fā)現(xiàn)燃箭,斷路器冲呢,智...
    卡卡羅2017閱讀 134,656評(píng)論 18 139
  • 林中有兩條路 人們總是走著一條 懷念著另一條 但愿有無(wú)數(shù)個(gè)平行時(shí)空 容納我們想象過(guò)的各種意外 如果有 我會(huì)昂首挺胸...
    水果獵人的彪悍生活閱讀 186評(píng)論 0 3
  • 最難忘, 你一眼望過(guò)來(lái)時(shí)的脈脈含情…… 我便嬌羞的低下頭招狸, 任憑火熱的心情把雙頰燙紅敬拓! 最難忘, 你偷偷遞過(guò)來(lái)的紙...
    夢(mèng)艷兒閱讀 173評(píng)論 0 3