您的当前位置:首页 >娱乐 >【LinuxSRE工程师培训】Redis集群的三种方式,你都掌握了吗? 正文

【LinuxSRE工程师培训】Redis集群的三种方式,你都掌握了吗?

时间:2025-11-04 08:04:05 来源:网络整理编辑:娱乐

核心提示

为什么要有集群单个Redis存在不稳定性,当Redis服务宕机或硬盘故障,系统崩溃之后,就没有可用的服务了,还会造成数据的丢失单个Redis的读写能力也是有限的还由于互联网的三高架构,高并发,高性能,

  为什么要有集群

  单个Redis存在不稳定性,工程当Redis服务宕机或硬盘故障,师培系统崩溃之后,集群就没有可用的种都掌服务了,还会造成数据的工程丢失

  单个Redis的读写能力也是有限的

  还由于互联网的三高架构,高并发,师培高性能,集群高可用

  | 概念

  通过添加服务器的种都掌数量,提供相同的工程服务,从而让服务器达到一个稳定,师培高效的集群状态

  | 三种模式

  主从模式

  哨兵模式

  Cluster模式

  主从模式介绍

  | 为什么要用主从复制

  单机redis的风险与问题

  问题一:机器故障

  ①硬盘故障,系统崩溃

  ②本质:数据丢失,种都掌可能对业务造成灾难性打击

  问题二:容量瓶颈

  ①内存不足,工程一台redis内存是师培有限的

  解决方案:

  为了避免单点Redis服务器故障,准备多台服务器,集群互相联通,将数据复制多个副本保存在不同服务器上,连接在一起,并保证数据是同步的,即使有其中一台服务器宕机,免费源码下载其他服务器依然可以继续提供服务,实现Redis的高可用,同时实现数据冗余备份

  | 工作原理

  如上图所示,是Redis的工作原理,其对应的文字说明如下:

  ①replica库通过"SLAVEOF 172.200.1.201 6379"命令连接master库并发送"SYNC"给master

  ②master库收到"SYNC",会立即触发"BGSAVE"后台保存RDB快照,并将RDB快照发送给replica库;

  ③replica库接收后会应用RDB快照;

  ④master库会陆续将中间产生的新的操作保存并发送给replica库;

  ⑤到此我们master复制集就正常工作了;

  ⑥再此以后,master库只要发生新的操作,都会以命令传播的形式自动发送给replica库;

  ⑦所有复制相关信息,从info信息中都可以查到,即使重启任何节点,他的master-replica关系依然都在;

  ⑧如果发生master-replica关系断开时,replica库数据没有任何损坏,在下次重连之后,replica库发送"PSYNC

  ⑨master库只会将replica库缺失部分的数据同步给replica库应用,达到快速恢复master-replica架构的目的;

  温馨提示:(可能面试时会问到):

  1、在Redis 2.8版本之前,如果master-replica架构中replica库宕机将会再次触发"SYNC",从而全量拷贝主库的数据,这样效率明显很低

  于是在Redis 2.8版本之后就新增了"PSYNC"指令以实现可以理解为"断点续传"的企商汇功能

  2、生产环境中,建议开启master库持久化功能,避免因主库意外重启而导致缓存丢失

  举个例子,master库右1w条数据,replica库在某一时刻仅有9k数据,还有1k数据未来得及同步master库时,master库意外重启导致KEY为0,此时replica库同步master库数据会将replica库已有的9k缓存数据删除以达到和master库同步的目的

  哨兵模式介绍

  哨兵(sentinel)是一个分布式系统,用于对主从结构中的每台服务器进行监控,当出现故障时通过投票机制选择新的master并将所有slave连接到新的master

  | 为什么有哨兵

  主机宕机,如何能够高可用的恢复正常,不用人为进行干预

  作用:

  监控:不断地检查master和slave是否正常运行;master存活检测,master与slave运行清空检测

  通知(提醒):当被监控地服务器出现问题时,向其他(哨兵、客户端)发送通知

  自动故障转移:断开master与slave连接,选取一个slave作为master,将其他slave连接到新地master,并告知客户端新地服务器地址

  注意:

  哨兵也是一台redis服务器,只是不提供数据服务

  通常哨兵配置数量为单数

  Cluster模式介绍

  redis最开始使用主从模式做集群,若master宕机需要手动配置slave转为master

  后来为了高可用提出来哨兵模式,该模式下有一个哨兵监视master和slave,站群服务器若master宕机可自动将slave转为master,但它也有一个问题,就是不能动态扩充,哨兵模式还是只有一个master

  所以在3.x提出cluster集群模式

  | 工作原理

  Redis数据分片原理说明:

  ①redis会有多组分片构成,本篇笔记实验环境是3组;

  ②redis cluster使用固定个数的slot存储数据,一共16384是slot;

  ③每组分片分得1/3 slot个数,分别为"0-5460,5461-10921,10922-16383"

  ④基于CRC16(key) % 16384公式会得到一个"槽位号"(该编号范围在"0-16383"之间);

  ⑤根据计算得出的槽位值,找到相对应的分片节点的主节点,存储到相应槽位上;

  ⑥如果客户端当时连接的节点不是将来要存储的分片节点,分片集群会将客户端连接切换至真正存储节点进行数据存储;

  综上所述,我们来举个例子,在Redis分布式集群中,假设我们执行了"SET name oldboy"这一条指令,那么数据该如何存储的呢?其大致的存储逻辑如下:

  ①使用"CRC16(KEY_NAME)"进行校验计算一个值,假设"CRC16(name)"的计算结果为"1234567890";

  ②再使用"CRC16(KEY_NAME)%16384"进行计算,从而得出该KEY_NAME被分配到哪个slot上,假设结果为"1234567890%16384=722",就表示数据被落到slot=722的分片上;

  ③而slot=722恰好在第一个分片上,因为我们第一个分片的slot范围就是"0-5460"

  主从模式部署

  | 为各个Redis实例创建数据和配置文件目

