本篇文章為大家展示了Redis中怎么實(shí)現(xiàn)實(shí)時(shí)訂閱推送功能,內(nèi)容簡(jiǎn)明扼要并且容易理解,絕對(duì)能使你眼前一亮,通過這篇文章的詳細(xì)介紹希望你能有所收獲。

方案1:MQ的延遲投遞。MQ雖然支持消息的延遲投遞但尺度太大1s 5s 10s 30s 1m,用來做精確時(shí)間點(diǎn)投遞不行!并且用戶執(zhí)行訂閱之后又取消訂閱的話,要把發(fā)出去的MQ消息delete掉這個(gè)操作有點(diǎn)頭大,短時(shí)間內(nèi)難以落地!并且用戶可以取消之后再訂閱,這又涉及到去重的問題。所以MQ的方案否掉。
方案2:傳統(tǒng)定時(shí)任務(wù)。這個(gè)相對(duì)來說就簡(jiǎn)單一點(diǎn),用定時(shí)任務(wù)是去db里面load用戶的訂閱提醒記錄,從中選出當(dāng)前可以推送的記錄。但有句話說得好任何脫離實(shí)際業(yè)務(wù)的設(shè)計(jì)都是耍流氓~。下面我們就分析一下傳統(tǒng)的定時(shí)任務(wù)到底適不適合我們的這個(gè)業(yè)務(wù)!

綜上所述我們就知道了一般傳統(tǒng)的定時(shí)任務(wù)存在以下缺點(diǎn):
1、性能瓶頸。只有一臺(tái)機(jī)在處理,在大體量數(shù)據(jù)面前力不從心!
2、實(shí)效性差。定時(shí)任務(wù)的頻率不能太高,太高會(huì)業(yè)務(wù)數(shù)據(jù)庫(kù)造成很大的壓力!
3、單點(diǎn)故障。萬一跑的那臺(tái)機(jī)掛了,那整個(gè)業(yè)務(wù)不可用了-。- 這是一個(gè)很可怕的事情!
所以傳統(tǒng)定時(shí)任務(wù)也不太適合這個(gè)業(yè)務(wù)。。。
那我們是不是就束手無策了呢?其實(shí)不是的! 我們只要對(duì)傳統(tǒng)的定時(shí)任務(wù)做一個(gè)簡(jiǎn)單的改造!就可以把它變成可以同時(shí)多機(jī)跑,并且實(shí)效性可以精確到秒級(jí),并且拒絕單點(diǎn)故障的定時(shí)任務(wù)集群!這其中就要借助我們的強(qiáng)大的redis了。
方案3:定時(shí)任務(wù)集群
首先我們要定義定時(shí)任務(wù)集群要解決的三個(gè)問題!
1、實(shí)效性要高
2、吞吐量要大
3、服務(wù)要穩(wěn)定,不能有單點(diǎn)故障
下面是整個(gè)定時(shí)任務(wù)集群的架構(gòu)圖。

架構(gòu)很簡(jiǎn)單:我們把用戶的訂閱推送記錄存儲(chǔ)到redis集群的sortedSet隊(duì)列里面,并且以提醒用戶提醒時(shí)間戳作為score值,然后在我們個(gè)每業(yè)務(wù)server里面起一個(gè)定時(shí)器頻率是秒級(jí),我的設(shè)定就是1s,然后經(jīng)過負(fù)載均衡之后從某個(gè)隊(duì)列里面獲取要推送的用戶記錄進(jìn)行推送。下面我們分析以下這個(gè)架構(gòu)
1、性能:除去帶寬等其它因素,基本與機(jī)器數(shù)成線性相關(guān)。機(jī)器數(shù)量越多吞吐量越大,機(jī)器數(shù)量少時(shí)相對(duì)的吞吐量就減少。
2、實(shí)效性:提高到了秒級(jí),效果還可以接受。
3、單點(diǎn)故障?不存在的!除非redis集群或者所有server全掛了。。。。
這里解析一下為什么用redis?
第一redis 可以作為一個(gè)高性能的存儲(chǔ)db,性能要比MySQL好很多,并且支持持久化,穩(wěn)定性好。
第二redis SortedSet隊(duì)列天然支持以時(shí)間作為條件排序,完美滿足我們選出要推送的記錄。
ok~既然方案已經(jīng)有了那如何在一天時(shí)間內(nèi)把這個(gè)方案落地呢?是的我設(shè)計(jì)出這個(gè)方案到基本編碼完成,時(shí)間就是一天。。。因?yàn)闀r(shí)間太趕鳥。
首先我們以u(píng)ser_id作為key,然后mod隊(duì)列數(shù)hash到redis SortedSet隊(duì)列里面。為什么要這樣呢,因?yàn)槿绻脩敉瑫r(shí)訂閱了兩張劵并且推送時(shí)間很近,這樣的兩條推送就可以合并成一條~,并且這樣hash也相對(duì)均勻。下面是部分代碼的截圖:

