鍍金池/ 教程/ 大數(shù)據(jù)/ 高可用客戶端指引
使用 Redis 實現(xiàn) Twitter(上)
集群(下)
使用 Redis 實現(xiàn) Twitter(下)
使用 Redis 作為 LRU 緩存
高可用(上)
高可用客戶端指引
集群(中)
高可用(下)
持久化
Redis 介紹
集中插入
集群(上)
從入門到精通(上)
從入門到精通(下)
從入門到精通(中)
分片
數(shù)據(jù)類型初探
復制

高可用客戶端指引

本文檔是一篇草案,其包含的指引將來可能會隨著Sentinel項目的進展而改變。

支持Redis Sentinel的Redis客戶端指引

Redis Sentinel是Redis實例的監(jiān)控解決方案,處理Redis主服務器的自動故障轉移和服務發(fā)現(xiàn)(誰是一組實例中的當前主服務器)。由于Sentinel具有在故障轉移期間重新配置實例,以及提供配置給連接Redis主服務器或者從服務器的客戶端的雙重責任,客戶端需要有對Redis Sentinel的顯式支持。

這篇文檔針對Redis客戶端開發(fā)人員,他們想在其客戶端實現(xiàn)中支持Sentinel,以達到如下目標:

  • 通過Sentinel實現(xiàn)客戶端的自動配置。
  • 改進Sentinel自動故障轉移的安全性。# 高可用客戶端指引

本文檔是一篇草案,其包含的指引將來可能會隨著 Sentinel 項目的進展而改變。

支持 Redis Sentinel 的 Redis 客戶端指引

Redis Sentinel 是 Redis 實例的監(jiān)控解決方案,處理 Redis 主服務器的自動故障轉移和服務發(fā)現(xiàn)(誰是一組實例中的當前主服務器)。由于 Sentinel 具有在故障轉移期間重新配置實例,以及提供配置給連接 Redis 主服務器或者從服務器的客戶端的雙重責任,客戶端需要有對 Redis Sentinel 的顯式支持。

這篇文檔針對 Redis 客戶端開發(fā)人員,他們想在其客戶端實現(xiàn)中支持 Sentinel,以達到如下目標:

  • 通過 Sentinel 實現(xiàn)客戶端的自動配置。
  • 改進 Sentinel 自動故障轉移的安全性。

要想獲得 Redis Sentinel 如何工作的細節(jié),請查看相關文檔(請查看本系列相關文章,譯者注),本文只包含 Redis 客戶端開發(fā)人員需要的信息,期待讀者已經(jīng)比較熟悉 Redis Sentinel 的工作方式。

通過 Sentinel 實現(xiàn) Redis 服務發(fā)現(xiàn)(Redis service discovery)

Redis Sentinel 通過像”stats”或”cache”這樣的名字來識別每個主服務器。每個名字實際上標識了一組實例,由一個主服務器和若干個從服務器組成。

網(wǎng)絡中用于特定目的的 Redis 主服務器的地址,在一些像自動故障轉移,手工觸發(fā)故障轉移(例如,為了提升一個 Redis 實例),或者其他原因引起的這樣的事件后可能會改變。

通常,Redis 客戶端中有一些硬編碼的配置來指定 IP 地址和端口作為網(wǎng)絡中 Redis 主服務器的地址。但是,如果主服務器的地址改變了,就需要手工介入到每個客戶端了。

支持 Sentinel 的 Redis 客戶端可以從使用 Sentinel 的主服務器的名稱自動發(fā)現(xiàn) Redis 的地址。所以支持 Sentinel 的客戶端應該可以從輸入中獲得,而不是硬編碼的 IP 地址和端口:

  • 指向已知的 Sentinel 實例的 ip:port 對列表。
  • 服務的名稱,像”timelines”或者”cache”。

下面是客戶端為了從 Sentinel 列表和服務名稱獲得主服務器地址而需要遵循的步驟。

第 1 步:連接第一個 Sentinel(connecting to the first Sentinel)

客戶端應該迭代 Sentinel 地址列表。應該嘗試使用較短的超時(大約幾百毫秒)來連接到每一個地址的 Sentinel。遇到錯誤或者超時就嘗試下一個 Sentinel 地址。

如果所有的 Sentinel 地址都沒有嘗試成功,就返回一個錯誤給客戶端。

第一個回應客戶端請求的 Sentinel 被置于列表的開頭,這樣在下次重連時,我們會首先嘗試在上一次連接嘗試是可達的 Sentinel,以最小化延遲。

第 2 步:請求主服務器地址(ask for master address)

一旦與 Sentinel 的連接建立起來,客戶端應該重新嘗試在 Sentinel 上執(zhí)行下面的命令:

SENTINEL get-master-addr-by-name master-name

這里的 master-name 應該被替換為用戶指定的真實服務名稱。

調用的結果可能是下面兩種回復之一:

  • ip:port 對。
  • 一個 null 回復。這表示 Sentinel 不知道這個主服務器。

如果收到了 ip:port 對,這個地址應該用來連接到 Redis 主服務器。否則,如果收到了一個 null 回復,客戶端應該嘗試列表中的下一個 Sentinel。

