- 是什么
- 能干嘛
- 常用三种方式
- 一主二仆
- Master
- Slave
- 测试
- 测试一
- 测试二
- 思考
- 思考一
- 思考二
- 薪火相传
- 配置
- 测试
- 测试一
- 测试二
- 注意
- 反客为主
- 方法
- 测试
- 复制原理
- 哨兵模式
- 是什么?
- 使用步骤
- 步骤1:
- 步骤2:
- 步骤3:
- 步骤4:
- 步骤5:
- 步骤6:
- 测试
- 复制延时
- 故障恢复策略
- SpringBoot 配置
- 测试
看了尚硅谷的资料,整理一下作为笔记
是什么主机数据更新后根据配置和策略,自动同步到备机的 master/slave 机制,Master 以写为主,Slave 以读为主
能干嘛- 读写分离,性能扩展
- 容灾快速恢复
我现在有三个 redis 服务,分别为:6380、6381 和 6382
一主二仆我们将把 6380 作为 Master,6381 和 6382 分别作为 Slave。
修改 6380 配置: pidfile /var/run/redis_6380.pid(Redis 进程相关信息) port 6380(Redis 端口号) dbfilename dump6380.rdb(RDB文件名称,我们这里使用的RDB持久化方式,关闭了AOF方式) requirepass 123456(Redis 密码)
直接启动 6380,即为 Master 使用命令:info replication 查看相关信息 role:master 表示 Redis 的角色为 Master connected_slaves 表示连接的 Slave 的数量(当前没有 Slave 连接)
因为 Slave 配置相似,故只描述 6381 的配置。
修改 6381 配置: pidfile /var/run/redis_6381.pid(Redis 进程相关信息) port 6381(Redis 端口号) dbfilename dump6381.rdb(RDB文件名称,我们这里使用的RDB持久化方式,关闭了AOF方式) requirepass 123456(Redis 密码) masterauth 123456(Master 密码) slaveof 127.0.0.1 6380(Master 地址、端口号) 同样配置一下 6382
启动 6381 和 6382,使用命令分别查看: 6380: 可以看到,connected_slaves:2 表示有两个 Slave,分别为: slave0:ip=127.0.0.1,port=6381,state=online,offset=2212,lag=1 slave1:ip=127.0.0.1,port=6382,state=online,offset=2226,lag=0
6381: 6382:
可以看到,6381 和 6382 的 role:slave,以及 : master_host:127.0.0.1(Master 的地址) master_port:6380(Master 的端口号) master_link_status:up(Master 的状态)
测试 测试一我们在 6380 上存写入数据: 然后在 6381 和 6382 上分别查看:
可以看到,Master 写入数据之后,将自动同步到 Slave 上
我们在 6381 上写入数据: 提示我们只可以读取不能进行写入操作
如果由于某种原因,其中一个 Slave 宕机,重新启动后是同步 Master 的全部数据还是 Slave 重启之后再写入 Master的数据? 我们将 6381 shutdown: 然后在 6380 写入新的数据:
重新启动 6381,查看数据:
可以看到,全部数据都同步到了 6381。
如果 Master 宕机,那么会不会有一个 Slave 替换为 Master 呢?
将 6380 shutdown: 分别查看 6381 和 6382:
我们可以看到,6381 和 6382 角色依然为 Slave,并不会替换为 Master。
上一个 Slave 可以是下一个 Slave 的 Master,Slave 同样可以接收其他 slaves 的连接额同步请求,那么该 Slave 作为了链条中下一个的 Master,可以有效减轻 Master 写的压力,去中心化降低风险。
6380 和6381 的配置不变,我们将 6382 的 slaveof 配置修改为: slaveof 127.0.0.1 6381 重启 6382。
我们分别查看6380、6381 和 6382 的信息: 6380: 6381:
6382:
可以看到,6382 的 master 是6381,而 6381 的 master 是 6380
我们在 6380 添加数据: 查看 6381 和 6382 的数据:
我们将 6381 宕机: 然后向 6380 写入数据:
查看 6382 的数据:
再次启动 6381后,再次查看 6381 和 6382 的数据:
可以看到,6381 和 6382 再次同步到了最新的数据集。
- 中途变更转向,会清除之前的数据,重新建立 Master/Slave关系,将拷贝最新的数据。
- 风险是一旦某个 Slave 宕机,后面的 Slave 都没有办法备份。
- 主机宕机,从机还是从机,无法写入数据了。
当一个 Master 宕机后,后面的 Slave 可以like升为 Master,其后面的 Slave 不用做任何修改。
方法使用命令 slaveof no one 将从机变为主机。
测试我们将 6380 关掉: 将 6381 变为主机:
可以看到,6381 变为了 Master,而且 6382 依然是 6381 的Slave
但是我们要意识到:当 Master 宕机后,我们是通过手动当时解决问题的。
复制原理说了三种主从复制的方案,我们总得指导一下它们复制的原理吧:
- Slave 启动成功,连接到 Master 后会发送一个 sync 命令;
- Master 接到命令后,启动后台的存盘进程,同时收集所有接收到的用于修改数据集的命令(类似于AOF嘛),在后台进程执行完毕后,Master 将传送整个数据文件到 Slave,以完成一次完全同步;
- 全量复制:而 Slave 服务在接收到数据文件后,将其存盘并加载到内存中;
- 增量复制:Master 继续将新的所有收集到的修改命令依次传给 Slave,完成同步;
- 但是,只要是重新连接 Master,就会进行完全同步(全量复制)
反客为主的自动版,能够后台监控主机是否故障,如果故障了,根据投票数将自动把从库转换为主库。
我们先将6380、6381 和 6382 调整为一主二从(因为一主二从更能说明问题)。
即:将 6382 的配置 replicaof 127.0.0.1 6381 改为 replicaof 127.0.0.1 6380
步骤2:将 6380 的配置加上如下配置: masterauth 123456(保持和三个 Redis 的密码一致)
因为之后测试的时候 6380 会变为 Slave,它需要知道新的 Master 的密码,否则会连接失败。
步骤3:在 6380 安装目录新建文件:sentinel-6380.conf、sentinel-6381.conf 和 sentinel-6382.conf。
步骤4:在sentinel-6380.conf、sentinel-6381.conf 和 sentinel-6382.conf 文件中修改配置:
- port 26380
三个哨兵端口分别设置为 26380、26381、26382
- sentinel monitor mymaster 39.105.35.163 6380 1
注意:使用云服务的话,我们这里一定要写外网地址,否则在 java 客户端连接 mymaster 的时候会连接失败。 mymaster 是主机的别名,39.105.35.163 6380 为主机的地址和端口,1 表示有一票通过即可
- sentinel auth-pass mymaster 123456
Master 的密码
- daemonize yes
支持后台启动
步骤5:分别启动 6380、6381 和 6382
步骤6:启动哨兵: ./src/redis-sentinel rediscopy/sentinel-6380.conf ./src/redis-sentinel rediscopy/sentinel-6381.conf ./src/redis-sentinel rediscopy/sentinel-6382.conf
1.我们先查看三台 Redis 的信息: 6380: 6381:
6382:
2.然后我们关闭 6380,并在此查看 6381 和 6382: 6380:
6381: 在此处已经可以看到,Master 已经是 6382 了。
重新选举出 Master 之后,我们需要重新连接客户端
6382: 3.我们再次启动 6380,并查看信息:
可以看到,6380 现在是 6382 的 Slave 了! 注意:由于Master 和 哨兵(sentinel)在同一台服务器上,所以当 Master 宕机的时候往往哨兵也同时宕机,所以我们可以在三台 Redis 中都加上哨兵,以保证更高的安全性。
由于所有的写操作都是先在 Master上操作,然后同步更新到 Slave 上,所以从 Master 同步到 Slave 机器有一定的延迟,当系统很繁忙的时候,延迟问题会更加严重,Slave 机器数量的增加会使这个问题更加严重。
故障恢复策略- 优先级在 redis.conf 中默认:slave-priority 100,值越小优先级越高
- 偏移量是指获得原主机数据最完整的
- 每个 Redis 实例启动后都会随机生成一个 40 位的 runid
spring:
redis:
#Redis单机单实例
# database: 1
# host: 192.168.217.129
# port: 6379
# password: 123456
#Redis哨兵模式
database: 0 #选择redis的第二个数据库
password: 123456 #redis密码
sentinel:
master: mymaster #主节点的名字 #下面是所有哨兵集群节点(26380为哨兵的端口号)
nodes: 39.105.35.163:26380,39.105.35.163:26381,39.105.35.163:26382
测试
OK,完整的过程!