然后要決定隊(duì)列的數(shù)量,一般正常來說我們有多少臺(tái)處理的服務(wù)器就定義多少條隊(duì)列。因?yàn)殛?duì)列太少,會(huì)造成隊(duì)列競(jìng)爭(zhēng),太多可能會(huì)導(dǎo)致記錄得不到及時(shí)處理。
然而最佳實(shí)踐是隊(duì)列數(shù)量應(yīng)該是可動(dòng)態(tài)配置化的,因?yàn)榫€上的集群機(jī)器數(shù)是會(huì)經(jīng)常變的。大促的時(shí)候我們會(huì)加機(jī)器是不是,并且業(yè)務(wù)量增長(zhǎng)了,機(jī)器數(shù)也是會(huì)增加是不是~。所以我是借用了淘寶的diamond進(jìn)行隊(duì)列數(shù)的動(dòng)態(tài)配置。

我們每次從隊(duì)列里面取多少條記錄也是可以動(dòng)態(tài)配置的

這樣就可以隨時(shí)根據(jù)實(shí)際的生產(chǎn)情況調(diào)整整個(gè)集群的吞吐量~。 所以我們的定時(shí)任務(wù)集群還是具有一個(gè)特性就是支持動(dòng)態(tài)調(diào)整~。
最后一個(gè)關(guān)鍵組件就是負(fù)載均衡了。這個(gè)是非常重要的!因?yàn)檫@個(gè)做得不好就會(huì)可能導(dǎo)致多臺(tái)機(jī)競(jìng)爭(zhēng)同時(shí)處理一個(gè)隊(duì)列,影響整個(gè)集群的效率!在時(shí)間很緊的情況下我就用了一個(gè)簡(jiǎn)單實(shí)用的利用redis一個(gè)自增key 然后 mod 隊(duì)列數(shù)量算法。這樣就很大程度上就保證不會(huì)有兩臺(tái)機(jī)器同時(shí)去競(jìng)爭(zhēng)一條隊(duì)列~.

最后我們算一下整個(gè)集群的吞吐量
10(機(jī)器數(shù)) * 2000(一次拉取數(shù)) = 20000。然后以MQ的形式把消息推送到消息中心,發(fā)MQ是異步的,算上其它處理0.5s。
其實(shí)發(fā)送20W的推送也就是10幾s的事情。
ok~ 到這里我們整個(gè)定時(shí)任務(wù)集群就差不多基本落地好了。如果你問我后面還有什么可以完善的話那就是:
1、加監(jiān)控, 集群怎么可以木有監(jiān)控呢,萬一出問題有任務(wù)堆積怎么辦~
2、加上可視化界面。
3、最好有智能調(diào)度,增加任務(wù)優(yōu)先級(jí)。優(yōu)先級(jí)高的任務(wù)先運(yùn)行嘛。
4、資源調(diào)度,萬一機(jī)器數(shù)量不夠,力不從心,優(yōu)先保證重要任務(wù)執(zhí)行。
上述內(nèi)容就是Redis中怎么實(shí)現(xiàn)實(shí)時(shí)訂閱推送功能,你們學(xué)到知識(shí)或技能了嗎?如果還想學(xué)到更多技能或者豐富自己的知識(shí)儲(chǔ)備,歡迎關(guān)注創(chuàng)新互聯(lián)-成都網(wǎng)站建設(shè)公司行業(yè)資訊頻道。
本文題目:Redis中怎么實(shí)現(xiàn)實(shí)時(shí)訂閱推送功能-創(chuàng)新互聯(lián)
URL標(biāo)題:http://chinadenli.net/article0/dpgoio.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供面包屑導(dǎo)航、外貿(mào)網(wǎng)站建設(shè)、ChatGPT、響應(yīng)式網(wǎng)站、品牌網(wǎng)站設(shè)計(jì)、移動(dòng)網(wǎng)站建設(shè)
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(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í)需注明來源: 創(chuàng)新互聯(lián)
猜你還喜歡下面的內(nèi)容