redis sentinel配置及使用说明

redis sentinel 可以实现对redis的监控、通知、自动故障转移,支持分布式。项目中使用此工具来解决redis单点问题,特此记录测试流程,如有问题,大家共同讨论!

基础知识:
redis sentinel官方文档(推荐):https://redis.io/topics/sentinel
中文blog:http://debugo.com/redis-sentinel/

测试环境

服务器:

  • ip: 192.168.2.230, 系统: centos, 服务: redis master && sentinel
  • ip: 192.168.2.231, 系统: centos, 服务: redis slave && sentinel
  • ip: 192.168.2.232, 系统: centos, 服务: redis slave && sentinel
  • ip: 192.168.2.233, 系统: centos, 服务: redis slave

redis相关版本:

  • redis server 3.2.3
  • python 2.7
  • redis-py 2.10.5

初始配置图解

mahua

说明:
(1). redis主服务在192.168.2.230服务器上,其他服务器均配置为其redis从服务器
(2). sentinel配置了3个服务(可以配置3个以上),均监控redis master服务
(3). 要保证三台服务器之间端口”6379”、”26379”均能正常通信
(4). 由于业务需求,192.168.2.233 redis slave节点不作为备用master节点,通过配置其slave-priority为0实现(在redis master挂掉以后,sentinel会根据slave-priority配置值的大小推荐哪个redis从节点作为master,此值越小则优先被推荐为master节点。且此值如果为0,则不会被推荐。默认值为100)

配置启动redis服务

(1). 各个机器分别安装redis(自带sentinel)

1
sudo yum install redis

(2). 192.168.2.230服务器上redis master修改如下配置(/etc/redis.conf)

1
2
3
bind 192.168.2.230 127.0.0.1
requirepass changeme
masterauth changeme # redis master也可能成为从节点,此配置也是要的

(3). 192.168.2.231服务器上redis slave修改如下配置(/etc/redis.conf)

1
2
3
4
bind 192.168.2.231 127.0.0.1
slaveof 192.168.2.230 6379
requirepass changeme
masterauth changeme

(4). 192.168.2.232服务器上redis slave修改如下配置(/etc/redis.conf)

1
2
3
4
bind 192.168.2.232 127.0.0.1
slaveof 192.168.2.230 6379
requirepass changeme
masterauth changeme

(5). 192.168.2.233服务器上redis slave修改如下配置(/etc/redis.conf)

1
2
3
4
5
bind 192.168.2.233 127.0.0.1
slaveof 192.168.2.230 6379
requirepass changeme
masterauth changeme
slave-priority 0 # 此配置保证此redis从节点不会被选举为主节点

(6). 各个机器分别启动redis服务

1
sudo service redis start

此时在192.168.2.230服务器的/var/log/redis/redis.log出现如下内容,则说明上面的redis主从服务配置成功

1
2
3
Synchronization with slave 192.168.2.231:6379 succeeded
Synchronization with slave 192.168.2.232:6379 succeeded
Synchronization with slave 192.168.2.233:6379 succeeded

(7). 192.168.2.230、192.168.2.231、192.168.2.232服务器上分别配置sentinel(/etc/redis-sentinel.conf)

1
2
3
4
5
6
7
sentinel monitor mymaster 192.168.2.230 6379 2
#(注意下面的配置一定要在上面的配置之后)
sentinel auth-pass mymaster changeme
sentinel down-after-milliseconds mymaster 60000
sentinel failover-timeout mymaster 180000
sentinel parallel-syncs mymaster 1
protected-mode no # 为了redis client能内网连接操作redis-sentinel

(8). 192.168.2.230、192.168.2.231、192.168.2.232服务器上分别启动sentinel

1
sudo service redis-sentinel start

此时在192.168.2.230服务器的/var/log/redis/sentinel.log出现类似如下内容,则说明上面的sentinel服务配置成功

1
2
3
4
5
6
7
Sentinel ID is a4b9821ce265f66d4c4787f4d2fa499e85bbfcfd
+monitor master mymaster 192.168.2.230 6379 quorum 2
+slave slave 192.168.2.231:6379 192.168.2.231 6379 @ mymaster 192.168.2.230 6379
+slave slave 192.168.2.232:6379 192.168.2.232 6379 @ mymaster 192.168.2.230 6379
+slave slave 192.168.2.233:6379 192.168.2.233 6379 @ mymaster 192.168.2.230 6379
+sentinel sentinel 6a5109657d32acd9ffff672d0f0907d34514b430 192.168.2.231 26379 @ mymaster 192.168.2.230 6379
+sentinel sentinel 7bac9c6484c13b9a58faed40153c1e7e2f481bfd 192.168.2.232 26379 @ mymaster 192.168.2.230 6379

