使用 redis-sentinel 实现 Redis 高可用集群

一、redis 和 redis-sentinel 启动时配置目录权限的配置问题(redis采用yum安装,不要用root用户运行redis)

  • PID文件放置目录的权限(/var/run/redis/)权限改为属主属组都是redis
  • /etc/redis-sentinel.conf:属主属组都改为redis,因为redis-sentinel服务启动后需要修改这个配置文件,没权限的话服务启动不了。

二、架构及redis主从配置说明

master:192.168.11.10:6379
slave1:192.168.11.12:6379
slave2:192.168.11.13:6379

# redis.conf
bind 0.0.0.0
protected-mode yes
port 6379
daemonize yes
pidfile /var/run/redis/redis.pid
logfile /var/log/redis/redis.log
stop-writes-on-bgsave-error yes
rdbcompression yes #是否压缩持久化文件
rdbchecksum no #是否进行文件md5检测
dbfilename dump.rdb
dir /var/lib/redis
slave-serve-stale-data yes
slave-read-only yes
requirepass redis_pass
appendonly yes             #该选项要打开,RDB模式服务器异常时可能会丢失部分数据,涉及到redis的两种持久化方式的区别,分别是RDB和AOF模式
appendfilename "appendonly.aof"
appendfsync everysec

##############################
#从服务器上加上这两条,主服务器上要把masterauth加上,不让主服务器挂掉后变成从服务器再同步主服务器后会失败
slaveof 192.168.11.10 6379
masterauth redis_pass

reids 主从做好后在主服务器上连接redis执行 info replication 可以看到如下结果

三、redis-sentinel 配置

#三个主机的 redis-sentine.conf 配置文件基本一致
# /etc/redis-sentinel.conf

protected-mode yes # redis3.2的安全设置,没有设置密码是禁止远程连接
port 26379
sentinel myid dc91b154679b125aecbe3b04b54882dfc76f3ff9 #本机ID,每一个sentinel不要把ID设置的一样
sentinel monitor def_master 192.168.11.10 6379 2 #告诉sentinel去监听的地址,'def_master' 为master的名字,可以自定义。数字2表示当有几个sentinel认为master失效时,master才失效
sentinel failover-timeout def_master 900000
sentinel auth-pass def_master redis_pass #设置slave和master的链接密码,主从密码要一致
sentinel config-epoch def_master 5 #故障转移后,最多有多少个从服务器可以同步数据,越少重新同步越快
dir '/tmp'

sentinel正常启动后连接sentinel的端口,执行 info sentinel 会看到以下结果


主从状况

停掉redis主服务器的服务后,主服务转到192.168.11.13这台服务器,并且192.168.11.12的同步服务器变为192.168.11.13


再把10上的redis服务启动,13也开始向10进行数据同步

三、使用VIP漂移解决 redis server IP 不固定的问题

  这里可以使用redis sentinel的一个参数client-reconfig-script,这个参数配置执行脚本,sentinel在做failover的时候会执行这个脚本,并且传递6个参数<master-name>、 <role>、 <state>、 <from-ip>、 <from-port>、 <to-ip> 、<to-port>,其中<to-ip>是新主redis的IP地址,可以在这个脚本里做VIP漂移操作

# vi /var/lib/redis/failover.sh
#!/bin/bash
set -u
set -e

MASTER_IP=${6}
MY_IP='192.168.11.12'   # 每个Server本身的IP
VIP='192.168.11.100'     # VIP
NETMASK='24'          # Netmask
INTERFACE='eth0'      # 接口
echo $INTERFACE

if [ ${MASTER_IP} = ${MY_IP} ]; then
    sudo /sbin/ip addr add ${VIP}/${NETMASK} dev ${INTERFACE}
    sudo /sbin/arping -q -c 3 -A ${VIP} -I ${INTERFACE}
    exit 0
else
    sudo /sbin/ip addr del ${VIP}/${NETMASK} dev ${INTERFACE}
    exit 0
fi
exit 1

  赋予脚本执行权限并且添加redis用户对于ip,和arping命令的sudo权限

chmod 755 /var/lib/redis/failover.sh
chown redis: /var/lib/redis/failover.sh
echo -e "redis\tALL=(ALL)\tNOPASSWD:/sbin/ip,NOPASSWD:/sbin/arping" >> /etc/sudoers

  最后开启redis-sentinel并且初次手动设置VIP。(测试后client-reconfig-script这个参数好像没有触发,最后自己写了个VIP漂移脚本解决了这个问题)

#########################################################################
# File Name: /var/lib/redis/failover.sh
# Author: lcs
# mail: liuchengsheng95@qq.com
# Created Time: 2018-04-07 15:38:33
#########################################################################
# 一定要用root用户运行
#!/bin/bash
MY_IP='192.168.11.16'   # 每个Server本身的IP
VIP='192.168.11.100'     # VIP
NETMASK='24'          # Netmask
INTERFACE='eth1'      # 接口

while true;do
    MASTER_IP=$(redis-cli -h 127.0.0.1 -p 26379 info sentinel | grep address | cut -d, -f3 | cut -d= -f2 | cut -d: -f1)
    if [ ${MASTER_IP} = ${MY_IP} ]; then
        ip -4 addr | grep $VIP || (/sbin/ip addr add ${VIP}/${NETMASK} dev ${INTERFACE};/sbin/arping -q -c 3 -A ${VIP} -I ${INTERFACE})
    else
        ip -4 addr | grep $VIP && /sbin/ip addr del ${VIP}/${NETMASK} dev ${INTERFACE}
    fi
    sleep 10;
done

推荐阅读更多精彩内容

  • 前言 Redis是一个高性能的key-value数据库,现时越来越多企业与应用使用Redis作为缓存服务器。楼主是...
    liangzzz阅读 2,937评论 9 147
  • 一、单个实例 当系统中只有一台redis运行时,一旦该redis挂了,会导致整个系统无法运行。 二、备份 由于单台...
    zhou阅读 19,924评论 9 96
  • 关键词:redis 、 sentinel(哨兵模式)、keepalived 一、Redis单实例 当系统中只运行一...
    fantasymango阅读 3,218评论 1 25
  • 1- 水平分区 VS 垂直分区 分区是分割数据到多个Redis实例的处理过程,因此每个实例只保存key的一个子集。...
    zhanglbjames阅读 2,680评论 0 3
  • 我是那种走路急匆匆的人,所以,总有与人相撞的事出现。 大多时候,彼此就这么走过。有时,我会说:不好意思。但也仅仅是...
    张金刚阅读 17评论 0 0