第 3 步:在目標實例中調用 ROLE 命令(call the ROLE command in the target instance)

一旦客戶端發(fā)現(xiàn)了主服務器實例的地址,就應該嘗試與主服務器的連接,然后調用 ROLE 命令來驗證實例的角色真的是一個主服務器。

如果 ROLE 命令不可用(Redis 2.8.12 引進的),客戶端可以使用 INFO 復制命令來解析角色:輸出中的某一個字段。

如果實例不是期待中的主服務器,客戶端應該等待一小段時間(幾百毫秒)然后再嘗試從第 1 步開始。

處理重連(Handling reconnections)

一旦服務名稱被解析為主服務器地址,并且與 Redis 主服務器實例的連接已經(jīng)建立,每次需要重新連接時,客戶端應該重新從第 1 步開始使用 Sentinel 來解析地址。例如,下面的情況下需要重新聯(lián)系 Sentinel:

  • 如果客戶端在超時或者 socket 錯誤后重連。
  • 如果客戶端因為被顯式關閉或者被用戶重連而重連。

在上面的情況下或者任何客戶端丟失了與 Redis 服務器連接的情況下,客戶端應該再次解析主服務器地址。

Sentinel 故障轉移斷開(Sentinel failover disconnection)

從 Redis 2.8.12 開始,當 Redis Sentinel 改變了實例的配置,例如,提升從服務器為主服務器,故障轉移后降級主服務器來復制新的主服務器,或者只是改變一個舊的(stale)從服務器的主服務器地址,會發(fā)送一個 CLIENT KILL 類型的命令給實例,來確保所有的客戶端都與重新配置過的實例斷開。這會強制客戶端再次解析主服務器地址。

如果客戶端要聯(lián)系一個還未更新信息的 Sentinel,通過 ROLE 命令驗證 Redis 實例角色會失敗,允許客戶端發(fā)現(xiàn)聯(lián)系上的 Sentinel 提供了舊的(stale)信息,然后會重試。

注意:一個舊的主服務器返回在線的同時,客戶端聯(lián)系一個舊的 Sentinel 實例是有可能的,所以客戶端可能連接了一個舊的主服務器,然而 ROLE 的輸出也是匹配的。但是,當主服務器恢復回來以后,Sentinel 將會嘗試將其降級為從服務器,觸發(fā)一次新的斷開。這個邏輯也適用于連接到一個舊的從服務器,其會被重新配置來復制一個不同的主服務器。

連接從服務器(Connecting to slaves)

有時候客戶端有興趣連接到從服務器,例如,為了分離(scale)讀請求。簡單修改一下第 2 步就可以支持連接從服務器。不是調用下面的命令:

SENTINEL get-master-addr-by-name master-name

客戶端應該調用:

SENTINEL slaves master-name

用于檢索從服務器實例的清單。

相應地,客戶端應該使用 ROLE 命令來驗證實例真的是一個從服務器,以防止分離讀請求到主服務器。

連接池(Connection pools)

對于實現(xiàn)了連接池的客戶端,當單個連接重連時,應該要再次聯(lián)系 Sentinel,如果是主服務器的地址改變了,所有已經(jīng)存在的連接都要關閉并且重新連接到新的地址。

錯誤報告(Error reporting)

客戶端應該在遇到錯誤時正確的返回信息給用戶,尤其是:

  • 如果沒有 Sentinel 能夠聯(lián)系上(這樣客戶端不可能從 SENTINEL get-master-addr-by-name 獲得回復),應該返回明確表明 Redis Sentinel 不可達的錯誤。
  • 如果所有池中的 Sentinel 返回 null 回復,用戶必須被通知 Sentinel 不認識這個主服務器名稱的錯誤。

Sentinel 列表自動刷新(Sentinels list automatic refresh)

一旦收到 get-master-addr-by-name 的成功回復,客戶端會按照下面的步驟來更新其內部的 Sentinel 節(jié)點的列表:

  • 使用 SENTINEL sentinels 命令獲取這臺主服務器的其他 Sentinel 列表。
  • 添加每個不在列表中的 ip:port 對到列表的后面。

客戶端不需要更新自己的配置文件來持久化列表。更新內存中表示的 Sentinel 列表的能力對改進可靠性已經(jīng)很有用了。

訂閱 Sentinel 事件來改進響應能力(Subscribe to Sentinel events to improve responsiveness)

介紹 Sentinel 的文檔中展示了客戶端可以使用發(fā)布訂閱來連接 Sentinel 以訂閱 Redis 實例的配置變更。

這種機制可以用來加快客戶端的重配置,也就是,客戶端可以監(jiān)聽發(fā)布訂閱,以知道配置變更什么時候發(fā)生,從而運行上文解釋的三步協(xié)議來解析新的 Redis 主服務器(或者從服務器)地址。

但是,通過發(fā)布訂閱收到的變更消息不能代替上面的步驟,因為不能保證客戶端可以收到所有的變更消息。

額外信息(Additional information)

要獲得額外信息或者討論這個指引的特定方面,請發(fā)消息到 Redis Google Group。

上一篇:集群(中)下一篇:分片