# 创建Redis的数据存储目录 mkdir -pv /oldboyedu/data/redis1637{0..2} # 创建Redis的配置文件存储目录 mkdir -pv /oldboyedu/softwares/redis1637{0..2}

  | 为各个Redis实例创建配置文件

  1)为"redis16370"实例创建配置文件

# cat > /oldboyedu/softwares/redis16370/redis.conf <<EOF port 16370 daemonize yes pidfile /oldboyedu/data/redis16370/redis.pid loglevel notice logfile /oldboyedu/data/redis16370/redis.log dbfilename dump.rdb dir /oldboyedu/data/redis16370 bind 172.200.1.201 127.0.0.1 requirepass oldboyedu masterauth oldboyedu # 配置RDB持久化策略 save 900 1 save 300 10 save 60 10000 # 配置AOF持久化 appendonly yes appendfsync everysec EOF

  2)为"redis16371"实例创建配置文件

# cat > /oldboyedu/softwares/redis16371/redis.conf <<EOF port 16371 daemonize yes pidfile /oldboyedu/data/redis16371/redis.pid loglevel notice logfile /oldboyedu/data/redis16371/redis.log dbfilename dump.rdb dir /oldboyedu/data/redis16371 bind 10.0.0.112 127.0.0.1 requirepass oldboyedu masterauth oldboyedu # 配置RDB持久化策略 save 900 1 save 300 10 save 60 10000 # 配置AOF持久化 appendonly yes appendfsync everysec EOF

  3)为"redis16372"实例创建配置文件

cat > /oldboyedu/softwares/redis16372/redis.conf <<EOF port 16372 daemonize yes pidfile /oldboyedu/data/redis16372/redis.pid loglevel notice logfile /oldboyedu/data/redis16372/redis.log dbfilename dump.rdb dir /oldboyedu/data/redis16372 bind 10.0.0.112 127.0.0.1 requirepass oldboyedu masterauth oldboyedu # 配置RDB持久化策略 save 900 1 save 300 10 save 60 10000 # 配置AOF持久化 appendonly yes appendfsync everysec EOF

  温馨提示:

  所有的requirepass建议设置为一致,这为我们"哨兵模式"做准备,很明显,"requirepass"表示配置当前实例的验证口令;

  注意"masterauth"表示的含义是主库的验证口令;下面的模板你可以根据自己业务的实际需求进行改动即可

cat > /oldboyedu/softwares/redis16372/redis.conf <<EOF port 16372 daemonize yes pidfile /oldboyedu/data/redis16372/redis.pid loglevel notice logfile /oldboyedu/data/redis16372/redis.log dbfilename dump.rdb dir /oldboyedu/data/redis16372 bind 10.0.0.112 127.0.0.1 requirepass oldboyedu masterauth oldboyedu # 配置RDB持久化策略 save 900 1 save 300 10 save 60 10000 # 配置AOF持久化 appendonly yes appendfsync everysec EOF

  | 启动各个Redis实例

  1)启动各个Redis实例

redis-server /oldboyedu/softwares/redis16370/redis.conf redis-server /oldboyedu/softwares/redis16371/redis.conf redis-server /oldboyedu/softwares/redis16372/redis.conf # 执行 ss -lnt 查看是否启动 ss -lnt

  2)停止各个Redis实例运行,此步骤可跳过,因为我们暂时还不需要停止Redis,我们要用Redis实例做主从架构

