1. 程式人生 > >Redis哨兵模式(Sentinel)的搭建

Redis哨兵模式(Sentinel)的搭建

事件 配置 切換 通過 發送消息 無法訪問 etc 一個 pub

一、Redis的哨兵模式

Sentinel是Redis官方提供的一種高可用方案(除了Sentinel,Redis Cluster是另一種方案),它可以自動監控Redis master/slave的運行狀態,如果發現master無法訪問了,就會啟動failover把其中一臺可以訪問的slave切換為master,並且通過pub/sub事件通知Redis客戶端新的master的ip地址。

支持Sentinel的Redis客戶端(例如java的Jedis)會在連接Redis服務器的時候向Sentinel詢問master的ip,並且會在收到master切換的pub/sub事件後自動重新連接到新的master。對調用Redis客戶端的業務系統來說,這些都是完全透明的。通過設置一組哨兵sentinel,監控Master的運行,當Master不可用時,自動完成上述的動作,而不需人工幹預。下圖就是哨兵模式。每個哨兵sentinel會向其它sentinal、master、slave定時發送消息,以確認對方是否“活”著,如果發現對方在指定時間(可配置)內未回應,則暫時認為對方已掛(所謂的“主觀認為宕機” Subjective Down,簡稱SDOWN)。

技術分享

若“哨兵群”中的多數sentinel,都報告某一master沒響應,系統才認為該master"徹底死亡"(即:客觀上的真正down機,Objective Down,簡稱ODOWN),通過一定的vote算法,從剩下的slave節點中,選一臺提升為master,然後自動修改相關配置。

技術分享

1、當redis master down了以後

2、監控到N個sentinel無法訪問master

3、哨兵進程發起投票啟動failover,投票結果為由其中一個哨兵進程發起failover

4、更新sentinel和slave的配置,將slave升級成master

5、向JedisClient發送master切換事件,jedis將訪問新的master

二、Redis3.2.3哨兵模式的配置

兩臺機器:12.99.105.205和12.99.105.206;

一主一從:master 12.99.105.205:6379,slave 12.99.105.206:6379;

三個哨兵進程:12.99.105.205:26379,12.99.105.206:26379,12.99.105.206:26380。

使用root用戶 修改 /etc/security/limits.conf文件,新增以下信息

redis hard nofile  30000
redis soft  nofile  30000

使用/usr/local/redis-3.2.3/data/作為數據目錄,分配100G以上的空間

master

的配置

daemonize yes
port 6379
pidfile "/usr/local/redis-3.2.3/data/redis.pid"
tcp-keepalive 60
logfile "usr/lcoal/redis-3.2.3/logs/redis.log"
dir "/user/local/redis-3.2.3/data"
masterauth "123456"
requirepass "123456"
appendonly yes

slave的配置

daemonize yes
port 6379
pidfile "/usr/local/redis-3.2.3/data/redis.pid"
tcp-keepalive 60
logfile "usr/lcoal/redis-3.2.3/logs/redis.log"
dir "/user/local/redis-3.2.3/data"
masterauth "123456"
requirepass "123456"
appendonly yes
slaveof 12.99.105.205 6379

slave與master的配置區別在於slave多了一行”slaveof 12.99.105.205 6379”。

12.99.105.205哨兵的配置為

port 26379
daemonize yes
pidfile "/usr/local/redis-3.2.3/data/sentinel.pid"
logfile "/usr/local/redis-3.2.3/sentinel.log"
protected-mode no
sentinel monitor mymaster 12.99.105.205 6379 2

12.99.105.206哨兵1的配置為

port 26379
daemonize yes
pidfile "/usr/local/redis-3.2.3/data/sentinel.pid"
logfile "/usr/local/redis-3.2.3/sentinel.log"
protected-mode no
sentinel monitor mymaster 12.99.105.205 6379 2

12.99.105.206哨兵2的配置為

port 26380
daemonize yes
pidfile "/usr/local/redis-3.2.3/data/sentinel.pid"
logfile "/usr/local/redis-3.2.3/sentinel.log"
protected-mode no
sentinel monitor mymaster 12.99.105.205 6379 2

哨兵的配置是一樣的,唯一的區別是端口的差異。

sentinel monitor mymaster 12.99.105.205 6379 2

這一行的配置是最重要的,表示它監聽的是哪個master,2表示3個哨兵中有2個哨兵認為符合啟動failover的條件,才會啟動failover,防止失誤。

Java應用連接redis3.2.3主從集群需要使用commons-pool2-2.2.jar和jedis-2.8.0.jar,

Redis連接池初始化的代碼如下,由於sentinel知道關於主從集群的一切信息(包括哪個是master,哪個slave),所以連接池初始化時,只需要把哨兵的信息傳進去就可以了。

 1 Set<String> sentinelSet = new HashSet<String>();
 2 String[] sentinels = new String[]{"12.99.105.205:26379","12.99.105.206:26379","12.99.105.206:26380"};
 3 for(int i=0;i<sentinels.length;i++){
 4     sentinelSet.add(sentinels[i]);
 5 }
 6 String masterName="mymaster";
 7 String password="123456";
 8 int timeout=2000;
 9 
10 JedisPoolConfig poolConfig=new JedisPoolConfig();
11 poolConfig.setMaxTotal(300);
12 poolConfig.setMaxIdle(200);
13 poolConfig.setTestOnBorrow(true);
14 poolConfig.setTestWhileIdle(false);
15 
16 Pool<Jedis> pool = new JedisSentinelPool(masterName,sentienlSet,poolConfig,timeout,password);

三、Redis3.2.3哨兵模式的驗證

測試程序應用通過Jedis不斷地向redis主從集群set和get,當kill掉redis master 的進程,應用會出現短暫的報錯(約30到40秒),之後又恢復正常。在這30~40秒的時間內,哨兵進程發起failover,更新sentinel、slave和原master的配置,將slave升級成master。

Redis哨兵模式(Sentinel)的搭建