高并发资金交易系统设计方案—百亿双十一、微信红包背后的技术架构
21CTO社區(qū)導(dǎo)讀 :
今天帶來(lái)的是一個(gè)長(zhǎng)篇文章。主要講解高可用的互聯(lián)網(wǎng)交易系統(tǒng)架構(gòu),包括雙十一、支付寶&微博紅包技術(shù)架構(gòu),以及微信紅包的技術(shù)架構(gòu),希望能給各位提供價(jià)值。
概述
話說(shuō)每逢雙十一節(jié)或春節(jié)等節(jié)假日,對(duì)大家來(lái)講是最歡樂(lè)的日子,可以在微信群中收發(fā)紅包,此外今年微信還推出了面對(duì)面紅包,讓大家拜年時(shí)可直接收發(fā),對(duì)于用戶來(lái)講很爽也很方便。但對(duì)于技術(shù)架構(gòu)側(cè)的考量,這使得微信紅包的收發(fā)數(shù)據(jù)成幾何倍數(shù)上升,處理的復(fù)雜度也增加了很多。
2017年微信紅包發(fā)送量最大的時(shí)間段是除夕夜,達(dá)到了142億個(gè)。如此大規(guī)模、高并發(fā)、高峰值的業(yè)務(wù)場(chǎng)景,怕是在美帝互聯(lián)網(wǎng)的技術(shù)團(tuán)隊(duì),包括EBay、Amazon等也無(wú)法想象,在這種巨大的流量與并發(fā)后面,需要什么樣級(jí)別的技術(shù)架構(gòu)支撐?當(dāng)達(dá)百億級(jí)別的資金交易規(guī)模時(shí),我們?cè)撛鯓觼?lái)保證系統(tǒng)的并發(fā)性能和交易安全?
當(dāng)今中國(guó)的電子商務(wù)平臺(tái),有兩個(gè)場(chǎng)景稱(chēng)得上億級(jí)以上的并發(fā)量:一個(gè)是阿里的雙十一,一個(gè)是微信的紅包,都是在一個(gè)單位時(shí)間達(dá)到億萬(wàn)以以上的請(qǐng)求負(fù)載。
阿里交易系統(tǒng)與紅包體系架構(gòu)
我們先來(lái)回顧一下阿里『雙十一』的業(yè)務(wù)場(chǎng)景。
中國(guó)移動(dòng)互聯(lián)網(wǎng)的完全普及,使得電商業(yè)務(wù)每年都幾百倍甚至更高倍速的增長(zhǎng),包括農(nóng)村用戶也對(duì)電商逐漸認(rèn)可。電商巨頭們每年創(chuàng)造出的新節(jié)日,無(wú)論是『雙十一』還是『雙十二』,都最大化點(diǎn)染了用戶的消費(fèi)欲望,人們?cè)谶@一天瘋狂下單和參與秒殺活動(dòng),期望用最便宜的價(jià)格購(gòu)買(mǎi)到心儀的商品,這導(dǎo)致一些平臺(tái)后端商品超賣(mài),服務(wù)器負(fù)載過(guò)高拒絕服務(wù)等問(wèn)題頻頻出現(xiàn)。
網(wǎng)站以及各個(gè)客戶端帶來(lái)巨大的流量對(duì)后端技術(shù)架構(gòu)的要求越來(lái)越苛刻。比如某個(gè)電商網(wǎng)站宕機(jī),對(duì)用戶和訂單的損失是無(wú)法估量的,就算老板拿著把刀放在桌子也無(wú)法根本上解決問(wèn)題,關(guān)鍵還是看技術(shù)團(tuán)隊(duì)的架構(gòu)、能力,同時(shí)也包括軟硬件等相關(guān)資源投入。
我們拿剛剛過(guò)去的2016年『雙十一』來(lái)講,阿里巴巴&淘寶網(wǎng)的當(dāng)天交易額為1207億元,而2015年的數(shù)字為912.17億元,成交額足足增長(zhǎng)了32.32%。1207億的巨大交易量,背后是阿里巴巴的云平臺(tái)提供的技術(shù)支撐。馬云同志說(shuō),所有的創(chuàng)新都是被逼出來(lái)的,不管是被他逼,還是用戶逼,阿里的技術(shù)平臺(tái)就是這樣被倒逼了出來(lái)。
在2016年的阿里技術(shù)棧中,和往年比技術(shù)平臺(tái)也發(fā)生了很大變化,一部分變成了數(shù)據(jù)挖掘,有一部分演變了人工智能計(jì)算。除了傳統(tǒng)的Web后端,還增加了直播平臺(tái)流媒體應(yīng)用。
視頻直播系統(tǒng)與Web系統(tǒng)有相同也有不同之處,來(lái)看大部分視頻直播平臺(tái)的存在著一些技術(shù)瑕疵。如下圖示:
以上的問(wèn)題在后端需要實(shí)施不同的技術(shù)解決方案,需要進(jìn)行日志采集實(shí)時(shí)監(jiān)控,比如對(duì)終端類(lèi)、后臺(tái)類(lèi)以及CDN的運(yùn)行日志進(jìn)行分析等。
阿里的直播端,視頻傳播使用了H.265編碼壓縮。H265編碼在壓縮比以及清晰度上要超過(guò)目前主流的H.264標(biāo)準(zhǔn)。阿里云使用了自己的ApsaraVideo平臺(tái)完成了這些任務(wù)。這個(gè)APsaraVideo提供了以下子系統(tǒng):
1、客戶端推流sdk
2、云端OpenAPI
3、CDN分發(fā)
阿里通過(guò)上面一系列產(chǎn)品,將推流、轉(zhuǎn)碼、分發(fā)、播放等問(wèn)題全部解決。
關(guān)于流量的負(fù)載均衡,阿里雙十一采用了雙專(zhuān)線的CDN,20T以上的帶寬,這樣可支撐1000萬(wàn)人同時(shí)在線下單和觀看視頻直播。
在視頻的傳播壓縮,阿里率先使用H.265編碼壓縮。H265在壓縮比以及清晰度上要超過(guò)目前主流采用的H.264標(biāo)準(zhǔn)。
數(shù)據(jù)存儲(chǔ)
在手機(jī)淘寶中的用戶關(guān)注信息存儲(chǔ)在云服務(wù)器的Redis中,訂單等持久化數(shù)據(jù)保存在RDS(阿里云的MySQL集群)中。
在阿里的電商平臺(tái),從雙11節(jié)開(kāi)始后,每筆交易隊(duì)列都是通過(guò)消息中間件系統(tǒng)來(lái)做流轉(zhuǎn),包括消息發(fā)布訂閱,狀態(tài),定時(shí),監(jiān)控報(bào)警等消息服務(wù)——這個(gè)消息系統(tǒng)是阿里自研的產(chǎn)品稱(chēng)為AliwareMQ(內(nèi)核為RocketMQ),當(dāng)然我們也可以使用ActiveMQ,RabbitMQ等開(kāi)源軟件。
商品支付成功后的訂單完成后,發(fā)給各個(gè)物流公司的訂單數(shù)據(jù)采用了PetaData的產(chǎn)品,支持OLTP和OLAP。不需要把一份數(shù)據(jù)進(jìn)行多次復(fù)制,然后再進(jìn)行數(shù)據(jù)分析,免去在線與離線數(shù)據(jù)倉(cāng)庫(kù)之間海量數(shù)據(jù)的傳輸和加載時(shí)間,實(shí)現(xiàn)在線分析決策。
支付寶與微博紅包架構(gòu)
支付寶紅包通過(guò)性能較高的分布式文件系統(tǒng)保證用戶數(shù)據(jù)的高可靠與高可用。分布式文件系統(tǒng)需要考慮多機(jī)集群之間的一致性與效率問(wèn)題。
新浪微博紅包在2017年除夕的發(fā)搶數(shù)量也達(dá)到了16億個(gè)以上,參與的用戶有不同的類(lèi)型與地域,對(duì)架構(gòu)、監(jiān)控與性能優(yōu)化具有一定的挑戰(zhàn)。除了通過(guò)CDN,分布式圖片系統(tǒng)等處理性能問(wèn)題,另外還有系統(tǒng)底層的內(nèi)核進(jìn)行優(yōu)化,安全修復(fù)以及軟硬件擴(kuò)容。
微信紅包技術(shù)架構(gòu)
2017年1月28日,正值農(nóng)歷正月初一,騰訊微信平臺(tái)公布了在除夕當(dāng)天用戶收發(fā)微信紅包的數(shù)量達(dá)到142億個(gè),收發(fā)峰值為76萬(wàn)/秒。
2015年的春節(jié)數(shù)據(jù):除夕搖一搖總次數(shù)110億次,峰值1400萬(wàn)次/秒,8.1億次每分鐘,微信紅包收發(fā)達(dá)10.1億次,除夕紅包為1.2億個(gè)。
2014年的紅包峰值每分鐘被拆開(kāi)紅包數(shù)量為2.5萬(wàn)個(gè)。我們可以看到,2017年是2014峰值的5000倍,紅包數(shù)量達(dá)到百億級(jí)別。
保障并發(fā)性能與資金交易安全,帶來(lái)了超級(jí)挑戰(zhàn)。
微信技術(shù)平臺(tái)總結(jié)過(guò)紅包技術(shù)有三大難點(diǎn):
快——如何保證用戶快速搖到紅包?
準(zhǔn)——如何保證搖到的紅包能成功拆開(kāi)?
穩(wěn)——如何保證拆開(kāi)的紅包能分享出去?
微信紅包技術(shù)結(jié)合電商平臺(tái)設(shè)計(jì)的秒殺系統(tǒng)之基礎(chǔ),采用了以下技術(shù)解決方案:
-
SET集合化
-
串行化請(qǐng)求隊(duì)列
-
雙維度分拆數(shù)據(jù)庫(kù)表
通過(guò)以上方案設(shè)計(jì),形成了自己的高并發(fā)、資金安全系統(tǒng)解決方案。
我們先回到使用場(chǎng)景中。
當(dāng)大量的微信用戶在同一時(shí)間搖紅包,就會(huì)產(chǎn)生每秒千萬(wàn)級(jí)請(qǐng)求。需要對(duì)請(qǐng)求疏導(dǎo)分流。
如果不進(jìn)行負(fù)載均衡,分離流量,直接到達(dá)后端服務(wù)器,多大的服務(wù)器集群都會(huì)被如此大的流量負(fù)何過(guò)大而崩潰。
我們來(lái)看除夕當(dāng)天后臺(tái)監(jiān)控?cái)?shù)據(jù)曲線便能說(shuō)明一切。如下圖示:
各位可以看到,在前臺(tái)紅包重重的分流減壓下,后端服務(wù)器負(fù)載仍然瞬間飆升幾十倍甚至更高。
紅包產(chǎn)品特點(diǎn)
微信紅包,特別是群里的紅包,我們稱(chēng)之為微信群紅包。這個(gè)東西的產(chǎn)品形態(tài)上像極了電商平臺(tái)上的商品“秒殺”活動(dòng)。
舉個(gè)場(chǎng)景栗子,某位土豪在微信群里發(fā)一個(gè)紅包,這相當(dāng)于商品“秒殺”商品上架。然后群里的其它人開(kāi)始瘋狂搶之,這個(gè)場(chǎng)面相當(dāng)于“秒殺”的庫(kù)存查詢(xún)——看看還有沒(méi)有貨。當(dāng)用戶搶到紅包后,紅包在眼前晃呀晃時(shí),食指輕點(diǎn)開(kāi)拆紅包的操作,它對(duì)應(yīng)了“秒殺”活動(dòng)中點(diǎn)擊秒殺按鈕動(dòng)作。
有的時(shí)候,點(diǎn)擊出紅包會(huì)提示網(wǎng)絡(luò)出問(wèn)題,則是秒殺時(shí)你的庫(kù)存隊(duì)列沒(méi)有別人的快,微信給了一個(gè)友好的提示罷了。
這點(diǎn)上,和我們?cè)?2306網(wǎng)站搶火車(chē)票是同樣的道理。
且不急下定論,微信紅包在產(chǎn)品形態(tài)上和商品秒殺相比,也有著自己的一些特點(diǎn)和難點(diǎn)。來(lái)看都是哪兩點(diǎn):
第一:微信紅包產(chǎn)品與商品“秒殺”,數(shù)量大&并發(fā)量更高。
為啥這么說(shuō)?各位看,當(dāng)土豪在群里發(fā)了一個(gè)紅包,相當(dāng)在網(wǎng)站發(fā)布了一次秒殺活動(dòng)對(duì)吧?有10萬(wàn)個(gè)微信群里的人在同一時(shí)刻發(fā)起紅包請(qǐng)求,也就是說(shuō)在瞬息之間,時(shí)時(shí)存在10萬(wàn)個(gè)“秒殺”活動(dòng)發(fā)布出來(lái)。
接下來(lái),10萬(wàn)個(gè)微信群里的用戶同時(shí)開(kāi)搶紅包,便產(chǎn)生了海量的并發(fā)查詢(xún)請(qǐng)求。
第二:微信紅包產(chǎn)品需要極高的安全級(jí)別。
紅包的收發(fā),本質(zhì)上就是資金的交易。微信紅包本身是微信支付(底層支撐是財(cái)付通平臺(tái)在干活)的一個(gè)商戶,由微信紅包來(lái)提供資金流轉(zhuǎn)服務(wù)。
群里土豪發(fā)紅包時(shí),相當(dāng)使用微信紅包商戶名義向微信支付申請(qǐng)購(gòu)買(mǎi)了一筆“錢(qián)”,而收貨地址是當(dāng)前的微信群。
當(dāng)土豪支付成功后,紅包就“發(fā)貨”到該微信群中,群里的人拆開(kāi)紅包后,微信紅包商戶提供將“錢(qián)”轉(zhuǎn)入拆紅包成功用戶的微信零錢(qián)服務(wù)。
由于是和錢(qián)相關(guān)的交易業(yè)務(wù),它比普通商品“秒殺”活動(dòng)有更高的業(yè)務(wù)嚴(yán)密和安全級(jí)別要求,與銀行的在線交易有過(guò)之而無(wú)不及。
而電商平臺(tái)上“秒殺”商品由商家提供的,庫(kù)存是被事先預(yù)設(shè)好的,即使出現(xiàn)“超賣(mài)”(即實(shí)際被搶的商品數(shù)量比計(jì)劃的庫(kù)存多)、“少賣(mài)”(即實(shí)際被搶的商戶數(shù)量比計(jì)劃的庫(kù)存少)時(shí)也有辦法解決,比如和用戶商量、不發(fā)貨或者做虛假繁榮,BD小伙伴對(duì)外吹吹牛也就算了。
對(duì)于微信紅包產(chǎn)品就非常非常嚴(yán)謹(jǐn),一塊錢(qián)也不能多,一分錢(qián)也不能少,絕不能有半點(diǎn)錯(cuò)誤。比如群里土豪發(fā)249元的紅包絕對(duì)不可以被拆出250塊錢(qián),用戶發(fā)了100塊錢(qián)未被領(lǐng)取,在24小時(shí)的退還期內(nèi)要精確地退還給原路——發(fā)紅包的用戶。
第三:微信紅包與接口效率。
微信紅包和微信支付與支付寶的最大區(qū)別是,自己不做金融(余額寶業(yè)務(wù)),所有的支付操作均與用戶綁定的銀行卡銀行接口交互。因此,與銀行接口的安全,效率性能等需要有嚴(yán)密的設(shè)計(jì)。
微信紅包架構(gòu)難點(diǎn)
上面幾次說(shuō),紅包架構(gòu)與秒殺系統(tǒng)有著些許相似。我們先重溫下典型的秒殺系統(tǒng)架構(gòu)設(shè)計(jì),來(lái)看下圖所示。
這個(gè)系統(tǒng)可謂是經(jīng)典。它由網(wǎng)關(guān)代理接入層、商業(yè)邏輯服務(wù)層、緩存與實(shí)體存儲(chǔ)層等構(gòu)成。其中:
代理層,可使用Nginx或Varnish來(lái)處理請(qǐng)求接入,Web服務(wù)器使用Nginx承載主要的業(yè)務(wù)邏輯,Cache層如使用Memcached或Redis來(lái)緩存庫(kù)存數(shù)量、數(shù)據(jù)庫(kù),使用MySQL/MariaDB集群中,做數(shù)據(jù)庫(kù)的持久化存儲(chǔ)。
業(yè)務(wù)邏輯層可以是多個(gè)Nginx的集群,Cache層可以是多臺(tái)機(jī)器組成的大的內(nèi)存池,包括數(shù)據(jù)庫(kù)緩存,OpCode緩存等不同類(lèi)型。
從數(shù)據(jù)庫(kù)側(cè)闡述,數(shù)據(jù)庫(kù)可以根據(jù)不同業(yè)務(wù)或日期進(jìn)行分表分庫(kù),讀寫(xiě)分離等組成一個(gè)負(fù)載平衡的集群。
在秒殺業(yè)務(wù)中,表現(xiàn)就是一個(gè)秒殺活動(dòng)對(duì)應(yīng)Inodb中的一條庫(kù)存。當(dāng)某個(gè)用戶開(kāi)始點(diǎn)秒殺動(dòng)作時(shí),系統(tǒng)的主要邏輯在于數(shù)據(jù)庫(kù)中對(duì)庫(kù)存的操作上。
這樣,在數(shù)據(jù)庫(kù)的事務(wù)中包含以下3個(gè)步驟:
1、鎖定庫(kù)存LOCK
2、插入秒殺記錄 INSERT
3、更新庫(kù)存 UPDATE
可以肯定的是,所有的大小電商網(wǎng)站均是依此套路。詳解解釋如下:
首先鎖定庫(kù)存為避免并發(fā)請(qǐng)求時(shí)出現(xiàn)“超賣(mài)”的情形,同時(shí)下單的用戶需要等待此事務(wù)執(zhí)行完后再執(zhí)行下一個(gè)事務(wù)。
在數(shù)據(jù)庫(kù)的事務(wù)完整性要求,這三步需要在一個(gè)時(shí)間段一個(gè)系列中完成,當(dāng)中間有一處錯(cuò)誤發(fā)生即進(jìn)行回滾,相當(dāng)于放棄當(dāng)前事務(wù),若無(wú)錯(cuò)誤發(fā)生,則整體事務(wù)的執(zhí)行順利被完成。
商品庫(kù)存在數(shù)據(jù)庫(kù)中記為一行,大量的用戶同時(shí)點(diǎn)擊購(gòu)買(mǎi)同一件SKU時(shí),第一個(gè)到達(dá)數(shù)據(jù)庫(kù)的請(qǐng)求就鎖住了這行庫(kù)存記錄。
在第一個(gè)事務(wù)完成提交之前這個(gè)鎖一直被第一個(gè)請(qǐng)求占用,后面的所有請(qǐng)求就需要排隊(duì)等待。
同時(shí)參與“秒殺”的用戶越多,并發(fā)進(jìn)數(shù)據(jù)庫(kù)的排隊(duì)請(qǐng)求就越多,如同旅行時(shí)去衛(wèi)生間,隊(duì)形被排的很長(zhǎng)。
所以并發(fā)請(qǐng)求搶鎖的事備,成為典型的“秒殺”或搶購(gòu)類(lèi)系統(tǒng)的設(shè)計(jì)難點(diǎn)。
在微信紅包系統(tǒng)的設(shè)計(jì)上,事務(wù)級(jí)操作量級(jí)更大。即便在普通的時(shí)間下,每一時(shí)刻都會(huì)有數(shù)以萬(wàn)計(jì)的微信群在同一時(shí)間端發(fā)起紅包,就是引發(fā)幾萬(wàn)并發(fā)請(qǐng)求搶鎖同時(shí)在排隊(duì),這使得數(shù)據(jù)庫(kù)的壓力比普通單個(gè)商品“庫(kù)存”被鎖放大更多倍。
解決高并發(fā)的常用解決方案
常見(jiàn)商品秒殺活動(dòng),解決高并發(fā)問(wèn)題,可以有如下幾種解決方案:
一,內(nèi)存數(shù)據(jù)庫(kù)替代數(shù)據(jù)庫(kù)事務(wù)
如上圖所示,我們把實(shí)時(shí)扣庫(kù)存的行為上移到內(nèi)存數(shù)據(jù)庫(kù)或者叫緩存層來(lái)干活,緩存操作完畢后再返回服務(wù)器成功,通過(guò)隊(duì)列異步返回到數(shù)據(jù)庫(kù)進(jìn)行持久化。
使用內(nèi)存操作替代磁盤(pán)操作,會(huì)明顯提升并發(fā)性能。但是需要注意引發(fā)的缺點(diǎn),如果在內(nèi)存操作完成,數(shù)據(jù)庫(kù)保存失敗,或內(nèi)存出現(xiàn)Crash,數(shù)據(jù)庫(kù)的存儲(chǔ)進(jìn)程不會(huì)進(jìn)行。因此,這種解決方案不適合與錢(qián)相關(guān)的交易系統(tǒng)應(yīng)用,特別是微信紅包。
二,使用樂(lè)觀鎖替代悲觀鎖
我們來(lái)回顧一下關(guān)系數(shù)據(jù)庫(kù)管理系統(tǒng)中的兩種鎖的概念。
悲觀鎖是DBMS里的一種并發(fā)控制的方法,它阻止一個(gè)事務(wù)以影響其他用戶的方式來(lái)修改數(shù)據(jù)。若一個(gè)事務(wù)執(zhí)行的操作對(duì)某行數(shù)據(jù)加了鎖,只有這個(gè)事務(wù)將鎖釋放,其他事務(wù)才能夠執(zhí)行與該鎖沖突的操作。此描述對(duì)應(yīng)于上面所說(shuō)的并發(fā)請(qǐng)求搶鎖行為。
而樂(lè)觀鎖,假設(shè)多用戶并發(fā)的事務(wù)在處理時(shí)不會(huì)彼此互相影響,各事務(wù)能夠在不產(chǎn)生鎖的情況下處理各自影響的那部分?jǐn)?shù)據(jù)。在提交數(shù)據(jù)更新之前,每個(gè)事務(wù)會(huì)先檢查在該事務(wù)讀取數(shù)據(jù)后,有沒(méi)有其他事務(wù)又修改了該數(shù)據(jù)。如果其他事務(wù)有更新的話,正在提交的事務(wù)會(huì)進(jìn)行回滾。
秒殺系統(tǒng)中,使用樂(lè)觀鎖會(huì)在庫(kù)存記錄中維護(hù)一個(gè)版本號(hào)。在更新庫(kù)存操作進(jìn)行前,先取當(dāng)前版本號(hào),在更新庫(kù)存的事務(wù)提交時(shí),檢查該版本號(hào)是否已被其他事務(wù)修改。若版本未被修改,則提交事務(wù),版本號(hào)加1。如果版本號(hào)已被其他事務(wù)修改,則回滾事務(wù),并給上層報(bào)錯(cuò)。
樂(lè)觀鎖方案解決了“并發(fā)請(qǐng)求搶鎖”的問(wèn)題,可以提高數(shù)據(jù)庫(kù)的并發(fā)處理能力。
似乎問(wèn)題被解決,使用樂(lè)觀鎖對(duì)于一般的應(yīng)用系統(tǒng)足夠,但將它應(yīng)用于微信紅包系統(tǒng)中,會(huì)引發(fā)下面幾個(gè)問(wèn)題。
如果拆紅包采用樂(lè)觀鎖,在并發(fā)搶到相同版本號(hào)的拆紅包請(qǐng)求中,只有一個(gè)人能拆紅包成功,其他的請(qǐng)求將事務(wù)回滾并返回失敗,給用戶報(bào)錯(cuò),用戶完全不可能接受這種體驗(yàn)。
采用樂(lè)觀鎖將會(huì)導(dǎo)致第一時(shí)間同時(shí)拆紅包的用戶有一部分直接返回失敗,反而那些『網(wǎng)慢手慢』的,會(huì)有可能因?yàn)椴l(fā)減小后拆紅包成功,這也會(huì)帶來(lái)用戶體驗(yàn)上的負(fù)面影響。
如果采用樂(lè)觀鎖的方式,會(huì)帶來(lái)大數(shù)量的無(wú)效更新請(qǐng)求、事務(wù)回滾,給DB造成不必要的額外壓力。
有鑒于以上原因,微信紅包系統(tǒng)也不能用樂(lè)觀鎖的方式解決并發(fā)搶鎖問(wèn)題。
微信紅包系統(tǒng)的高并發(fā)解決方案
我們綜合上面的一系列分析,微信紅包針對(duì)相應(yīng)的技術(shù)難點(diǎn),采用了下面幾個(gè)方案來(lái)解決高并發(fā)問(wèn)題。
1 系統(tǒng)垂直集合化
集合(SET)化,即分組進(jìn)行管理。
當(dāng)微信紅包用戶發(fā)一個(gè)紅包時(shí),微信紅包系統(tǒng)生成一個(gè)ID當(dāng)它的唯一標(biāo)識(shí),接下來(lái)針對(duì)于這個(gè)紅包的所有發(fā)、搶、拆、查詢(xún)?cè)斍榈炔僮鞫几鶕?jù)這個(gè)ID關(guān)聯(lián)。
紅包系統(tǒng)根據(jù)這個(gè)紅包ID,按一定的規(guī)則(如按ID尾號(hào)取模等),垂直上下切分。切分后,一個(gè)垂直鏈條上的邏輯服務(wù)器、服務(wù)器統(tǒng)稱(chēng)為一個(gè)SET(集合)。
這樣,每個(gè)集合間相互獨(dú)立,互相解耦,不存在任何關(guān)聯(lián)。
同一個(gè)紅包ID的所有請(qǐng)求,包括發(fā)、搶、拆、查詳情詳情等,合并在一個(gè)集合內(nèi)處理,形成高內(nèi)聚。
通過(guò)此法,系統(tǒng)將所有紅包請(qǐng)求這個(gè)巨大的洪流分散為多股小流,猶似諸侯各國(guó),互不影響,各自治理。請(qǐng)看下圖所示:
綜上所述內(nèi)容,這個(gè)方案對(duì)同時(shí)存在海量事務(wù)級(jí)操作的問(wèn)題,將海量化為微量,問(wèn)題得以解決。
2 邏輯服務(wù)層將HTTP請(qǐng)求隊(duì)化列化,解決數(shù)據(jù)庫(kù)并發(fā)
前面提到過(guò),微信紅包系統(tǒng)是個(gè)交易系統(tǒng),而數(shù)據(jù)庫(kù)操作的事務(wù)性(悲觀/樂(lè)觀鎖,回滾等特性)是不可能不用的,因此勢(shì)必會(huì)存在“并發(fā)搶鎖”的現(xiàn)象。
我們把到達(dá)數(shù)據(jù)的事務(wù)操作(拆紅包行為)的并發(fā)改為串行,由統(tǒng)一一個(gè)通道出口,就不會(huì)存在“并發(fā)搶鎖”的問(wèn)題了。
這個(gè)其實(shí)和很多電商平臺(tái),以及PUSH系統(tǒng)等原理相似。
這樣我們的策略就清晰明白了,接著來(lái)把拆紅包的事務(wù)操作串行地進(jìn)入數(shù)據(jù)庫(kù),來(lái)將請(qǐng)求在服務(wù)器層以FIFO(先進(jìn)先出)的方式排隊(duì),就可以達(dá)成串行的效果。
關(guān)于服務(wù)器的FIFO隊(duì)列系統(tǒng),在前面提到過(guò)阿里的RoketMQ、ActiveMQ還有RabbitMQ等消息中間件產(chǎn)品。當(dāng)然騰訊的技術(shù)團(tuán)隊(duì)自己設(shè)計(jì)了一個(gè)分布式的、輕巧的、靈活的FIFO隊(duì)列產(chǎn)品。
具體解決方案實(shí)現(xiàn)如下:
首先,將同一個(gè)紅包ID的所有請(qǐng)求歸聚到同一臺(tái)服務(wù)器。使用集合化,將同一個(gè)紅包ID的全部請(qǐng)求,提到到同一個(gè)集合中。同個(gè)SET中會(huì)存在多臺(tái)服務(wù)器同時(shí)連接同一臺(tái)數(shù)據(jù)庫(kù)服務(wù)器。這是基于容災(zāi)、性能等考慮,多臺(tái)服務(wù)器互備冗余,并且將流量進(jìn)行均衡負(fù)載。
怎樣將同一個(gè)紅包ID所有請(qǐng)求,提到同一臺(tái)服務(wù)器上?在集合化的設(shè)計(jì)之外,微信紅包系統(tǒng)添加了一層基于紅包ID 哈希值的分流,如下圖所示:
這和很多分布式系統(tǒng)很像,如圖片的分布式存儲(chǔ),數(shù)據(jù)庫(kù)的哈希分布等,可謂大道相通。
我們接下來(lái)再設(shè)計(jì)單機(jī)請(qǐng)求排隊(duì)之方案。當(dāng)同一臺(tái)服務(wù)器上的所有請(qǐng)求被接管后,然后按紅包ID進(jìn)行排隊(duì),串行地進(jìn)入工作進(jìn)程處理,達(dá)到排隊(duì)的效果。看下圖所示:
接下來(lái)我們使用memcached來(lái)控制并發(fā)數(shù)量,具體實(shí)施為:
為了防止服務(wù)器中的請(qǐng)求隊(duì)列過(guò)載,導(dǎo)致隊(duì)列被降級(jí),所有請(qǐng)求又沖進(jìn)了數(shù)據(jù)庫(kù),造成數(shù)據(jù)庫(kù)鎖與響應(yīng)過(guò)慢,紅包系統(tǒng)又增加了與服務(wù)器同機(jī)部署的memcached內(nèi)存數(shù)據(jù)庫(kù),把它用來(lái)控制拆同一個(gè)紅包的請(qǐng)求并發(fā)數(shù)。我們實(shí)際是利用memcached的CAS原子性累增操作,來(lái)控制同時(shí)進(jìn)入數(shù)據(jù)庫(kù)中執(zhí)行拆紅包事務(wù)的請(qǐng)求數(shù),苦超過(guò)預(yù)先設(shè)定數(shù)值則直接拒絕服務(wù),用于處理數(shù)據(jù)庫(kù)負(fù)載升高時(shí)的降級(jí)體驗(yàn)。
通過(guò)以上三個(gè)措施,我們就控制了數(shù)據(jù)庫(kù)的“并發(fā)搶鎖”問(wèn)題。
3 雙維度庫(kù)表設(shè)計(jì),保障系統(tǒng)性能穩(wěn)定
任何系統(tǒng)的進(jìn)化,在持久層都開(kāi)始分庫(kù)分表,微信紅包系統(tǒng)也不例外。
微信紅包的分庫(kù)表規(guī)則,最開(kāi)始是根據(jù)紅包ID的哈希值分為多庫(kù)多表。
隨著紅包數(shù)據(jù)量逐漸增大,單表數(shù)據(jù)量也逐漸增加,數(shù)據(jù)庫(kù)的性能與單表數(shù)據(jù)量有一定相關(guān)性,例如InndoDB單表數(shù)據(jù)量達(dá)到幾T的時(shí)水平時(shí),性能會(huì)有不同程序的下降,這樣就影響系統(tǒng)性能穩(wěn)定性。
我們可以采用冷(不經(jīng)常被查詢(xún)到)熱(頻率存取的)數(shù)據(jù)的分離,將歷史冷數(shù)據(jù)與當(dāng)前熱數(shù)據(jù)分開(kāi)存儲(chǔ),來(lái)解決這個(gè)問(wèn)題。
在處理冷熱數(shù)據(jù)的分離時(shí),在紅包ID維度分庫(kù)表的基礎(chǔ)上,增加了以循環(huán)天分表的維度,形成了雙維度分庫(kù)表的特色。
具體如下,比如分庫(kù)表規(guī)則使用哈希+月份的開(kāi)工,類(lèi)似db_xx.t_y_dd設(shè)計(jì)。其中:xx/y是紅包ID的哈希值的后3位,dd是月份,取值范圍在01~31,代表一個(gè)月天數(shù)最多到31天。
通過(guò)兩種維度的分庫(kù)表,我們解決了數(shù)據(jù)單表的大量膨脹,導(dǎo)致性能下降的問(wèn)題,從而保障了系統(tǒng)性能的穩(wěn)定性。同時(shí)在熱冷數(shù)據(jù)分離的問(wèn)題上,使得數(shù)據(jù)遷移變得簡(jiǎn)單優(yōu)雅。
以上是微信紅包系統(tǒng)在解決高并發(fā)問(wèn)題上的設(shè)計(jì)方案。總結(jié)起就是:采用集合化分治、隊(duì)列系統(tǒng)、多維度分庫(kù)分表方案,使得單集群數(shù)據(jù)庫(kù)的并發(fā)性能提升了多倍,取得了良好的用戶體驗(yàn)。
在平時(shí)節(jié)假日、2015和2016春節(jié)實(shí)踐中充分證明了可行性,取得了顯著的效果。在剛剛過(guò)去的2017雞年除夕夜,微信紅包收發(fā)峰值達(dá)到76萬(wàn)每秒,收發(fā)微信紅包142億個(gè)。微信紅包系統(tǒng)的表現(xiàn)穩(wěn)定,實(shí)現(xiàn)了除夕夜紅包收發(fā)順暢零故障。
小結(jié)
本文從實(shí)戰(zhàn)出發(fā),講解了電商平臺(tái)以及交易系統(tǒng)的典型紅包系統(tǒng)的構(gòu)建,包括分布式集群系統(tǒng)的靈活應(yīng)用,實(shí)現(xiàn)Web服務(wù)器、內(nèi)存、緩存以及數(shù)據(jù)庫(kù)的有效利用。通過(guò)秒殺系統(tǒng)觸類(lèi)而旁通到紅包系統(tǒng),用簡(jiǎn)單有效的思維來(lái)解決復(fù)雜問(wèn)題。
作者:21CTO社區(qū)
說(shuō)明:本文參考了騰訊大講堂關(guān)于微信紅包架構(gòu)的文章,原文一部分生澀部分做了優(yōu)化。阿里架構(gòu)一部分內(nèi)容參考了阿里云社區(qū)關(guān)于雙十一的部分內(nèi)容。
來(lái)源:http://www.sohu.com/a/126891351_505802
總結(jié)
以上是生活随笔為你收集整理的高并发资金交易系统设计方案—百亿双十一、微信红包背后的技术架构的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 端午节送香包有什么意义?
- 下一篇: 阿里P8架构师谈:阿里双11秒杀系统如何