自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

你真的懂 Redis 哨兵集群嗎?一主二從三哨兵架構(gòu)如何扛住百萬級并發(fā)?

數(shù)據(jù)庫 Redis
主從復(fù)制架構(gòu)面臨一個嚴(yán)峻問題:master 宕機(jī),無法執(zhí)行寫操作,無法自動選擇將一個 slave 切換為 master,也就是無法實現(xiàn)自動故障切換。

通過之前的學(xué)習(xí),你已知道 Redis 主從復(fù)制是高可用的基石,某個 slave 宕機(jī)依然可以將請求發(fā)送給 master 或者其他 slave,但是如果 master 宕機(jī),則只能響應(yīng)讀操作,寫請求無法再執(zhí)行。

所以主從復(fù)制架構(gòu)面臨一個嚴(yán)峻問題:master 宕機(jī),無法執(zhí)行寫操作,無法自動選擇將一個 slave 切換為 master,也就是無法實現(xiàn)自動故障切換。

Chaya:“還記得那晚我與男友約會,眼前是橡樹的綠葉,白色的竹籬笆。好想告訴我的他,這里像幅畫,一起手牽手么么噠(此處省略 10000 字)。

“Redis 忽然宕機(jī),我的戀人小 Q 總不能把我推開,停止甜蜜,然后打開電腦手工進(jìn)行主從切換,再通知其他程序員把地址改成新 master 的信息上線?!?/p>

如此一折騰,你心里的雨傾盆地下,萬萬使不得。所以必須有一個高可用的方案,為此,我提供一個高可用方案——哨兵(sentinel)。

哨兵是什么?

吃瓜群眾:“Redis 大佬,雖然我沒有女朋友,但是未雨綢繆,我要掌握這個哨兵模式,防止當(dāng)我與女朋友約會時被打擾,你快說說什么是哨兵以及哨兵的實現(xiàn)原理吧?!?/p>

先來看看哨兵是什么?搭建哨兵集群的方法我就不細(xì)說了,假設(shè)三個哨兵組成一個哨兵集群,三個數(shù)據(jù)節(jié)點構(gòu)成一個一主兩從的 Redis 主從架構(gòu),如圖 3-17 所示。

圖3-17

Redis 哨兵集群高可用架構(gòu)有三種角色,分別是 master、slave 和 sentinel。

  • sentinel 之間互相通信,組成一個集群實現(xiàn)哨兵高可用,選舉出一個 leader 執(zhí)行故障遷移操作。
  • master 與 slave 之間通信,組成主從復(fù)制架構(gòu)。
  • sentinel 與 master/ slave 通信,是為了對該主從復(fù)制架構(gòu)進(jìn)行管理,包括監(jiān)視(Monitoring)、通知(Notification)、自動故障切換(Automatic Failover)、配置提供者(Configuration Provider)。

哨兵監(jiān)控的 master 的名字叫作 mymaster,master 的 IP 地址是 127.0.0.1,端口是 6379。quorum 是關(guān)鍵參數(shù),它的作用如下。

  • 指定在標(biāo)記 master 故障并嘗試執(zhí)行故障切換時需要一定數(shù)量達(dá)成一致意見的哨兵進(jìn)程。大白話就是需要多少個哨兵進(jìn)程認(rèn)為 master 宕機(jī),真正標(biāo)記 master 宕機(jī)才能啟動故障切換過程。
  • 對于多個哨兵,需要選出一個 leader 來執(zhí)行實際的故障自動轉(zhuǎn)移操作,當(dāng)某個哨兵的票數(shù)超過 quorum 時,就選舉這個哨兵為 leader,負(fù)責(zé)自動故障切換。quorum 的值一般取哨兵個數(shù)的一半以上 (n/2 + 1) 比較合理。

哨兵只要配置 master 信息即可與三個角色建立聯(lián)系。

Chaya:“為什么哨兵只需要配置 master 信息就可以與三個角色建立聯(lián)系?”

  • 哨兵可以通過 master 獲取 slave 的信息,并與 slave 建立連接。master 與 slave 是主從關(guān)系,通過 info 命令就可以通過 master 獲取 slave 的 IP 地址 和 port、runid 等信息。
  • 通過上面的步驟,哨兵與 master 和所有的 slave 建立連接,哨兵之間的互相感知則通過 Redis 的發(fā)布/訂閱機(jī)制實現(xiàn)。每個哨兵通過發(fā)布/訂閱 master 的 sentinel:hello 頻道發(fā)布和接收信息,以此感知其他哨兵的存在并建立連接。

哨兵的任務(wù)

