分布式-redis哨兵模式架构

文章目录

简介

为了解决主从模式无法自动故障转移与恢复的问题,Redis引入了哨兵模式,主要是在主从复制的基础上加入了哨兵节点,用于监控主节点和从节点状态,当主节点发生故障时,哨兵节点可以自动进行故障转移,选择一个从节点升级为主节点,并通知其他从节点和应用程序进行更新。

优点:可以动态切换主从库,中心型公司首选

缺点:

  1. 单个master主节点提供写服务,redis存储的数据有限(<10G),并发量不足(<3w)
  2. 自动切换主从库会产生访问瞬断的情况,切换没有那么快

工作原理:

  1. 哨兵节点定期向所有主节点和从节点发送PING命令,如果在指定的时间内未收到PONG响应,哨兵节点会将该节点标记为主观下线
  2. 如果一个主节点被多数哨兵节点标记为主观下线,那么它将被标记为客观下线
  3. 当主节点被标记为客观下线时,哨兵节点会触发故障转移过程,它会从所有健康的从节点中选举一个新的主节点
  4. 并将所有从节点切换到新的主节点实现自动故障转移。同时哨兵节点会更新所有客户端的配置指向新的主节点。

生产级部署文档

硬件:1主2从3哨兵,针对中大型公司(日活百万级至千万级,QPS 10万+)的场景:

角色 IP地址 主机名 硬件配置 操作系统
主节点 192.168.1.10 redis-m1 16核 / 64GB / 1TB CentOS 7.9
从节点1 192.168.1.11 redis-s1 16核 / 64GB / 1TB CentOS 7.9
从节点2 192.168.1.12 redis-s2 16核 / 64GB / 1TB CentOS 7.9
哨兵1 192.168.1.13 sentinel1 16核 / 64GB / 1TB CentOS 7.9
哨兵2 192.168.1.14 sentinel2 16核 / 64GB / 1TB CentOS 7.9
哨兵3 192.168.1.15 sentinel3 16核 / 64GB / 1TB CentOS 7.9

说明

  • 所有服务器之间网络互通,防火墙开放 6379 (Redis)和 26379(哨兵)端口。
  • 主从节点和哨兵节点分开部署,避免资源争用,提高稳定性。

常用命令:

java 复制代码
# 查看集群信息
redis-cli -a <password> info replication

# 手动故障转移,必须在想要提升为主节点的从节点上执行
# 1.默认(安全)模式		
# PS:数据零丢失,会等待从节点的数据与主节点完全同步后,再进行无损切换
redis-cli -a 你的密码 CLUSTER FAILOVER  

# 2.强制(FORCE)模式	
# PS:主节点不可用时使用。跳过与主节点的数据同步检查,直接发起故障转移,但仍需集群中多数主节点同意
redis-cli -a 你的密码 CLUSTER FAILOVER FORCE

# 3.接管(TAKEOVER)模式		
# PS:最强硬、有数据丢失风险,完全忽略集群共识和数据一致性,从节点单方面宣布成为主节点
redis-cli -a 你的密码 CLUSTER FAILOVER TAKEOVER

# 哨兵手动切换
# 强制哨兵对指定的主节点(<master-name>)发起一次故障转移,无论该主节点当前是否真实下线。
# 哨兵会选举出一个从节点将其提升为新主节点,并将其他从节点指向新主节
redis-cli -p 26379 SENTINEL FAILOVER <master-name>

# 查看哨兵状态
redis-cli -p 26379 info sentinel

基础配置-所有节点

java 复制代码
# 设置主机名(根据角色修改)
hostnamectl set-hostname redis-m1   # 主节点
hostnamectl set-hostname redis-s1   # 从节点1
hostnamectl set-hostname redis-s2   # 从节点2
hostnamectl set-hostname sentinel1  # 哨兵1
hostnamectl set-hostname sentinel2  # 哨兵2
hostnamectl set-hostname sentinel3  # 哨兵3

# 关闭防火墙
systemctl stop firewalld
systemctl disable firewalld
# 或者开放端口
# firewall-cmd --permanent --add-port=6379/tcp --add-port=26379/tcp
# firewall-cmd --reload

# 关闭SELinux(临时)
setenforce 0
sed -i 's/^SELINUX=enforcing/SELINUX=disabled/' /etc/selinux/config

安装Redis-主从节点

java 复制代码
// 方式一:源码编译
cd /usr/local/src
wget https://download.redis.io/releases/redis-7.2.4.tar.gz
tar xzf redis-7.2.4.tar.gz
cd redis-7.2.4
make && make install PREFIX=/usr/local/redis

// 创建数据目录和配置目录:
mkdir -p /data/redis/{data,logs,conf,run}
useradd redis -s /sbin/nologin -M
chown -R redis:redis /data/redis /usr/local/redis

# 启动redis[暂时不启动]
./redis-server /data/redis/conf/redis.conf

