項目已經在github上傳,歡迎指教。redis-cluster-dockergit
首先先把基礎概念內容相對理一遍:github
在這邊先對幾個名詞進行說明:redis
名詞 | 邏輯結構 | 物理結構 |
---|---|---|
主節點(master) | Redis主服務/數據庫 | 一個獨立的redis進程 |
從節點(slave) | Redis從服務/數據庫 | 一個獨立的redis進程 |
Redis數據節點 | 主節點和從節點 | 主節點和從節點的進程 |
Sentinel節點 | 監控Redis數據節點 | 一個獨立的Sentinel節點進程 |
Sentinel節點集合 | 若干Sentinel節點的抽象組合 | 若干Sentinel節點進程 |
Redis Sentinel | Redis高可用實現方案 | Sentinel節點集合和Redis數據節點進程 |
應用方 | 泛指一個或多個客戶端 | 一個或者多個客戶端進程或者線程 |
Red Sentinel是Redis的高可用實現方案。算法
Redis的主從複製模式能夠將主節點的數據改變同步給從節點,這樣從節點就能夠起到兩個做用:第一,做爲主節點的一個備份,一旦主節點出了故障不可達的狀況,從節點能夠做爲後備頂上來,而且保證數據儘可能不丟失(主從複製是最終一致性)。第二,從節點能夠擴展主節點的讀能力。docker
Redis主從複製模式下,一旦主節點出現了故障不可達,就須要Redis Sentinel自動完成發現和故障轉移,而且通知應用方,從而實現真正的高可用。shell
Redis Sentinel是一個分佈式架構,其中包括若干個Sentinel節點和Redis數據節點,每一個Sentinel節點會對數據節點和其他Sentinel節點進行監控,當他發現節點不可達時,會對節點作下線標識。若是被標誌的是主節點,它還會和其餘Sentinel節點進行「協商」,當大多數Sentinel節點都認爲主節點不可達時候,它們回選舉出一個Sentinel節點來完成自動故障轉移的工做,同時會將這個變化實時通知給Redis應用方。整個過程是徹底自動的,不須要人工來介入。數據庫
所以,能夠總結Redis Sentinel具備如下幾個功能:bash
同時看到,Redis Sentinel包含若干個Sentinel節點,這樣作也帶來了兩個好處:服務器
注意,Sentinel節點自己就是獨立的Redis節點,只不過它們有一點特殊,它們不存儲任何數據,只支持部分命令。網絡
Redis Sentinel的基本實現原理,具體包含如下幾個方面:
1.每隔10s,每一個Sentinel節點會向主節點和從節點發送info命令獲取最新的拓撲結構。如:
# Replication
role:master
connected_salves:2
slave0:ip=127.0.0.1,port=6380,state=online,offset=4917,lag=1
slave1:ip=127.0.0.1,port=6380,state=online,offset=4917,lag=1
複製代碼
Sentinel節點經過對上述結果進行解析就能夠找到相應的從節點。具體表如今:
簡單總結:
1)每隔10秒,會向主從節點發送info獲取拓撲信息。2)每隔2秒,向*__sentinel__:hello頻道發送對主節點判斷和當前Sentinel信息,也就是本身的彙報結果。3)每隔1秒,向其他全部**節點發送ping,保持聯繫。*
主觀下線:就像前面說的第三個定時任務,每一個Sentinel節點每隔1s對主、從節點、其餘Sentinel節點發送ping作心跳檢測。當這些節點超過配置的時長沒有收到有效的恢復,Sentinel節點就會對該節點作失敗斷定,這個行爲叫作主觀下線。
能夠看出是一家之言,有誤判的可能。
客觀下線:當Sentinel主觀下線的節點是主節點時,該Sentinel節點會經過Sentinel is-master-down-by-addr命令向其餘Sentinel節點詢問對主節點的判斷,當超過個數,Sentinel節點認爲主節點確實有問題,這時候Sentinel會作出客觀下線的決定,這樣客觀下線的含義是比較明顯了。
上面指的是對主節點客觀下線的,注意,從節點、Sentinel節點在主觀下線後,沒有後續的故障轉移操做。
故障轉移的工做只須要一個Sentinel節點來完成便可,因此Sentinel節點之間會作一個領導者選舉的工做,選一個Sentinel節點做爲領導者進行故障轉移的工做。而採用的就是Raft算法。這邊講解一下Redis Sentinel進行領導者選舉的大體思路:
**簡單來講:**在客觀下線確認的同時,就會請求當領導者的贊成。
超過半數Sentinel節點贊成,或者配置時候的贊成下線人數贊成。
從剛剛選舉出的領導者Sentinel節點,他來進行故障轉移:
在從節點列表中選出一個節點做爲新的主節點,選擇方法以下:
對第一部選出來的從節點執行slaveof no one命令讓它成爲主節點。
Sentinel領導者節點會向剩餘的從節點發送命令,讓它們成爲新主節點的從節點,複製規則和parallel-syncs參數有關。
也就是用來限制在一次故障轉移以後,每次向新的主節點發起復制操做的從節點個數。(避免對主節點形成過分網絡和磁盤IO的開銷)
Sentinel節點集合會將原理的主節點更新爲從節點,並保持着對其關注,當其恢復後命令它去複製新的主節點。
原主節點在從新上線後會被要求去複製新的主節點。也就是說,Sentinel節點依然會對這些下線節點進行按期監控,這是Redis Sentinel設計思路決定的。
前提:本試驗環境已經提早安裝了docker和docker-compose
說明:本次部署是單機僞集羣,想要部署真正的集羣,修改ip地址拆分配置到各個主機上部署便可。
這邊先說一些部署技巧:
部署至少3個且奇數個的Sentinel節點:
- 3個以上是經過Sentinel節點的個數提升對於故障判定的準確性,由於領導者選舉須要至少通常加1個的節點,奇數個節點能夠在知足該條件的基礎上節省一個節點。詳情見前面說起的概念內容。
- Sentinel節點集合能夠只監控一個主節點,也能夠監控多個主節點。
項目分紅兩個目錄,一個是redis目錄。主要存放redis主從節點的docke-compose文件。
在redis文件夾下建立redis目錄,主要是爲了持久化redis。(RDB和AOF路徑同樣)
在同文件夾下新建 docker-compose.yml文件。
├── data
│ ├── master
│ ├── slave1
│ └── slave2
└── docker-compose.yml
複製代碼
這邊簡單說重要的配置項:
...
container_name: redis-master
...
volumes:
- ./data/master:/data
command: redis-server --port 6379 --requirepass 123
...
container_name: redis-slave-1
...
volumes:
- ./data/slave1:/data
command: redis-server --slaveof 192.168.0.107 6379 --port 6380 --requirepass 1234 --masterauth 123
複製代碼
須要配置好對應驗證密碼和容器命以便從節點鏈接主節點。注意從節點鏈接不能用127.0.0.1鏈接上主服務器。這個的緣由就是redis主服務器綁定了127.0.0.1,那麼跨服務器IP的訪問就會失敗,從服務器用IP和端口訪問主的時候,主服務器發現本機6379端口綁在了127.0.0.1上,也就是隻能本機才能訪問,外部請求會被過濾。這邊我修改成ifconfig獲取的網卡地址,若是是線上生產環境建議綁定IP地址。
接下來是在跟目錄下創建文件夾sentinel:
sentinel monitor mymaster 192.168.0.107 6379 2
sentinel down-after-milliseconds mymaster 30000
sentinel parallel-syncs mymaster 1
sentinel auth-pass mymaster 1234
sentinel failover-timeout mymaster 180000
sentinel deny-scripts-reconfig yes
複製代碼
在文件夾下新建docker-compose.yml。如今sentinel文件夾結構以下:
├── conf
│ ├── sentinel1.conf
│ ├── sentinel2.conf
│ └── sentinel3.conf
└── docker-compose.yml
複製代碼
配置項重點是如下2條(注意配置文件每次成功運行後會自動更新一些節點信息):
#自定義集羣名,其中 192.168.8.188 爲 redis-master 的 ip,6379 爲 redis-master 的端口,2 爲最小投票數(由於有 3 臺 Sentinel 因此能夠設置成 2)
sentinel monitor mymaster 192.168.8.188 6379 2
# 每一個Sentinel節點都要經過按期發送ping命令來判斷redis數據節點和其他Sentinel節點是否可達,超過down-after-milliseconds即爲不可達。
sentinel down-after-milliseconds mymaster 30000
複製代碼