哨兵是 Redis 的一種運(yùn)行模式,它專注于對 Redis 實例(master、slave)運(yùn)行狀態(tài)的監(jiān)控,并能夠在 master 發(fā)生故障時通過一系列的機(jī)制實現(xiàn)選主及主從切換,實現(xiàn)自動故障切換,確保整個 Redis 系統(tǒng)的可用性。

Chaya 可以安心地與愛人在歡樂港灣約會,盡情享受甜蜜,哪怕是吵架都那么醉人,不再需要擔(dān)心 Redis 忽然宕機(jī)帶來的煩惱。

我們先從全局看哨兵,簡要地了解它的整個運(yùn)作流程,接著針對每個任務(wù)詳細(xì)分析,Redis 哨兵的主要職責(zé)如下。

  • 監(jiān)控(Monitoring):Redis 的哨兵不斷檢查 master 和 slave 實例是否按預(yù)期工作。它監(jiān)視實例的健康狀態(tài),包括 master 和所有 slave。
  • 自動故障切換(Automatic Failover)**:如果 master 出現(xiàn)故障或不按預(yù)期工作,Redis 的哨兵則啟動自動故障切換流程。在此過程中,一個 slave 會被晉升為新的 master。
  • 通知(Notification):讓 slave 執(zhí)行 replicaof 命令與新的 master 同步數(shù)據(jù);并且通知客戶端與新的 master 建立連接,如圖 3-18 所示。
  • 配置提供者(Configuration Provide):哨兵充當(dāng)了客戶端服務(wù)發(fā)現(xiàn)的權(quán)威來源??蛻舳诉B接到任何一個哨兵以獲取新的 master 的地址,確保能夠連接到正確的實例。

1. 監(jiān)控

Redis :八卦一下,Chaya,你的戀人用什么方式來了解你每天的喜怒哀樂呢?

Chaya:“這很簡單,他每天給我發(fā)微信消息、打電話或者打視頻,若是哪天我不接電話,或者他發(fā)送微信消息時出現(xiàn)紅色感嘆號,就說明我把他拉黑了?!?/p>

哨兵與各個角色節(jié)點建立連接后,通過PING、INFO、PUBLISH / SUBSCRIBE命令來監(jiān)控所有實例的健康狀態(tài),當(dāng)然,它不會說情話。

哨兵默認(rèn)會以每秒一次的頻率向所有的 master、slave、哨兵發(fā)送 PING 命令,這個其實是一個心跳檢測,用于探測實例是否存活。

  • PING:所有節(jié)點之間通過發(fā)送 PING 命令確認(rèn)對方是否在線,默認(rèn)每秒發(fā)送一次。
  • I NFO:哨兵向 master、slave 發(fā)送該命令,用于獲取 slave 的詳細(xì)信息。
  • PUBLISH / SUBSCRIBE:哨兵會訂閱 master 和 slave 的 sentinel:hello 頻道,并通過該頻道發(fā)布自己的信息,這樣其他哨兵之間就可以建立聯(lián)系。

如果一個 master 實例距離最后一次有效回復(fù) PING 命令的時間超過 down-after- milliseconds 選項所指定的值,這個 master 實例就會被哨兵標(biāo)記為“主觀下線”。

如果 slave 沒有在指定時間內(nèi)響應(yīng)哨兵的 PING 命令,則直接被標(biāo)記為“主觀下線”。

只有當(dāng)大于或等于法定個數(shù)(quorum)的哨兵節(jié)點認(rèn)為該 master 主觀下線時,才能將該 master 改為客觀下線。接著才會開啟自動故障切換流程。

PING 命令的回復(fù)有兩種情況。

  • 有效回復(fù):返回 +PONG、-LOADING 和-MASTERDOWN 中的任何一種。
  • 無效回復(fù):有效回復(fù)之外的回復(fù),或者不在指定時間內(nèi)返回任何回復(fù)。

Chaya:“主觀下線和客觀下線的作用是什么?”

主要是為了避免出現(xiàn)哨兵誤判 master 運(yùn)行的情況,一旦出現(xiàn)誤判,就會出現(xiàn) master 實際沒有下線,可是哨兵誤以為其已經(jīng)下線的情況,接著就會啟動主從故障切換流程,之后的選主和通知操作都會消耗大量資源。

誤判一般會發(fā)生在集群網(wǎng)絡(luò)壓力較大、網(wǎng)絡(luò)擁塞或者是 master 本身壓力較大的情況下。

既然一個哨兵容易誤判,那就使用多個哨兵進(jìn)行投票判斷。哨兵機(jī)制也是類似的,采用多實例組成的集群模式進(jìn)行部署,就是哨兵集群。