配置主从复制

主节点配置

编辑 /data/redis/conf/redis.conf

java 复制代码
bind 192.168.1.10 127.0.0.1 # 设置绑定IP,允许外部访问
protected-mode no 			# 保护模式,如果在非本地网络
port 6379 					# 设置端口
tcp-backlog 511
timeout 0
tcp-keepalive 300
daemonize no    			# 由systemd管理,不后台运行
supervised systemd
pidfile /data/redis/run/redis_6379.pid
loglevel notice
logfile "/data/redis/logs/redis-6379.log"
databases 16

# 主节点认证密码(可选,建议设置)
requirepass Redis123
masterauth Redis123

# 持久化配置 RDB+AOF
save 900 1
save 300 10
save 60 10000
stop-writes-on-bgsave-error yes
rdbcompression yes
rdbchecksum yes
dbfilename dump-6379.rdb
dir /data/redis/data

# AOF配置(可根据需求选择开启)
appendonly yes
appendfilename "appendonly-6379.aof"
appendfsync everysec
no-appendfsync-on-rewrite no
auto-aof-rewrite-percentage 100
auto-aof-rewrite-min-size 64mb
aof-load-truncated yes
aof-use-rdb-preamble yes

# 内存管理(根据实际内存调整,留出系统内存)
maxmemory 48GB
maxmemory-policy allkeys-lru   # 淘汰策略

# 慢日志
slowlog-log-slower-than 10000
slowlog-max-len 128

# 其他优化
hash-max-ziplist-entries 512
hash-max-ziplist-value 64
list-max-ziplist-size -2
set-max-intset-entries 512
zset-max-ziplist-entries 128
zset-max-ziplist-value 64

启动redis ./redis-server /data/redis/conf/redis.conf

从节点配置

  1. 两个从节点配置基本相同,只需修改replicaof指向主节点。

编辑 /data/redis/conf/redis.conf,在主节点配置基础上增加:

java 复制代码
replicaof 192.168.1.101 6379  		 # 指向主节点IP和端口
masterauth your_master_password 	 # 如果主节点设置了密码
  1. 其余配置与主节点相同,注意内存策略一致

验证:

java 复制代码
1. 主节点:
    ./redis-cli -a 密码 info replication
    输出应显示connected_slaves:2,并且从节点状态正常。
2. 从节点:
    ./redis-cli -a 密码 info replication
    应看到role:slave,并显示主节点信息。

启动redis ./redis-server /data/redis/conf/redis.conf

哨兵节点配置

哨兵用于监控主从节点,实现自动故障转移,每个哨兵节点运行独立的哨兵进程。只需安装redis二进制,不需要启动Redis服务,也可以只安装哨兵(redis-sentinel)

  • 安装
java 复制代码
// 方式一:源码编译
cd /usr/local/src
wget https://download.redis.io/releases/redis-7.2.4.tar.gz
tar xzf redis-7.2.4.tar.gz
cd redis-7.2.4
make && make install PREFIX=/usr/local/redis

// 创建数据目录和配置目录:
mkdir -p /data/sentinel/{data,logs,conf,run}
useradd redis -s /sbin/nologin -M
chown -R redis:redis /data/sentinel /usr/local/redis
  • 配置

哨兵配置文件(所有哨兵节点基本一致),编辑 /data/sentinel/conf/sentinel.conf

java 复制代码
# 基础配置
port 26379
daemonize no
supervised systemd
pidfile /data/sentinel/run/sentinel_26379.pid
logfile "/data/sentinel/logs/sentinel-26379.log"
dir /data/sentinel/data

# 监控主节点,2表示至少2个哨兵同意故障转移
sentinel monitor redis-m1 192.168.1.10 6379 2

# 哨兵连接主节点的密码(如果设置了requirepass)
sentinel auth-pass redis-m1 Redis123

# 主观下线时间,默认30秒
sentinel down-after-milliseconds mymaster 30000

# 故障转移超时时间,默认180秒
sentinel failover-timeout mymaster 180000

# 同时并行同步数,故障转移后可以同时有1个从节点同步新主
sentinel parallel-syncs mymaster 1

# 保护模式关闭(如果不需要)
protected-mode no
  • 启动

./redis-sentinel /data/sentinel/conf/sentinel.conf

  • 验证

在任意哨兵节点执行:****./redis-cli -p 26379 info sentinel

显示结果如下:

plain 复制代码
# Sentinel
sentinel_masters:1
sentinel_tilt:0
sentinel_running_scripts:0
sentinel_scripts_queue_length:0
sentinel_simulate_failure_flags:0
master0:name=mymaster,status=ok,address=192.168.1.10:6379,slaves=2,sentinels=3

高可用验证

主从复制测试

  • 在主节点设置键:redis-cli -h 192.168.1.101 SET testkey "hello"
  • 在从节点获取:redis-cli -h 192.168.1.102 GET testkey 应返回"hello"。