这里注意如果出现类似如下内容的log(+sdown)可能是因为centos上的防火墙问题,重新配置自己的防火墙规则后可以修复(测试环境下可以先关闭防火墙)

1
+sdown slave 192.168.2.233:6379 192.168.2.233 6379 @ mymaster 192.168.2.230 6379

查看服务信息

(1). 查看sentinel监控的redis master服务

1
2
redis-cli -h 192.168.2.230 -p 26379
192.168.2.230:26379>sentinel masters

(2). 查看redis master的所有从服务

1
2
redis-cli -h 192.168.2.230 -p 26379
192.168.2.230:26379>sentinel slaves mymaster

redis client操作(以python为例)

(1). 安装redis

1
pip install redis

(2). 操作

1
2
3
4
5
6
7
8
9
10
11
12
>>> from redis.sentinel import Sentinel
>>> sentinel = Sentinel([('192.168.2.230', 26379), ('192.168.2.231', 26379), ('192.168.2.232', 26379)], socket_timeout=0.1)
>>> sentinel.discover_master('mymaster')
('192.168.2.230', 6379)
>>> sentinel.discover_slaves('mymaster')
[('192.168.2.233', 6379), ('192.168.2.232', 6379), ('192.168.2.231', 6379)]
>>> master = sentinel.master_for('mymaster', password='changeme', socket_timeout=0.1)
>>> slave = sentinel.slave_for('mymaster', password='changeme', socket_timeout=0.1)
>>> master.set('foo', 'bar')
True
>>> slave.get('foo')
'bar'

=================================== 华丽的分割线 ========================================
=================================== 华丽的分割线 ========================================
=================================== 华丽的分割线 ========================================

测试redis master挂掉后主从切换

(1). 在192.168.2.230服务器上停掉redis master服务

1
sudo service redis stop

此时查看个服务器上的/var/log/redis/sentinel.log可以很清楚一次主从切换的过程

使用python client查看此时的redis服务状态(也可以使用sentinel里面的命令查看: “sentinel masters”,”sentinel slaves mymaster”)

1
2
3
4
5
6
7
8
9
10
11
12
>>> from redis.sentinel import Sentinel
>>> sentinel = Sentinel([('192.168.2.230', 26379), ('192.168.2.231', 26379), ('192.168.2.232', 26379)], socket_timeout=0.1)
>>> sentinel.discover_master('mymaster')
('192.168.2.232', 6379)
>>> sentinel.discover_slaves('mymaster')
[('192.168.2.231', 6379), ('192.168.2.233', 6379)]
>>> master = sentinel.master_for('mymaster', password='changeme', socket_timeout=0.1)
>>> slave = sentinel.slave_for('mymaster', password='changeme', socket_timeout=0.1)
>>> master.set('foo', 'bar1')
True
>>> slave.get('foo')
'bar1'

可以知道此时redis master已经切换到192.168.2.232服务器,而redis slave已经指向新的redis master

(3). 在192.168.2.230服务器上再启动redis服务

1
sudo service redis start

此时/var/log/redis/sentinel.log中只有简单的一条信息如下:
-sdown slave 192.168.2.230:6379 192.168.2.230 6379 @ mymaster 192.168.2.232 6379
表示192.168.2.230上的redis以从服务的身份重新加入了,redis master仍为192.168.2.232

使用python client查看此时的redis服务状态(也可以使用sentinel里面的命令查看: “sentinel masters”,”sentinel slaves mymaster”)

1
2
3
4
5
6
7
8
9
10
11
12
>>> from redis.sentinel import Sentinel
>>> sentinel = Sentinel([('192.168.2.230', 26379), ('192.168.2.231', 26379), ('192.168.2.232', 26379)], socket_timeout=0.1)
>>> sentinel.discover_master('mymaster')
('192.168.2.232', 6379)
>>> sentinel.discover_slaves('mymaster')
[('192.168.2.230', 6379), ('192.168.2.231', 6379), ('192.168.2.233', 6379)]
>>> master = sentinel.master_for('mymaster', password='changeme', socket_timeout=0.1)
>>> slave = sentinel.slave_for('mymaster', password='changeme', socket_timeout=0.1)
>>> master.set('foo', 'bar2')
True
>>> slave.get('foo')
'bar2'

坚持原创技术分享,您的支持将鼓励我继续创作!

热评文章