引入多個哨兵實例一起進(jìn)行判斷,就可以避免單個哨兵因為自身網(wǎng)絡(luò)狀況不好,而誤判主庫下線的情況。

同時,多個哨兵的網(wǎng)絡(luò)同時不穩(wěn)定的概率較小,由它們一起做決策,也能降低誤判率。

主觀下線

主觀下線(Subjectively Down,SDOWN)指一個哨兵認(rèn)為一個 Redis 實例已經(jīng)不可用或者已經(jīng)下線,這有可能是網(wǎng)絡(luò)不通、心跳超時或連接失敗等原因?qū)е碌摹?/p>

例如對于 master 或者 slave,在 down-after-milliseconds 指定的毫秒數(shù)之內(nèi),如果沒有向哨兵發(fā)送的 PING 命令回復(fù),或者返回一個錯誤,那么哨兵會將這個服務(wù)器標(biāo)記為主觀下線。

需要注意的是,Redis 的哨兵的主要目標(biāo)是確保 master 的高可用性,而不是 slave 的高可用性。

因此,主觀下線和客觀下線的主要關(guān)注點通常是 master。slave 通常不會被單獨標(biāo)記為客觀下線,因為它們不承擔(dān) master 的關(guān)鍵角色,它們的主要責(zé)任是復(fù)制數(shù)據(jù)。

客觀下線

判斷 master 是否下線不能只由一個哨兵說了算,只有過半的哨兵判斷 master 主觀下線,才能將 master 標(biāo)記為客觀下線,如圖 3-19 所示。

3-19

之前提到過 sentinel monitor <master-name> <ip> <redis-port> <quorum> 的配置,參數(shù) quorum 是判斷客觀下線的依據(jù)之一,意思是至少有 quorum 個哨兵判定這個 master 主觀下線,才會將這個 master 標(biāo)記為客觀下線。

只有 master 被判定為客觀下線,才會進(jìn)一步觸發(fā)哨兵執(zhí)行主從切換流程。

2. 自動故障切換

Chaya:“一旦判斷 master 客觀下線,就在 slave 中選一個作為新的 master 嗎?”

哨兵的第二個任務(wù)是選擇一個 slave 作為新的 master,并對外提供服務(wù)。之后其他 slave 會與新的 master 進(jìn)行主從復(fù)制,這個過程叫作自動故障切換,如圖 3-20 所示。

3-20

吃瓜群眾:“如何從眾多 slave 中選出一個做 master 呢?”

Chaya:“我覺得篩選過程就像找戀愛對象,每個人心中都有標(biāo)尺,會通過直覺、習(xí)慣和自己的標(biāo)準(zhǔn)從所有的追求者中選擇一個最適合自己的?!?/p>

類似地,Redis 有自己的篩選規(guī)則,按照一定的篩選條件和打分策略,選出一個“節(jié)點”擔(dān)任 master。

篩選條件

Chaya:“有哪些篩選條件?”

  • 下線或網(wǎng)絡(luò)斷連的 slave 直接丟棄。
  • 網(wǎng)絡(luò)無異常:slave 最后一次響應(yīng) PING 命令的時間不能超過 5 倍 PING 周期;slave INFO(每 10s 發(fā)送一次 INFO 命令)的信息更新時間不能超過 3 倍 INFO 刷新周期。
  • 評估過往的網(wǎng)絡(luò)狀態(tài):slave 與 master 斷開連接,斷連時間不能超過(現(xiàn)在-master 被標(biāo)記為下線的時間)+(master 的 down-after- milliseconds 配置項的值乘以 10),單位是毫秒。

總之,下線或者網(wǎng)絡(luò)經(jīng)常斷開的 slave 不能要。如果新的 master 很快出現(xiàn)網(wǎng)絡(luò)故障,就又得重新選擇新的 master,這不“鬧著玩”嗎,得排除掉!

打分

過濾掉不合適的 slave 之后,使用快速排序?qū)?slave 列表進(jìn)行打分,按照以下排序找出“王者”。

  • slave 優(yōu)先級:通過 replica-priority 100 配置項,給不同的 slave 配置不同優(yōu)先級,默認(rèn)是 100,值越低,優(yōu)先級越高,配置為特殊值 0 表示不會晉升為 master。
  • 更大復(fù)制偏移量(processed replication offset):已復(fù)制的數(shù)據(jù)量越多,slave_repl_offset 與 master_repl_offset 的差值就越小。
  • slave runID:在優(yōu)先級和復(fù)制進(jìn)度都相同的情況下,runID 最小的 slave 得分最高,該 slave 會被選為新的 master。