故障转移测试

  1. 在主节点上执行:systemctl stop redis
  2. 等待30秒左右(down-after-milliseconds配置),哨兵会检测到主观下线,随后发起投票,选举新的主节点。可以在哨兵日志中查看故障转移过程:

tail -f /data/sentinel/logs/sentinel-26379.log

  1. 故障转移完成后,查看当前主节点:

/usr/local/redis/bin/redis-cli -p 26379 sentinel get-master-addr-by-name mymaster

返回新的主节点IP和端口,旧主节点恢复后会自动成为新主的从节点。

性能测试

总写能力:仅主节点处理写,最大写QPS约5万~8万(保守估计3万+)。

总读能力:主节点+两个从节点均可处理读,假设读请求均匀分发,最大读QPS可达15万~24万

总混合QPS:在读写比例2:8下,整体QPS可达 10万~15万

性能优化

硬件优化

在 所有Redis节点(主、从)的 /etc/sysctl.conf 中添加,并执行 sysctl -p 使配置生效

shell 复制代码
# 提高连接队列大小,应对高并发连接
net.core.somaxconn = 1024

# 允许内存过载,避免Redis启动时因内存分配失败
vm.overcommit_memory = 1

# 禁用透明大页,减少内存延迟波动
# 立即生效
echo never > /sys/kernel/mm/transparent_hugepage/enabled
# 永久生效
echo 'echo never > /sys/kernel/mm/transparent_hugepage/enabled' >> /etc/rc.local
chmod +x /etc/rc.local

Redis优化

最大内存+多线程+最大客户端连接数+RDB/AOF持久化+内存淘汰策略

shell 复制代码
# Redis配置优化
# 1.物理内存:建议为物理内存的50%,留出部分给OS和持久化子进程(如bgsave)
maxmemory 32GB 

# 2.启用多线程IO处理网络读写:建议min(总核数 - 2, 8)。
# 超过8个线程后,性能提升会变得非常有限,甚至可能因为线程切换开销而导致收益下降,建议逐步调优
io-threads 8

# 主节点允许线程处理读操作
# 默认是 no,即只使用多线程来处理写操作(向客户端回写结果)。
# 设置为 yes,多线程也会处理读操作(从客户端读取命令和解析协议)
io-threads-do-reads yes

# 3.网络
# 最大客户端连接数,根据并发量调整,默认10000,可适当提高
maxclients 20000

# 客户端空闲超时,设为0禁用(保持长连接)
timeout 0

# TCP keepalive,检测死连接
tcp-keepalive 300

# 4.持久化策略,根据业务对数据安全的要求权衡性能。
# RDB快照:如果允许少量数据丢失,可仅使用RDB,并降低快照频率(例如)
save 900 1 
save 300 10 
save 60 10000 

# AOF
# 如需更高数据安全性,开启AOF并设置 
appendfsync everysec

# 如果磁盘IO成为瓶颈,可考虑关闭AOF,仅用RDB+主从复制

# 5.内存淘汰策略
# allkeys-lru适合一般缓存场景
# volatile-lru适合业务有明确过期需求
# 确保内存达到上限时能平滑淘汰数据,避免OOM
conf maxmemory-policy allkeys-lru   

# 6.禁用或优化危险命令
rename-command FLUSHALL ""         # 禁用
rename-command CONFIG "C0NFIG"     # 重命名
相关推荐
电气铺二表姐137744166151 小时前
智能虚拟电厂系统 分布式能源集中调度 支持多协议并网控制
分布式·能源
远方16091 小时前
116-Oracle 26ai 断言(assertion)新特性
大数据·数据库·sql·oracle·database·ai编程
八月瓜科技1 小时前
擎策·知海全球专利数据库 技术赋能检索 让科技创新少走弯路
大数据·数据库·人工智能·科技·深度学习·娱乐
珠海西格1 小时前
工商业分布式光伏:西格防逆流方案如何适配高负荷波动场景?
大数据·服务器·分布式·云计算·能源
萤丰信息1 小时前
智慧园区:数智赋能,重构城市运营新生态
人工智能·科技·安全·重构·架构·智慧城市·智慧园区
Max_uuc2 小时前
【内核心法】撞碎“内存墙”:高性能 C++ 中的缓存友好型设计与数据局部性进化
缓存
南棱笑笑生2 小时前
20260310解决瑞芯微原厂RK3576的Android14刷入乐晓电子的K7开发板后适配ADB连接
数据库·rockchip
兴通扫码设备2 小时前
ocr工业场景适配升级:深圳市兴通物联XTC8501智能相机接口与环境适应性技术解析
数据库·人工智能·深度学习·数码相机·计算机视觉
rannn_1112 小时前
【Redis|实战篇1】黑马点评|短信登录功能实现
java·redis·后端·缓存·项目