目录
在一主多从的Redis架构中,从节点可以起到数据冗余备份和读写分离的作
用。如果主节点遇到故障导致无法提供服务时,可以采用手动方式将其一个从节
点提升为主节点,保证Redis主从能够正常工作。主从切换通过手动完成比较耗
时、费力,并且影响Redis正常服务。为此,Reids提供了哨兵兵功能,实现了自
动化的系统监控和故障恢复功能。哨兵(Sentinel),主要负责监控主从节点运行是否正常,以及当主节点出现故障时自动将一个从节点转换为新的主节点。哨兵是一个独立的进程。,最基础的通用哨兵哨兵最基础架构由两部分组成,包括哨兵节点和数据节点。其中,哨兵节点是特殊的Redis节点,并不存储数据,出于高可用方面考虑,哨兵架构中通常都是多个哨兵节点共同提供服务。数据节点用于存储Redis数据。包括主节点和从节点
资源访问的拦截与统计
当请求访问被 Sentinel 保护的资源时:
入口拦截:通过 SphU.entry(resourceName)
方法触发 Slot Chain 的执行。统计数据:StatisticSlot
会收集资源的实时数据,包括:QPS(每秒请求数)、并发线程数。响应时间、成功 / 失败 / 异常请求数。数据存储:统计数据存储在 滑动窗口(滑动时间窗口) 中,例如:窗口划分为多个小格子(如 1 秒划分为 10 个格子,每个格子 100ms)。新数据写入当前格子,旧格子数据逐步过期,实现高效的实时统计。
流量控制规则的校验(FlowSlot)
流量控制规则分为 QPS 限流 和 并发线程数限流:
QPS 限流:基于滑动窗口统计的 QPS,与规则配置的阈值对比。若超过阈值,触发限流(拒绝请求或排队等待)。并发线程数限流:统计资源的并发执行线程数,超过阈值时拒绝新请求。限流模式:直接拒绝:超出阈值时立即拒绝请求(默认模式)。匀速排队:将请求放入队列,按固定间隔处理(适用于削峰场景)。关联限流:当关联资源的流量超过阈值时,限流当前资源(如保护支付接口时,关联订单查询接口的流量)。
熔断降级规则的校验(DegradeSlot)
熔断降级用于保护下游服务,常见策略:
慢调用熔断:当资源的平均响应时间(RT)超过阈值且请求数达到最小请求数时,触发熔断。异常比例熔断:当资源的异常请求比例超过阈值且请求数达标时,触发熔断。异常数熔断:当资源的异常请求数超过阈值时,触发熔断。熔断恢复:熔断后进入 “休眠期”,到期后允许少量请求试探,若恢复正常则关闭熔断。
实现原理:系统保护与热点参数限流
系统保护(SystemSlot)
根据系统全局指标(如 CPU、内存、线程数)触发保护,防止雪崩:
判断条件:系统负载(Load1)超过阈值且当前并发线程数超过阈值。内存使用率超过阈值。主动触发系统保护规则(如线程池队列已满)。
热点参数限流(ParamFlowSlot)
针对请求中的参数(如商品 ID、用户 ID)进行精细化限流:
实现方式:通过 @SentinelResource
注解标记参数,或通过 API 定义热点参数。统计每个参数值的访问频率,对高频参数值单独限流。支持参数例外项(如白名单参数值不限制)。
实现原理:扩展机制与生态集成
插件扩展
Sentinel 支持通过 SPI 机制扩展 Slot、规则持久化(如 Nacos、ZooKeeper)、数据源等。例如:集成 Spring Cloud Alibaba 时,自动适配 Feign、RestTemplate 等组件。异步与响应式支持支持异步编程模型(如 Spring WebFlux),通过 SphU.asyncEntry
处理异步资源。监控与告警实时监控数据通过 TransportModule
上报至控制台或外部系统(如 Prometheus)。支持自定义告警规则(如通过 API 发送短信、邮件)
关闭防火墙内核
systemctl stop firewalld
systemctl disable firewalld
setenforce 0
sed -i "s/^SELINUX=.*/SELINUX=disabled/g" /etc/selinux/config
修改主机名
hostnamectl set-hostname sentinel01
hostnamectl set-hostname sentine102
hostnamectl set-hostname sentine103
hostnamectl set-hostname master
hostnamectl set-hostname slave01
hostnamectl set-hostname slave02
Master.slave01.slave2节点操作
yum -y install gcc gcc-c++ make
tar -zxvf redis-6.2.4.tar.gz -C /usr/src/
cd /usr/src/redis-6.2.4/
make & make PREFIX=/usr/local/redis install
#PREFIX指定安装路径
ln -s /usr/local/redis/bin/* /usr/local/bin/
make && make PREFIX=/usr/local/redi:sinstall只是安装了二进制文件到系
统中,并没有启动脚本和配置文件。Redis提供了默认的配置文件,将配置文件
复制到/etc/目录下,然后编写服务脚本用于启动Redis及设置开机启动。当
Redis启动完成后,默认监听6379端口。
创建配置文件目录,适用默认配置文件
mkdir /etc/redis
cp /usr/src/redis-6.2.4/redis.conf 7etc//redis/6379.conf
vim /etc/systemd/system/redis.service
[Unit]
cription=Redis
After=network.target
[Service]
Type=forking
ExecStart=/usr/local/redis/bin/redis-server /etc/redis/6379.conf
[Install]
WantedBy=multi-user.target
EOF
修改配置文件
Master,Slave01,Slave02
[root@master ~]# vim /etc/redis/6379.conf
bind 127.0.0.1 192.168.207.167
#默认75行进行修改(监听地址)
#98行默认存在(redis端口号)
port 6379
daemonize yes
#257行进行修改(启用守护进程)
289行默认存在(PID文件)
pidfile /var/run/redis_6379.pid
loglevel notice
#297行默认存在(日志级别)
#203行进行添加(日志文件)
logfile "/var/log/redis_6379. log
启动服务
[root@master ~]# systemctl daemon-reload
[root@master ~]# systemctl start redis
[root@master ~]# systemctl enable redis
查看监听端口
[root@master ~] # netstat -anpt | netstat -anpt
tcp 0 0 192.168.207.167:6379 0.0.0.0:*
LISTEN 1285/redis-server
tcp 0 0 127.0.0.1:6379 0.0.0.0:*
LISTEN 12853/redis-server
主节点执行
[root@master ^]# redis-cli
127.0.0.1:6379>inforeplication
# Replication
自己的角色
role:master
connected slaves:2 #两个从节点
slave0:ip=192.168.207.168, port=6379, state=online, offset=280, lag=0
从节点对应的记录
slavel: ip=192.168. 207.169, port=6379, state=online, offset=280, lag=0
从节点对应的记录
从节点执行
[root@slave01 ~]# redis-cli
127.0.0.1:6379>inforeplication
Replication
role:slave #自己的角色
#主节点
master_host:192. 168.207.167
master_port:6379
master_link_status:up
[root@sentinel01 ~]# yum -y install gcc gcc-c++ make
[root@sentinel01 ~]#tar -zxvf redis-6.2.4.tar.gz -C /usr/src/
[root@sentine101 ~]# cd /usr/src/redis-6.2.4/
[root@sentinel01 redis-6.2.4 ~]# make & make & make instali
[root@sentinel01 redis-6.2.4 ~]# mkdir /etc/redis
[root@sentine101 redis-6.2.4 ~]# cp /usr/src/redis-6.2.4/redis. conf
/etc/redis/6379.conf
[root@sentinel01 redis-6.2.4 ~]# vim /etc/redis/6379.coonf
sentinel monitor master 192.168.207.167 6379 2 # 末)尾添加即可
bind0.0.0.0.0 #默认75行进行修改
daemonizeyes#默认257行进行修改
sentinelmonitor:哨兵命令
master:主节点名字
192.168.207.167 63792:主节点IP和端口,最后的2柔表示,当主节点出现
故障,至少需要两个哨兵节点同意,才能判定主节点故障
vim /etc/systemd/system/redis.server
[Unit]
Description=Redis
After=network.target
[Service]
Type=forking
ExecStart=/usr/local/bin/redis-sentinel /etc/redis/6379.conf
[Install]
WantedBy=multi-user.target
EOF
启动服务
[root@sentinel01 ~]# systemctl daemon-reload
[root@sentinel01 ~]# systemctl start redis
[root@sentinel01 ~]# systemctl enable redis
查看进程
[root@sentinel01 ~]#ps -aux | grep redis
root 13230 0.2 0.2 165064 9232 ? Ssl 12:05 0:00
/usr/local/bin/redis-sentinel 0.0.0.0:6379 [sentinel]
root 13255 0.0 0.0 112824 980 pts/l R+ 12:06 0:00 grep--color=auto redis
[root@sentinel01 ~]# redis-cli
127.0.0.1:6379> info sentinel
# Sentinel
sentinel masters:1
sentinel_tilt:0
sentinel_running_scripts:0
sentinel_scripts_queue_length:0
sentinel_simulate_failure_flags:0
master0:name=master, status=ok, address=192.168.207.167:6379, slaves=2, s
entinels=3
当主节点出现故障时,故障发现和转移是由哨兵来控制的,此时会将主节点切换
到其他从节点关掉主节点之后,等待一会时间,再次在sentine101上查看哨兵系统状态将会发现,原来的主节点进行了切换。下面手动模拟主节点出现故障,停止主节点上的Redis服务。具体操作如下:
[root@master ~]# systemctl stop redis
127.0.0.1:6379>info sentinel
# Sentinel
sentinel_masters:l
sentinel_tilt:0
sentinel_running_scripts:0
sentinel_scripts_queue_length:0
sentinel_simulate_failure_flags:0
#########################################################
master0:name=master, status=ok, address=192.168.207.169:6379, slaves=2,s
entinels=3
#########################################################
当主节点进行切换后,一个从节点变成了主节点。此时从节点数量仍然是2,
是因为在进行主从切换时,原来的故障的节点会被设置为新主的从节点,哨兵系
统并不会对故障节点进行客观下线,而是认为该从节点一致存在。当故障修复之
后,将会变为新的从节点投入适用。
对于哨兵节点,主要是epoch相关配置的变化,进行一次主从切换,epoch相关
的参数都会加1
[root@sentinel01 ~]# tail -9 /etc/redis/6379. conf