Redis Sentinel 介紹與部署
1. Sentinel介紹
1.1 主從復制的問題
Redis主從復制可將主節點數據同步給從節點,從節點此時有兩個作用:
一旦主節點宕機,從節點作為主節點的備份可以隨時頂上來。
擴展主節點的讀能力,分擔主節點讀壓力。
但是問題來了:
一旦主節點宕機,從節點晉升成主節點,同時需要修改應用方的主節點地址,還需要命令所有從節點去復制新的主節點,整個過程需要人工干預。
主節點的寫能力受到單機的限制。
主節點的存儲能力受到單機的限制。
第一個問題,我們接下來講的Sentinel就可以解決。而后兩個問題,Redis也給出了方案Redis Cluster。
1.2 Redis Sentinel的高可用
Redis Sentinel是一個分布式架構,包含若干個Sentinel節點和Redis數據節點,每個Sentinel節點會對數據節點和其余Sentinel節點進行監控,當發現節點不可達時,會對節點做下線標識。
如果被標識的是主節點,他還會選擇和其他Sentinel節點進行“協商”,當大多數的Sentinel節點都認為主節點不可達時,他們會選舉出一個Sentinel節點來完成自動故障轉移工作,同時將這個變化通知給Redis應用方。
接下來我們就通過部署一個Redis Sentinel實例來了解整體框架。
2. Redis Sentinel部署
我們部署的拓撲結構如圖所示:
分別有3個Sentinel節點,1個主節點,2個從節點組成一個Redis Sentinel。
roleIPport
master127.0.0.16379
slave1127.0.0.16380
slave2127.0.0.16381
Sentinel1127.0.0.126379
Sentinel2127.0.0.126380
Sentinel3127.0.0.126381
2.1 啟動主節點
配置:
port 6379daemonize yes
logfile "6379.log"dbfilename "dump-6379.rdb"dir "/var/redis/data/"
啟動主節點
?? sudo redis-server redis-6379.conf
使用PING命令檢測是否啟動
?? redis-cli -h 127.0.0.1 -p 6379 ping
PONG
2.2 啟動兩個從節點
配置(兩個從節點配置相同,除了文件名有區分)
port 6380daemonize yes
logfile "6380.log"dbfilename "dump-6380.rdb"dir "/var/redis/data/"
slaveof 127.0.0.1 6379? ? ? // 從屬主節點
啟動兩個從節點
?? sudo redis-server redis-6380.conf
?? sudo redis-server redis-6381.conf
使用PING命令檢測是否啟動
?? redis-cli -h 127.0.0.1 -p 6380 ping
PONG
?? redis-cli -h 127.0.0.1 -p 6381 ping
PONG
主節點視角
?? redis-cli -h 127.0.0.1 -p 6379 INFO replication# Replicationrole:master
connected_slaves:2slave0:ip=127.0.0.1,port=6380,state=online,offset=85,lag=0slave1:ip=127.0.0.1,port=6381,state=online,offset=85,lag=0......
從節點視角(6380端口)
?? redis-cli -h 127.0.0.1 -p 6380 INFO replication# Replicationrole:slave
master_host:127.0.0.1master_port:6379master_link_status:up
......
確立中從關系,如下圖所示:
2.4 部署Sentinel節點
3個Sentinel節點的部署方法是相同的(端口不同)。以26379為例。
配置
// Sentinel節點的端口port 26379?
dir /var/redis/data/
logfile "26379.log"http:// 當前Sentinel節點監控 127.0.0.1:6379 這個主節點// 2代表判斷主節點失敗至少需要2個Sentinel節點節點同意// mymaster是主節點的別名sentinel monitor mymaster 127.0.0.1 6379 2//每個Sentinel節點都要定期PING命令來判斷Redis數據節點和其余Sentinel節點是否可達,如果超過30000毫秒且沒有回復,則判定不可達sentinel down-after-milliseconds mymaster 30000//當Sentinel節點集合對主節點故障判定達成一致時,Sentinel領導者節點會做故障轉移操作,選出新的主節點,原來的從節點會向新的主節點發起復制操作,限制每次向新的主節點發起復制操作的從節點個數為1sentinel parallel-syncs mymaster 1//故障轉移超時時間為180000毫秒sentinel failover-timeout mymaster 180000
啟動(兩種方法)?
redis-sentinel sentinel-26379.conf
redis-server sentinel-26379.conf --sentinel
sudo redis-sentinel sentinel-26379.conf --sentinel
確認
?? redis-cli -h 127.0.0.1 -p 26379 INFO Sentinel# Sentinelsentinel_masters:1sentinel_tilt:0sentinel_running_scripts:0sentinel_scripts_queue_length:0sentinel_simulate_failure_flags:0master0:name=mymaster,status=ok,address=127.0.0.1:6379,slaves=2,sentinels=1 //sentinels=1表示啟動了1個Sentinel
部署三個Sentinel節點之后,真個拓撲結構如圖所示:
當部署號Redis Sentinel之后,會有如下變化?
Sentinel節點自動發現了從節點、其余Sentinel節點。
去掉了默認配置,例如:parallel-syncs、failover-timeout。
新添加了紀元(epoch)參數。
我們拿端口26379的舉例,啟動所有的Sentinel和數據節點后,配置文件如下:
port 26379dir "/var/redis/data"sentinel myid 70a3e215c1a34b4d9925d170d9606e615a8874f2
sentinel monitor mymaster 127.0.0.1 6379 2sentinel config-epoch mymaster 0sentinel leader-epoch mymaster 0daemonize yes
logfile "26379.log"http:// 發現了兩個從節點sentinel known-slave mymaster 127.0.0.1 6381sentinel known-slave mymaster 127.0.0.1 6380// 發送了連個Sentinel節點sentinel known-sentinel mymaster 127.0.0.1 26381 e1148ad6caf60302dd6d0dbd693cb3448e209ac2
sentinel known-sentinel mymaster 127.0.0.1 26380 39db5b040b21a52da5334dd2d798244c034b4fc3
sentinel current-epoch
2.5 故障轉移實驗
先查看一下節點的進程pid
?? ps -aux | grep redis
root? ? 18225? 0.1? 0.0? 40208 11212 ?? ? ? ? Ssl? 22:10? 0:05 redis-server 127.0.0.1:6379root? ? 18234? 0.0? 0.0? 38160? 8364 ?? ? ? ? Ssl? 22:10? 0:04 redis-server 127.0.0.1:6380root? ? 18244? 0.0? 0.0? 38160? 8308 ?? ? ? ? Ssl? 22:10? 0:04 redis-server 127.0.0.1:6381root? ? 20568? 0.1? 0.0? 38160? 8460 ?? ? ? ? Ssl? 23:05? 0:02 redis-sentinel *:26379 [sentinel]
root? ? 20655? 0.1? 0.0? 38160? 8296 ?? ? ? ? Ssl? 23:07? 0:02 redis-sentinel *:26380 [sentinel]
root? ? 20664? 0.1? 0.0? 38160? 8312 ?? ? ? ? Ssl? 23:07? 0:02 redis-sentinel *:26381 [sentinel
?? sudo kill -9 18225?? ps -aux | grep redis
root? ? 18234? 0.0? 0.0? 38160? 8364 ?? ? ? ? Ssl? 22:10? 0:05 redis-server 127.0.0.1:6380root? ? 18244? 0.0? 0.0? 38160? 8308 ?? ? ? ? Ssl? 22:10? 0:05 redis-server 127.0.0.1:6381root? ? 20568? 0.1? 0.0? 38160? 8460 ?? ? ? ? Ssl? 23:05? 0:03 redis-sentinel *:26379 [sentinel]
root? ? 20655? 0.1? 0.0? 38160? 8296 ?? ? ? ? Ssl? 23:07? 0:03 redis-sentinel *:26380 [sentinel]
root? ? 20664? 0.1? 0.0? 38160? 8312 ?? ? ? ? Ssl? 23:07? 0:03 redis-sentinel *:26381 [sentinel]
此時,Redis Sentinel對主節點進行客觀下線(Objectively Down, 簡稱 ODOWN)的判斷,確認主節點不可達,則通知從節點中止復制主節點的操作。
當主節點下線時長超過配置的下線時長30000秒,Redis Sentinel執行故障轉移操作。
此時,我們查看一下Sentinel節點監控的主節點信息:
127.0.0.1:26379> sentinel masters 1)? 1) "name"? ? 2) "mymaster"? ? 3) "ip"? ? 4) "127.0.0.1"? ? 5) "port"? ? 6) "6380"? ? ? ? ? //可以看到主節點已經成為6380端口的節點? ? 7) "runid"? ? 8) "084850ab4ff6c2f2502b185c8eab5bdd25a26ce2"? ? 9) "flags"? 10) "master"? ? ..............
看一下Sentinel節點監控的從節點信息:
127.0.0.1:26379> sentinel slaves mymaster1)? 1) "name"? ? 2) "127.0.0.1:6379"? ? ? ? ? ? //ip:port? ? 3) "ip"? ? 4) "127.0.0.1"? ? 5) "port"? ? 6) "6379"? ? 7) "runid"? ? 8) ""? ? 9) "flags"? 10) "s_down,slave,disconnected"? //端口6379的原主節點已經斷開了連接? ..............2)? 1) "name"? ? 2) "127.0.0.1:6381"? ? ? ? ? ?
? ? 3) "ip"? ? 4) "127.0.0.1"? ? 5) "port"? ? 6) "6381"? ? 7) "runid"? ? 8) "24495fe180e4fd64ac47467e0b2652894406e9e4"? ? 9) "flags"? 10) "slave"? ? ? ? ? ? ? ? ? ? ? //本來的從節點,還是從節點的role? ? ..............
由以上信息可得,端口為6380的Redis數據節點成為新的主節點,端口為6379的舊主節點斷開連接。如圖所示:
我們在試著重啟端口6379的數據節點。
?? sudo redis-server redis-6379.conf
?? ps -aux | grep redis? ? ? ? ? ? ?
root? ? 18234? 0.1? 0.0? 40208 11392 ?? ? ? ? Ssl? 5月22? 0:06 redis-server 127.0.0.1:6380root? ? 18244? 0.1? 0.0? 40208 10356 ?? ? ? ? Ssl? 5月22? 0:07 redis-server 127.0.0.1:6381root? ? 20568? 0.1? 0.0? 38160? 8460 ?? ? ? ? Ssl? 5月22? 0:05 redis-sentinel *:26379 [sentinel]
root? ? 20655? 0.1? 0.0? 38160? 8296 ?? ? ? ? Ssl? 5月22? 0:05 redis-sentinel *:26380 [sentinel]
root? ? 20664? 0.1? 0.0? 38160? 8312 ?? ? ? ? Ssl? 5月22? 0:05 redis-sentinel *:26381 [sentinel]
menwen? 22475? 0.0? 0.0? 14216? 5920 pts/2? ? S+? 5月22? 0:00 redis-cli -p 26379// 6379的數據節點已重啟root? ? 22617? 0.0? 0.0? 38160? 8304 ?? ? ? ? Ssl? 00:00? 0:00 redis-server 127.0.0.1:6379?
看看發生什么:
127.0.0.1:26379> sentinel slaves mymaster1)? 1) "name"? ? 2) "127.0.0.1:6379"? ? //6379端口的節點重啟后,變成了"活"的從節點? ? 3) "ip"? ? 4) "127.0.0.1"? ? 5) "port"? ? 6) "6379"? ? 7) "runid"? ? 8) "de1b5c28483cf150d9550f8e338886706e952346"? ? 9) "flags"? 10) "slave"? ? ..............2)? 1) "name"? ? ? ? ? ? ? //6381端口的節點沒有變化,仍是從節點? ? 2) "127.0.0.1:6381"? ? ..............
他被降級成為端口6380的從節點。
從上面的邏輯架構和故障轉移試驗中,可以看出Redis Sentinel的以下幾個功能。
監控:Sentinel節點會定期檢測Redis數據節點和其余Sentinel節點是否可達。
通知:Sentinel節點會將故障轉移通知給應用方。
主節點故障轉移:實現從節點晉升為主節點并維護后續正確的主從關系。
配置提供者:在Redis Sentinel結構中,客戶端在初始化的時候連接的是Sentinel節點集合,從中獲取主節點信息。
3. Sentinel配置說明
sentinel monitor mymaster 127.0.0.1 6379 2
當前Sentinel節點監控 127.0.0.1:6379 這個主節點
2代表判斷主節點失敗至少需要2個Sentinel節點節點同意
mymaster是主節點的別名
sentinel down-after-milliseconds mymaster 30000
每個Sentinel節點都要定期PING命令來判斷Redis數據節點和其余Sentinel節點是否可達,如果超過30000毫秒且沒有回復,則判定不可達
sentinel parallel-syncs mymaster 1
當Sentinel節點集合對主節點故障判定達成一致時,Sentinel領導者節點會做故障轉移操作,選出新的主節點,原來的從節點會向新的主節點發起復制操作,限制每次向新的主節點發起復制操作的從節點個數為1。
sentinel failover-timeout mymaster 180000
故障轉移超時時間為180000
sentinel auth-pass \ \?
如果Sentinel監控的主節點配置了密碼,可以通過sentinel auth-pass配置通過添加主節點的密碼,防止Sentinel節點無法對主節點進行監控。
例如:sentinel auth-pass mymaster MySUPER--secret-0123passw0rd
sentinel notification-script \ \?
在故障轉移期間,當一些警告級別的Sentinel事件發生(指重要事件,如主觀下線,客觀下線等)時,會觸發對應路徑的腳本,想腳本發送相應的事件參數。
例如:sentinel notification-script mymaster /var/redis/notify.sh
sentinel client-reconfig-script \ \?
在故障轉移結束后,觸發應對路徑的腳本,并向腳本發送故障轉移結果的參數。
例如:sentinel client-reconfig-script mymaster /var/redis/reconfig.sh。