redis-cli -p 16370 -a oldboyedu shutdown redis-cli -p 16371 -a oldboyedu shutdown redis-cli -p 16372 -a oldboyedu shutdown

  | 开启Redis的主从

  实验说明:以 redis16370 实例为主库,以 redis16371 实例和 redis16372 实例为从库

# 从库实例开启主从 redis-cli -p 16371 -a oldboyedu SLAVEOF 10.0.0.112 16370 redis-cli -p 16372 -a oldboyedu SLAVEOF 10.0.0.112 16370

  | 主库实例查看主从信息

redis-cli -p 16370 -a oldboyedu INFO REPLICATION

  | 从库实例查看主从信息

  在 "redis16371" 实例中查看主从状态信息:

  信息

redis-cli -p 16371 -a oldboyedu INFO REPLICATION

  在 "redis16372" 实例中查看主从状态信息:

redis-cli -p 16372 -a oldboyedu INFO REPLICATION

  | 验证主从配置是否生效

  在"redis16370"实例主库的11号数据库创建测试数据

# redis-cli -p 16370 -a oldboyedu -n 11 16370[11]> KEYS * (empty array) 16370[11]> SET name oldboyedu OK 16370[11]> SET age 18 OK 16370[11]> KEYS * 1) "name" 2) "age" 16370[11]> QUIT

  在"redis16371"实例从库的11号数据库查看是否同步主库的11号数据库

# redis-cli -p 16371 -a oldboyedu -n 11 16371[11]> KEYS * 1) "name" 2) "age" 16371[11]> GET name "oldboyedu" 16371[11]> GET age "18" 16371[11]> QUIT

  在"redis16372"实例从库的11号数据库查看是否同步主库的11号数据库

# redis-cli -p 16372 -a oldboyedu -n 11 16371[11]> KEYS * 1) "name" 2) "age" 16371[11]> GET name "oldboyedu" 16371[11]> GET age "18" 16371[11]> QUIT

  | 解除"redis16372"实例的主从关系

redis-cli -p 16372 -a oldboyedu SLAVEOF NO ONE

  | 跨节点部署Redis集群实战案例

(0)主从架构设计 主库为: 10.0.0.108 从库: 10.0.0.106 10.0.0.107 (1)10.0.0.106的配置 install -d /oldboyedu/data/redis cat > /oldboyedu/softwares/redis/conf/redis.conf <<EOF port 8106 daemonize yes pidfile /oldboyedu/data/redis/redis.pid loglevel notice logfile /oldboyedu/data/redis/redis.log dbfilename oldboyedu_linux.rdb dir /oldboyedu/data/redis/ bind 10.0.0.106 requirepass oldboyedu masterauth oldboyedu # 配置RDB持久化策略 save 900 1 save 300 10 save 60 10000 EOF redis-server /oldboyedu/softwares/redis/conf/redis.conf (2)10.0.0.107的配置 install -d /oldboyedu/data/redis cat > /oldboyedu/softwares/redis/conf/redis.conf <<EOF port 8107 daemonize yes pidfile /oldboyedu/data/redis/redis.pid loglevel notice logfile /oldboyedu/data/redis/redis.log dbfilename oldboyedu_linux.rdb dir /oldboyedu/data/redis/ bind 10.0.0.107 requirepass oldboyedu masterauth oldboyedu # 配置RDB持久化策略 save 900 1 save 300 10 save 60 10000 EOF redis-server /oldboyedu/softwares/redis/conf/redis.conf (3)10.0.0.108的配置 install -d /oldboyedu/data/redis cat > /oldboyedu/softwares/redis/conf/redis.conf <<EOF port 8108 daemonize yes pidfile /oldboyedu/data/redis/redis.pid loglevel notice logfile /oldboyedu/data/redis/redis.log dbfilename oldboyedu_linux.rdb dir /oldboyedu/data/redis/ bind 10.0.0.108 requirepass oldboyedu masterauth oldboyedu # 配置RDB持久化策略 save 900 1 save 300 10 save 60 10000 EOF redis-server /oldboyedu/softwares/redis/conf/redis.conf (4)从库开启主从 # 10.0.0.106: redis-cli -p 8106 -h 10.0.0.106 -a oldboyedu SLAVEOF 10.0.0.108 8108 # 10.0.0.107: redis-cli -p 8107 -h 10.0.0.107 -a oldboyedu SLAVEOF 10.0.0.108 8108