哨兵向篩選出來的 slave 發(fā)送 slave no one 命令,使得該 slave 成為新的 master,哨兵并不關(guān)心命令返回的結(jié)果,它會發(fā)送 info 命令給 slave,并根據(jù)命令的回復(fù)內(nèi)容確認(rèn) slave 是否成功轉(zhuǎn)換為 master。

Chaya:“舊的 master 重新恢復(fù)正常時要怎么處理?”

舊的不去,新的不來,有些人一旦錯過就不在,既然已經(jīng)錯過,相逢也只能是過客。

原 master 恢復(fù)正常,重新連接哨兵,這時集群已經(jīng)有新的 master,所以舊的 master 被哨兵降級為 slave。

3. 通知

新的 master 出現(xiàn)后,哨兵還有一件重要的事情要做——將新的 master 的連接信息通過 slave 命令發(fā)送給其他 slave,通知 slave 執(zhí)行 replacaof 命令和新的 master 建立連接進(jìn)行主從復(fù)制。

接著,哨兵會定時給 slave 發(fā) INFO 命令,從 INFO 命令的回復(fù)內(nèi)容來確認(rèn) slave 是否與新的 master 成功建立連接。檢測到所有 slave 都與新的 master 建立連接,自動故障切換就完成了。

如果還有剩余 slave 沒有連上新的 master,則哨兵還會再做一次努力,再次向這些 slave 發(fā)送 slave 命令,要求他們與新的 master 建立連接。

4. 配置提供者

Redis 客戶端只需要跟哨兵打交道,就可以無感知地連接到新的 master,最重要的原因是哨兵提供了一些 API 來檢查主從節(jié)點的運(yùn)行狀況。

哨兵集群實現(xiàn)原理

如果只有一個哨兵就會存在單點故障問題。Redis sentinel 是一個分布式系統(tǒng),由多個哨兵協(xié)作組成集群實現(xiàn)高可用。

  • 當(dāng)多個哨兵達(dá)成一致認(rèn)為某個 master 不可用時,才執(zhí)行故障遷移,降低了誤報的概率。
  • 不需要所有哨兵都可用,哨兵集群依然可以正常工作。

Chaya:“哨兵是如何感知其他哨兵節(jié)點的呢?又如何知道 slave 節(jié)點的信息并監(jiān)控呢?當(dāng) master 不可用時,到底由哪個哨兵來執(zhí)行自動故障切換呢?”

1. 發(fā)布/訂閱機(jī)制

哨兵互相發(fā)現(xiàn)

哨兵之間可以互相感知發(fā)現(xiàn),這歸功于 Redis 的發(fā)布/訂閱機(jī)制。

當(dāng)哨兵與 master 建立連接后,使用發(fā)布/訂閱機(jī)制在特殊的頻道發(fā)布自己的信息,例如 IP 地址和端口,同時訂閱該頻道獲取其他哨兵發(fā)布的消息。

master 有一個 sentinel:hello 的專用通道,用于哨兵之間發(fā)布和訂閱消息。

可以比喻為哨兵利用 master 建立的sentinel:hello 微信群發(fā)布自己的消息,同時關(guān)注其他哨兵發(fā)布的消息,如圖 3-21 所示。

3-21

哨兵如何感知并監(jiān)控 slave

哨兵之間建立連接形成集群還不夠,哨兵還需要跟所有 slave 建立連接,否則無法監(jiān)控它們。除此之外,如果發(fā)生了主從切換也需要通知 slave 重新與新的 master 建立連接進(jìn)行數(shù)據(jù)同步。

哨兵向 master 發(fā)送 INFO 命令,master 接收到命令后,將 slave 列表告訴哨兵。

哨兵根據(jù) master 響應(yīng)的 slave 名單信息與所有 salve 建立連接,并且根據(jù)這個連接持續(xù)監(jiān)控 slave,剩下的哨兵也基于此實現(xiàn)監(jiān)控,如圖 3-22 示。

2. 選擇哨兵執(zhí)行主從切換

Chaya:“master 不可用后,如何選擇一個哨兵來執(zhí)行自動故障切換呢?”

任何哨兵判斷 master 主觀下線后,都會向其他哨兵發(fā)送 is-master-down-by- addr 命令,其他哨兵收到命令后則根據(jù)自己與 master 之間的連接狀況分別響應(yīng) Y 或者 N,Y 表示贊成,N 表示反對。

如果某個哨兵獲得了大多數(shù)哨兵的贊成票,就標(biāo)記 master 為客觀下線。

