1 哨兵工作机制 1.1 环境架构
每个哨兵节点,每 10 秒向已知的各个主从节点发送 info 命令,获取最新的拓扑结构关系和各个节点详细信息;
每个哨兵节点每 1 秒向它已知的 Master、Slave 节点以及其他哨兵节点发送一个 ping 命令,从最后一次成功响应的时间开始,超过 down-after-milliseconds 设置的时间,则监测的哨兵标记为下线;
如果一个 Master 节点被哨兵标记为下线,其它所有哨兵节点再次每秒 1 个 ping,未收到 pong 则确认下线,进入主观下线状态;
确认 Master 主观下线的哨兵节点数,如果达到配置参数的值,则 Master 节点进入正式客观下线;
如果确认 Master 主管下线的哨兵节点数,达不到配置的值,客观下线状态移除;
如果哨兵节点能重新与 Master 节点进行 ping-pong ,主观下线状态移除。
1.2 为什么要用哨兵集群
防止误判:对于节点的故障判断是由多个 Sentinel 节点共同完成。
高可靠:即使个别 Sentinel 节点不可用,整个 Sentinel 节点集合依然是健壮的。
1.3 Leader 选举流程 每个哨兵都有机会成为 leader 负责故障转移,哨兵节点之间相互请求,选举自身为 leader,每个哨兵节点必须同意或拒绝投票,当一个哨兵节点的投票数达到 哨兵总数 / 2 + 1 时,则选为 leader 负责故障转移。
1.4 故障转移
负责故障转移的哨兵节点会按以下步骤选择 Master 节点:
将现有节点拓扑结构中下线的节点过滤掉;
在剩余的从节点中,选择 replica-priority(5.0 之前的 slave-priority)参数最小的节点作为 Master,0 代表不参与选举;
如果未选出,则根据复制偏移量,选择最大的节点,复制偏移量越大代表数据越完整;
若仍未选出,则根据 redis 运行时生成的随机 run id,选择最小 id 节点作为 Master。
选择出 Master 之后,改变其它节点的主从关系,并重写配置,使得主从关系的持久化;并依据新的 Master 节点的数据,使其它节点进行数据同步。
2 主从部署
一般来说,主从模式至少 1 个 master+2 个 slave 节点
主节点 6379,从节点 6380/6381,哨兵节点 4001/4002/4003 (详细配置参考 )
2.1 Master 节点 2.1.1 配置 cat redis_6379.conf
1 2 3 4 5 6 7 8 9 10 bind 10.1.1.1port 6379 requirepass qweasd masterauth qweasd daemonize yes pidfile /var/run/redis_6379.pid dir /opt/redis/redis_6379dbfilename 6379_dump.rdb
2.1.2 启动 1 2 cd /opt/redissrc/redis-server redis_6379.conf
2.2 Slave 节点 2.2.1 配置 cat redis_6380.conf redis_6381.conf
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 bind 10.1.1.1port 6380 masterauth qweasd masterauth qweasd replicaof 10.1.1.1 6379 daemonize yes pidfile /var/run/redis_6380.pid dir /opt/redis/redis_6380dbfilename 6380_dump.rdb
2.2.2 启动
分别启动 2 个从节点,默认从节点只读
1 2 3 cd /opt/redissrc/redis-server redis_6380.conf src/redis-server redis_6381.conf
2.3 查看日志 2.3.1 Master 主节点,同步信息 1 2 3 4 5 6 7 8 9 1487:M 31 May 2022 04:46:16.774 * Replica 10.1.1.1:6379 asks for synchronization 1487:M 31 May 2022 04:46:16.774 * Full resync requested by replica 10.1.1.1:6379 ...... 1487:M 31 May 2022 04:46:16.894 * Synchronization with replica 10.1.1.1:6379 succeeded ...... 1487:M 31 May 2022 04:46:18.738 * Replica 10.1.1.1:6380 asks for synchronization 1487:M 31 May 2022 04:46:18.738 * Full resync requested by replica 10.1.1.1:6380 ...... 1487:M 31 May 2022 04:46:18.805 * Synchronization with replica 10.1.1.1:6380 succeeded
2.3.2 Slave 从节点信息 1 2 3 4 5 6 7 8 9 1491:S 31 May 2022 04:46:18.734 * Connecting to MASTER 10.1.1.1:6379 1491:S 31 May 2022 04:46:18.735 * MASTER <-> REPLICA sync started 1491:S 31 May 2022 04:46:18.737 * Master replied to PING, replication can continue ...... 1491:S 31 May 2022 04:46:18.754 * Full resync from master: cd06ef23f36a4b98e0b0126d04d667b5ec6031ce:0 1491:S 31 May 2022 04:46:18.805 * MASTER <-> REPLICA sync : receiving 176 bytes from master to disk 1491:S 31 May 2022 04:46:18.807 * MASTER <-> REPLICA sync : Flushing old data 1491:S 31 May 2022 04:46:18.810 * MASTER <-> REPLICA sync : Loading DB in memory 1491:S 31 May 2022 04:46:18.825 * MASTER <-> REPLICA sync : Finished with success
2.4 查看集群状态
使用 redis-cli 连接 master 查看信息如下:
1 2 3 4 5 6 7 10.1.1.1:6379> info replication role:master connected_slaves:2 slave0:ip=10.1.1.1,port=6380,state=online,offset=1484,lag=1 slave1:ip=10.1.1.1,port=6381,state=online,offset=1484,lag=0 ...
3 哨兵部署 3.1 配置
哨兵配置 sentinel_4001.conf、sentinel_4002.conf、sentinel_4003.conf
只需配置 master 节点地址,自动获取整个拓扑关系。
1 2 3 4 5 6 7 8 9 10 11 12 bind 10.1.1.1port 4001 daemonize yes sentinel monitor sineMaster 10.1.1.1 6379 2 sentinel auth-pass sineMaster qweasd sentinel down-after-milliseconds sineMaster 3000 dir /opt/redis/sentinel_4001
3.2 启动 3 个哨兵节点 1 2 3 4 cd /opt/redissrc/redis-sentinel sentinel_4001.conf src/redis-sentinel sentinel_4002.conf src/redis-sentinel sentinel_4003.conf
3.3 查看日志 1 2 3 4 5 6 1496:X 31 May 2022 05:09:03.984 1496:X 31 May 2022 05:09:03.984 1496:X 31 May 2022 05:09:03.987 * +slave slave 10.1.1.1:6379 10.1.1.1 6379 @ sineMaster 10.1.1.1 6379 1496:X 31 May 2022 05:09:03.992 * +slave slave 10.1.1.1:6380 10.1.1.1 6380 @ sineMaster 10.1.1.1 6379 1496:X 31 May 2022 05:09:04.380 * +sentinel sentinel ee753589ab5dea31a568e33eeee5aaf8366ebede 10.1.1.1 4002 @ sineMaster 10.1.1.1 6379 1496:X 31 May 2022 05:09:05.393 * +sentinel sentinel cbc1e91f109f153d0a2b49d81b039af57ad27309 10.1.1.1 4001 @ sineMaster 10.1.1.1 6379
3.4 查看哨兵集群状态 src/redis-cli -h 10.1.1.1 -p 4001
1 2 3 4 5 6 7 8 10.1.1.1:4001> info sentinel sentinel_masters:1 sentinel_tilt:0 sentinel_running_scripts:0 sentinel_scripts_queue_length:0 sentinel_simulate_failure_flags:0 master0:name=sineMaster,status=ok,address=10.1.1.1:6379,slaves=2,sentinels=3
4 集群维护 4.1 添加 slve 节点 4.1.1 新增 6382 配置文件 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 bind 10.1.1.1port 6382 requirepass "qweasd" masterauth "qweasd" daemonize yes pidfile "/var/run/redis_6382.pid" dbfilename "6382_dump.rdb" dir "/opt/redis/redis_6382" save 3600 1 save 300 100 save 60 10000 user default on nopass sanitize-payload ~* &* +@all replicaof 10.1.1.1 6380
4.1.2 启动 src/redis-server redis_6382.conf
4.1.3 查看节点信息
数据会自动同步
1 2 3 4 5 6 7 8 9 10 10.1.1.1:6382> keys * 1) "str1" 2) "str3" 3) "str4" 4) "str2" 10.1.1.1:6382> info replication role:slave master_host:10.1.1.1 master_port:6380
4.2 master 节点下线维护 4.2.1 数据手动落盘 src/redis-cli -h 10.1.1.1 -p 6380 -a qweasd save
4.2.2 手动切换节点 1 2 3 4 5 6 7 8 9 10.1.1.1:4001> info sentinel sentinel_masters:1 sentinel_tilt:0 sentinel_running_scripts:0 sentinel_scripts_queue_length:0 sentinel_simulate_failure_flags:0 master0:name=sineMaster,status=ok,address=10.1.1.1:6380,slaves=3,sentinels=3 10.1.1.1:4001> sentinel failover sineMaster
4.2.3 查看新 master 节点 1 2 3 4 5 6 7 8 10.1.1.1:4001> info sentinel sentinel_masters:1 sentinel_tilt:0 sentinel_running_scripts:0 sentinel_scripts_queue_length:0 sentinel_simulate_failure_flags:0 master0:name=sineMaster,status=ok,address=10.1.1.1:6379,slaves=3,sentinels=3
4.2.4 查看 Redis 集群状态 1 2 3 4 5 6 7 8 info replication role:master connected_slaves:3 slave0:ip=10.1.1.1,port=6382,state=online,offset=2502699,lag=0 slave1:ip=10.1.1.1,port=6381,state=online,offset=2502563,lag=1 slave2:ip=10.1.1.1,port=6380,state=online,offset=2502563,lag=1 ...
4.2.5 测试数据 (可不操作直接进行下一步) 4.2.5.1 新 master 节点写入数据 1 2 10.1.1.1:6379> set str5 str5 OK
4.2.5.2 slave 节点查看数据 1 2 3 4 5 6 10.1.1.1:6382> keys * 1) "str3" 2) "str5" 3) "str4" 4) "str1" 5) "str2"
4.2.6 停掉原来的 master 节点 src/redis-cli -h 10.1.1.1 -p 6380 -a qweasd SHUTDOWN
5 高可用测试 5.1 主从同步测试 5.1.1 master 写入数据 1 2 3 4 5 6 7 8 src/redis-cli -h 10.1.1.1 -p 6379 -a qweasd Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe. 10.1.1.1:6379> set str1 str1 OK 10.1.1.1:6379> set str2 str2 OK 10.1.1.1:6379> set str3 str3 OK
5.1.2 查看 slave 节点 5.1.2.1 6380 1 2 3 4 10.1.1.1:6380> keys * 1) "str2" 2) "str1" 3) "str3"
5.1.2.2 6381 1 2 3 4 10.1.1.1:6381> keys * 1) "str3" 2) "str2" 3) "str1"
5.2 主从切换测试 5.2.1 停掉 master src/redis-cli -h 10.0.16.12 -p 6379 -a qweasd SHUTDOWN
5.2.2 查看哨兵状态
可以看到 Sentinel 配置的 master 节点会自动切换成新的 ip (命令参考 )
1 2 3 4 5 6 7 8 info sentinel sentinel_masters:1 sentinel_tilt:0 sentinel_running_scripts:0 sentinel_scripts_queue_length:0 sentinel_simulate_failure_flags:0 master0:name=sineMaster,status=ok,address=10.1.1.1:6380,slaves=2,sentinels=3
5.2.3 查看 Redis 状态
slave 节点会自动切换到新的 master 节点
1 2 3 4 5 6 10.1.1.1:6380> info replication role:master connected_slaves:1 slave0:ip=10.1.1.1,port=6381,state=online,offset=2135687,lag=0 ...
5.2.4 新 master 节点写入数据 1 2 10.1.1.1:6380> set str4 str4 OK
5.2.5 slave 节点查看数据
数据已经同步过来
1 2 3 4 5 10.1.1.1:6381> keys * 1) "str4" 2) "str3" 3) "str1" 4) "str2"
5.2.6 启动停掉的旧 master 节点
数据已经同步过来,并且自动修改 master 节点 ip,这里要注意,密码不会自动修改,需要配置提前加入masterauth 参数
1 2 3 4 5 6 7 8 9 10 11 10.1.1.1:6379> keys * 1) "str1" 2) "str4" 3) "str2" 4) "str3" 10.1.1.1:6379> info replication role:slave master_host:10.1.1.1 master_port:6380 master_link_status:up
5.2.7 查看配置文件
每一次故障转移,哨兵都会使各个节点的配置文件同步改变,无需人工干预维持主从关系。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 sentinel_4001.conf bind 10.1.1.1port 4001 daemonize yes sentinel monitor sineMaster 10.1.1.1 6380 2 sentinel auth-pass sineMaster qweasd sentinel down-after-milliseconds sineMaster 3000 dir "/opt/redis/sentinel_4001" protected-mode no pidfile "/var/run/redis.pid" user default on nopass sanitize-payload ~* &* +@all sentinel myid 444785ae34de834b920cedec95eb5425f873a2f2 sentinel config-epoch sineMaster 5 sentinel leader-epoch sineMaster 5 sentinel current-epoch 5 sentinel known-replica sineMaster 10.1.1.1 6379 sentinel known-replica sineMaster 10.1.1.1 6381 sentinel known-sentinel sineMaster 10.1.1.1 4003 872820ad14a3d0a4bfaf2ad79d18e0137f07b704 sentinel known-sentinel sineMaster 10.1.1.1 4002 7a985407acebebce1163cef703475e1074981a93 redis_6379.conf bind 10.1.1.1port 6379 requirepass "qweasd" daemonize yes pidfile "/var/run/redis_6379.pid" dbfilename "6379_dump.rdb" masterauth qweasd save 3600 1 save 300 100 save 60 10000 user default on sanitize-payload dir "/opt/redis" replicaof 10.1.1.1 6380 cat redis_6380.confbind 10.1.1.1port 6380 masterauth "qweasd" requirepass "qweasd" daemonize yes pidfile "/var/run/redis_6380.pid" dbfilename "6380_dump.rdb" dir "/opt/redis/redis_6380" save 3600 1 save 300 100 save 60 10000 user default on
6 备份与恢复 参考: Redis备份与恢复 ]