1. 什么是事務(wù)
由一組操作構(gòu)成的可靠、 獨(dú)立的工作單元。
事務(wù)具有以下特點(diǎn):
?Atomicity(原子性)
?Consistency(一致性)
?Isolation(隔離性)
?Durability(持久性)
成都創(chuàng)新互聯(lián)公司專(zhuān)注于中大型企業(yè)的成都做網(wǎng)站、網(wǎng)站設(shè)計(jì)、外貿(mào)營(yíng)銷(xiāo)網(wǎng)站建設(shè)和網(wǎng)站改版、網(wǎng)站營(yíng)銷(xiāo)服務(wù),追求商業(yè)策劃與數(shù)據(jù)分析、創(chuàng)意藝術(shù)與技術(shù)開(kāi)發(fā)的融合,累計(jì)客戶(hù)上1000家,服務(wù)滿(mǎn)意度達(dá)97%。幫助廣大客戶(hù)順利對(duì)接上互聯(lián)網(wǎng)浪潮,準(zhǔn)確優(yōu)選出符合自己需要的互聯(lián)網(wǎng)運(yùn)用,我們將一直專(zhuān)注品牌網(wǎng)站建設(shè)和互聯(lián)網(wǎng)程序開(kāi)發(fā),在前進(jìn)的路上,與客戶(hù)一起成長(zhǎng)!
2.事務(wù)的一致性
單體應(yīng)用可以在數(shù)據(jù)庫(kù)的事物管理器中獲得強(qiáng)一致性,這種本地事物可靠簡(jiǎn)單。
而在微服或者SOA的場(chǎng)景下,我們的本地事物就不作用了。對(duì)于分布式系統(tǒng) Google 提出 CAP定理 ,
分布式的事物只能同時(shí)擁有以下三項(xiàng)中的兩個(gè):
?Consistency(一致性): 所有 用戶(hù)看到一致的數(shù)據(jù)。
?Availability(可用性): 總能找 到一個(gè)可用的數(shù)據(jù)復(fù)本。
?Tolerance to Network Partition(分區(qū)容忍性): 即使 在系統(tǒng)被分區(qū)的情況下,仍然滿(mǎn)足上述兩點(diǎn)。
分布式系統(tǒng)的事物無(wú)法做到強(qiáng)一致性,只能做到最終一致性。
3.常見(jiàn)分布式事物的處理方案
事物消息,簡(jiǎn)單的說(shuō)就是消息投遞成功,你本地的數(shù)據(jù)庫(kù)事物肯定提交成功,消息投遞失敗你本地事物也肯定提交失敗。相當(dāng)于你投遞消息和操作數(shù)據(jù)庫(kù)是綁定在一起的,兩者是在同一個(gè)事物中。
非事物消息,簡(jiǎn)單的說(shuō)就是消息投遞成功,本地?cái)?shù)據(jù)庫(kù)事物不一定執(zhí)行成功。
而現(xiàn)有的開(kāi)源的MQ框架 大多數(shù)是不支持 事物消息的,也沒(méi)有和本地事物進(jìn)行配合。
RocketMQ 好像實(shí)現(xiàn)了這個(gè)事物消息功能,有興趣的同學(xué)可以去看看。
先來(lái)看個(gè)案例:
假設(shè)我有一個(gè) 文章微服 負(fù)責(zé)發(fā)布文章,查詢(xún)文章列表等,還有一個(gè) 用戶(hù)微服 保持用戶(hù)的一些基本信息,如:用戶(hù)發(fā)文章的篇數(shù)等。
現(xiàn)在發(fā)文章在 文章微服,而用戶(hù)的發(fā)文篇數(shù)在 用戶(hù)微服。這種情況下我們?cè)趺幢WC 發(fā)文的計(jì)數(shù) 不會(huì)多也不會(huì)少,保證其的一致性的呢?
大家先來(lái)看一段代碼:
假設(shè)這是 文章微服 發(fā)文代碼:
@Transactional
public void saveArticle(Article article){
try{
//保存文章
articleDao.saveArticle(article);
MqEvent saveArticleEvent = new MqEvent();
//消息ID
saveArticleEvent.setMsgId(UUIDUtil.mongoObjectId());
//發(fā)送保存文章 事件個(gè)用戶(hù)服務(wù)
sender.sendAddArticleMqEvent(saveArticleEvent);
}catch (Exception e){
//拋異常 讓事務(wù)回滾
throw new RuntimeException();
}
}
}
看起來(lái)很正常呀!沒(méi)有什么問(wèn)題! 我們來(lái)列舉一下可能會(huì)出現(xiàn)的情況;
保存文章正常,MQ發(fā)送也正常,好萬(wàn)事大吉,數(shù)據(jù)都正常。
保存文章正常,MQ發(fā)送失敗,拋異常。這時(shí)數(shù)據(jù)回滾,雖然出了點(diǎn)問(wèn)題 但是數(shù)據(jù)正常。這也沒(méi)問(wèn)題。
文章保存失敗,這時(shí)肯定拋異常,MQ發(fā)送走不到,這時(shí)也是正常的。
雖然這種做法看起來(lái)沒(méi)有什么問(wèn)題,但其實(shí)是有問(wèn)題的。
為了解決這個(gè)問(wèn)題,我們需要 增加一個(gè)本地事件表,專(zhuān)門(mén)存放 MQ事件 ,有定時(shí)器輪訓(xùn)去發(fā)送MQ消息,發(fā)送成功后做標(biāo)記,或者刪除。很多MQ都會(huì)有 消息回執(zhí)的。當(dāng)成功投遞到消息隊(duì)列是 就會(huì)得到回執(zhí)。
于是我們的代碼應(yīng)該改成這樣:
@Transactional
public void saveArticle(Article article) {
articleDao.saveArticle(article);
MqEvent saveArticleEvent = new MqEvent();
//消息ID
saveArticleEvent.setMsgId(UUIDUtil.mongoObjectId());
// 保存事件到事件表
mqEventDao.addMQEvent(saveArticleEvent);
}
這樣在本地事物的強(qiáng)一致性下可以保證,發(fā)文的同事插入發(fā)文事件。
說(shuō)說(shuō) 用戶(hù)微服那邊的處理 , 用戶(hù)微服也應(yīng)該有一個(gè)這樣的事件表,保存接收的事件,通過(guò)輪訓(xùn)等方式處理這些事件,只有成功的接收了事件,事件才能從MQ隊(duì)列里面消失。MQ在消費(fèi)消息的時(shí)候如果遇到異常會(huì)重新將消失重新發(fā)回到隊(duì)列中,很多MQ具有這個(gè)特性。
細(xì)心的同學(xué)可能會(huì)想到我同一個(gè)事件消息投遞了兩次怎么辦?這就涉及冪等性的設(shè)計(jì)了,看到上面的消息ID沒(méi)? 這就是為冪等性設(shè)計(jì)的 唯一ID;當(dāng)用戶(hù)微服收到兩個(gè)消息ID是一樣的時(shí)候,丟棄掉一個(gè)。
我們的微服系統(tǒng) 只要涉及 增 刪 改 的操作都應(yīng)該通過(guò)可靠事件進(jìn)行操作,而不能直接通過(guò) REST 接口,去操作,也不能直接的發(fā)送事件去操作。對(duì)于消防端,要做好冪等性的處理??煽渴录幚砦⒎氖挛锼闶潜容^靠譜的做法,2pc,3pc ,Tcc 在微服事物處理這一塊,基本上起不了什么作用。
本人的理解大概是這樣,歡迎大家提出疑問(wèn)。
針對(duì)于上面所涉及到的知識(shí)點(diǎn)我總結(jié)出了有1到5年開(kāi)發(fā)經(jīng)驗(yàn)的程序員在面試中涉及到的絕大部分架構(gòu)面試題及答案做成了文檔和架構(gòu)視頻資料免費(fèi)分享給大家(包括Dubbo、redis、Netty、zookeeper、Spring cloud、分布式、高并發(fā)等架構(gòu)技術(shù)資料),希望能幫助到您面試前的復(fù)習(xí)且找到一個(gè)好的工作,也節(jié)省大家在網(wǎng)上搜索資料的時(shí)間來(lái)學(xué)習(xí),也可以關(guān)注我一下以后會(huì)有更多干貨分享。
當(dāng)前文章:分布式事務(wù)處理方案,微服事務(wù)處理方案
瀏覽地址:http://www.rwnh.cn/article46/jcjghg.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供虛擬主機(jī)、響應(yīng)式網(wǎng)站、手機(jī)網(wǎng)站建設(shè)、網(wǎng)站改版、網(wǎng)站維護(hù)、定制開(kāi)發(fā)
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶(hù)投稿、用戶(hù)轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來(lái)源: 創(chuàng)新互聯(lián)