例如,一共有 3 個哨兵組成集群,那么 quorum 就可以配置為 2,當(dāng)一個哨兵獲得了 2 張贊成票(包含自己的 1 票)時,就可以標(biāo)記 master“客觀下線”。

獲得多數(shù)贊成票的哨兵向其他哨兵發(fā)送 SENTINEL is-master-down-by-addr <masterip> <masterport> <sentinel.current_epoch>命令,聲明自己想要執(zhí)行主從切換并開始拉票。

其他哨兵則進(jìn)行投票,投票過程叫作 leader 選舉,選舉的過程借鑒了分布式系統(tǒng)中的 Raft 協(xié)議。

簡單地說,哨兵標(biāo)記當(dāng)前 master 客觀下線后,通過投票的方式從哨兵集群中選舉出一個哨兵作為 leader 角色執(zhí)行故障切換。

Chaya:“我發(fā)現(xiàn)判斷 master 是否客觀下線和哨兵拉票選舉 leader 是同樣的命令?!?/p>

沒錯,is-master-down-by-addr 命令有兩個作用:

  • 一是詢問其他哨兵是否認(rèn)為某個 master 已經(jīng)主觀下線;
  • 二是開始進(jìn)行自動故障切換時,當(dāng)前哨兵向其他哨兵實例進(jìn)行"拉票",讓其他哨兵選舉自己為 leader。

哨兵想要成為 leader 沒那么簡單,得有兩把“刷子”。需要滿足以下條件。

  • 獲得其他哨兵過半的投票。
  • 投票的數(shù)量大于或等于 quorum 的值。

如果 sentine 集群有 2 個實例,此時,一個哨兵要想成為 leader,那么必須獲得 2 票,而不是 1 票。

所以,如果有一個哨兵宕機(jī)了,那么此時的集群是無法進(jìn)行主從庫切換的。因此,通常我們至少會配置 3 個哨兵實例。

3. 發(fā)布/訂閱機(jī)制

在 Redis 中,發(fā)布/訂閱(Pub/Sub)機(jī)制發(fā)布不同事件,讓客戶端訂閱消息。哨兵提供的消息訂閱頻道有很多,不同頻道包含了主從庫切換過程中的不同關(guān)鍵事件。

master 相關(guān)

與 master 相關(guān)的消息訂閱頻道。

◎ +sdown:節(jié)點處于主觀下線狀態(tài)。

◎ -sdown:節(jié)點不再處于主觀下線狀態(tài)。

◎ +odown:節(jié)點進(jìn)入客觀下線狀態(tài)。

◎ -odown:節(jié)點退出客觀下線狀態(tài)。

◎ +switch-master:master 地址發(fā)生了變化。

slave 相關(guān)

與 slave 相關(guān)的消息訂閱頻道。

◎ +slave-reconf-sent:leader 哨兵發(fā)送 REPLICAOF 命令重新配置從庫。

◎ +slave-reconf-inprog:slave 配置了新的 master,但是尚未同步。

◎ +slave-reconf-done:slave 配置了新的 master,并完成了數(shù)據(jù)同步。

Redis 的發(fā)布/訂閱機(jī)制尤其重要,有了發(fā)布/訂閱機(jī)制,哨兵和哨兵之間、哨兵和 slave 之間、哨兵和客戶端之間就都能建立起連接了,各種事件的發(fā)布也是通過這個機(jī)制實現(xiàn)的。

責(zé)任編輯:姜華 來源: 碼哥跳動
相關(guān)推薦

2025-02-14 03:00:00

2025-01-12 13:06:45

2023-04-11 08:30:52

2023-10-26 07:47:53

Redis哨兵集群

2023-09-27 06:26:07

2022-06-08 16:55:56

服務(wù)器Redis架構(gòu)

2022-12-21 09:50:41

2021-03-31 10:12:12

MongoDBQPS存儲

2019-05-13 14:17:06

抓包Web安全漏洞

2021-04-01 08:50:54

SentinelRedis 集群原理

2022-02-14 08:33:51

Redis哨兵集群

2019-10-18 09:50:47

網(wǎng)絡(luò)分層模型網(wǎng)絡(luò)協(xié)議

2020-04-14 21:12:42

Redis集群Linux

2019-09-15 10:38:28

網(wǎng)絡(luò)分層模型

2023-11-29 08:03:05

2021-03-31 05:57:40

集群搭建哨兵集群Redis

2022-02-11 08:41:19

WindowsRedis集群

2020-06-08 08:20:11

Redis高可用集群

2024-07-16 08:38:06

2020-09-02 17:28:26

Spring Boot Redis集成
點贊
收藏

51CTO技術(shù)棧公眾號