700字范文,内容丰富有趣,生活中的好帮手!
700字范文 > Redis【4】 - 主从复制 心跳机制 哨兵

Redis【4】 - 主从复制 心跳机制 哨兵

时间:2019-03-18 20:34:03

相关推荐

Redis【4】 - 主从复制 心跳机制 哨兵

上一篇: /LawssssCat/article/details/105131393下一篇:https://lawsssscat./article/details/105157134

Redis 集群概述

单台 Redis 服务器可能遇到的问题

单个 Redis 服务器会发生单点故障, 并且一台服务器需要处理所有的请求负载,压力较大 (容错性差)从容量上,单个 Redis 服务器的内存容量有限,就算一台 Redis 服务器内容容量为 256G,也不能将所有内容作为 Redis 存储内容。

一般来说,单台Redis最大使用内容不应该超过 20G

基本描述

高可用 (High Availability):通常来描述一个系统经过专门的设计,从而减少停工时间,而保持其服务的高可用。高并发(High Concurrency):通过设计保证系统能够同时并行处理很多请求

通常指标有:

响应时间(Response Time)吞吐量(Throught)每秒查询率 QPS (Query Per Second)并发用户数等

响应来说,牺牲了一致性

提升系统的并发能力

提升系统并发能力的方式,主要有两种:垂直扩展(Scale Up)与水平扩展(Scale Out)。

# 垂直扩展(升硬件)

垂直扩展:提升单机处理能力。垂直扩展的方式只有两种

增强单机硬件性能,如:

添加 CPU 核数如 32 核,升级更好的网卡如万兆,升级根号的硬盘如SSD,扩充硬盘容量如 2T,扩充系统内存如 128G

提升单机架构性能,如:

使用 Cache 来减少 IO 次数,使用异步来增加单服务吞吐量,使用无锁数据结构来减少响应时间

如果预算不是问题,单机扩展往往最自接,快捷

但有一个致命的不足,单机性能总是有限的。

所以分布式架构设计高并发终极解决方案还是水平扩展

# 水平扩展(分压力)

水平扩展:只要增加服务器数量,就能线性扩充系统性能。

水平扩展对系统架构设计是有要求的,难点在于:如何在架构各层进行可水平扩展 的设计

Redis 主从复制

简介

一个 Redis 服务可以有多个该服务的复制品,这个 Redis 服务成为 Master

其他复制称为 Slaves

如图:我们将一个 Redis 服务器作为主库(master),其他三台作为从库(Slave),主库只负责写数据,每次有数据库更新的数据同步到它所有的从库,而从库只负责读数据

两个好处:

读写分离:提高服务器的负载能力,可根据读请求的规模自由增加或减少从库的数量可用性:数据被复制成好几份,一台机器故障,可以快速从其他机器获取数据并回复。

在 Redis 主从模式中,一台主库可以拥有多个从库 ,但是一个从库只能隶属于一个主库。

工作流程

# 建立连接阶段 slaveof(或 replicaof)

启动从服务器

设置 master 的 地址和端口,保存 master 信息

# --port 6380 指定从库服务的 端口号# --slaveof 127.0.0.1 6379 指定主服务器/usr/local/redis/bin/redis-server /usr/local/redis/redis.conf --port 6380 --slaveof 127.0.0.1 6379

加上 slaveof 参数启动另一个 Redis 实例作为从库,并且监听 6380 端口

登录从服务器

/usr/local/redis/bin/redis-cli -p 6380 -a root

主从变换

# 不是任何的从slaveof no one # 指定从属的主服务器slaveof ip地址 端口号

# 数据同步阶段 psync

数据同步阶段 master 说明

如果master 数据量大,同步阶段应该避免高峰期,避免master 阻塞,影响业务正常执行复制缓冲区大小设定不合理,会导致数据溢出。

如果进行全量复制时,部分复制的缓存区被被填满,会出现指令丢失情况

这种情况下,在进行完成复制后,会进行第二次全量复制(如果部分复制的缓存区一直被填满,一直出现指令丢失,会导致slave陷入死循环状态)

避免这种情况,需要修改主服务器配置:repl-backlog-size 1mb,来调整复制缓存区的大小。

改多少合理?

计算机性能决定

master 单机内存占用主机内存的哔哩不应过大,建议使用50%~70%的内存,留下30%~50%内存用于执行 bgsave命令和创建复制缓冲区

数据同步阶段 slave 说明

为了避免 slave 进行全量复制、部分复制时,服务器响应阻塞或数据不同步,建议关闭此期间的对外服务

slave-server-stale-data yes|no

数据同步阶段,master发送给slave信息可以理解为 master 是 slave的一个客户端,主动向 slave 发送命令

多个 slave 同时对 master 请求数据同步,master 发送的 RDB 文件增多,会对宽带造成巨大冲击。如果master带宽不足,数据同步需要错峰

后面会讲技术方面的解决方案

slave过多时,建议调整拓扑结构时,由一主多从结构变成树状结构,中间的节点即是master,也是slave。

注意,使用树状结构时,由于层级深度,导致深度越高的 slave 与 最顶层的 master 间数据同步延迟较大,数据一致性差,应谨慎选择

问题解决

PSYNC 失败:-NOMASTERLINK Can’t SYNC while not connected with my master

127.0.0.1:6380> PSYNCEntering replica output mode... (press Ctrl-C to quit)SYNC with master failed: -NOMASTERLINK Can't SYNC while not connected with my master

这个问题,有两个可能性

你的主服务器自定义了密码

那么从服务器在连接时要指定主服务器的密码

主服务器设置成了 slave 模式(从服务器)

登录客户端,用slaveof no one命令改回来

master_link_status:down

同步不成功,并且在info里面发现,master_link_status:down

要么是上面的情况,要么是防火墙没开

打开防火墙端口命令

# 端口看你自己情况firewall-cmd --zone=public --add-port=3679/tcp --permanentfirewall-cmd --reload

# 命令传播阶段

这个阶段就一句话:保证实时数据同步

当 master 数据库状态被修改后,导致主从服务器数据状态不一致,此时需要让主从数据同步到一致的状态,同步的动作成为命令传播master 将接收到的数据变更命令发送给 slave,slave 接收命令后执行命令

部分复制(的细节)

命令传播阶段出现了断网现象和处理

网络闪断:忽略短时间网络中断:部分复制长时间网络中断:全量复制

部分复制的三个核心要输(下面一个个说)

服务器的运行 id (run id)主服务器的复制积压缓冲区 (也就是前面简称的:复制缓冲区)主主从服务器的复制偏移量

1. 服务器运行ID(runid)

概念服务器运行 id 是每台服务器每次运行的身份识别码,一台服务器多次运行可以生成多个运行 id组成:运行 id 由 40 位字符组成,是一个随机的十六进制字符

例如:

1b26e30907309452dede588893477e847cfcedd4

ffffffffffaaaaaaaaaaeeeeeeeeee1111111111 (神选id 🐶)作用运行 id 被用于在服务器间进行传输,识别身份

如果想两次操作均对同一台服务器进行,必须每次操作携带对应的运行id,用于对方识别实现方法

运行id在每台服务器启动时自动生成

master在首次连接slave时,会将自己的运行id发送给slave,slave保存此运行id

通过 info Server 命令,可以查看节点的runid

2、 3 . 复制积压缓冲区 + 偏移量

(如图)master 会将部分复制的命令放在复制缓冲区

当 slave 1 断网,缓冲区会等待玩过重新连接后,才把数据发出

主从复制工作流程

复制缓冲区

概念是一个先进先出(FIFO)的队列,用于存储服务器执行过程的命令

由来:每台服务器启动时,如果开启AOF或者被成为master节点,即创建复制缓冲区

(因此,我们通常不会吧AOF关闭)

内部组成:偏移量+字节值

工作原理

就是通过 offset 判断同的 slave 当前数据传输到什么程度了master记录已发送的信息对应的 offsetslave记录已接收的信息对应的 offset

# 总结:数据同步+命令传播阶段工作流程(详细)

心跳机制

进入命令传播阶段, master 与 slave 间需要进行信息交换,使用心跳机制进行维护,实现双方连接保持在线

master 心跳:

指令:PING周期:由repl-ping-slave-period决定,默认10s作用:判断 slave 是否在线查询:INFO replication(获取slave最后一次连接时间间隔,lag项维持在0或1视为正常)

slave 心跳任务指令:REPLCONF ACK [offset]周期:1秒(比master相对快)作用1:汇报slave自己的复制偏移量,获取最新的数据变更指令作用2:判断master是否在线

心跳阶段注意事项

当 slave 多数掉线,或延迟过高时,master为保障数据稳定性,将拒绝所有信息同步操作

如:

min-slaves-to-write 2 min-slaves-max-lag 8

slave 数量少于2个,或者所有slave的延迟都大于等于10秒时,强制关闭master写功能,停止数据同步。

slave 数量由 slave 发送REPLCONF ACK命令做确认

slave 延迟由 slave 发送REPLCONF ACK命令做确认

# 总结:工作全流程(详细)

部分复制、全量复制看上面

# 主从复制常见问题

1、master 重启后的全量复制

一旦master重启,runid发生改变,会导致全部slave的全量复制。

解决方案

redis内部解决了,不需要我们设置(了解)

在 master 关闭时执行指令 shutdown save ,进行 RDB 持久haunted,将 runid 与 offset 保存到 RDB 文件中。

(下图,可以通过redis-check-rdb进行查看)

master 重启后加载 RDB 文件恢复数据

2、频繁的全量复制

(前面提及)

问题现象:网络不佳,出现网络中断,slave 不能提供服务原因:复制缓冲区过小,断网后 slave 的 offset 越界,触发全量复制最终结果:slave 反复进行全量复制解决方案:修改缓冲区大小

repl-backlog-size建议设置如下: 测算 master 到 slave 的重连平均时长second获取 master 平均每秒产生写命令数据总量write_size_per_second最优复制缓冲区空间 =2 * second * write_sieze_per_second

3、频繁的网络中断 (1)

4、频繁的网络中断(2)

5、数据不一致

哨兵模式(主机“宕机”怎么办)

将宕机的 master 下线找到一个 slave 作为 master通知所有的 slave 连接新的 master启动新的 master 与 slave全量复制 * N+部分复制 * N

# 哨兵

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

作用

监控

不断的检查 master 和 slave 是否正常运行

master 存活检测、master 与 slave 运行情况检测

通知(提醒)

自动故障转移

# 启动哨兵模式

配置哨兵

配置 一拖二 的主从结构配置三个哨兵(配置相同,端口不同)

参看 sentinel.conf启动哨兵

redis-sentinel sentinel-端口号.conf

哨兵配置文件(sentinel.conf)的位置

把配置复制到/usr/local/redis目录

cp /opt/redis-5.0.8/sentinel.conf /usr/local/redis/sentinel26379.conf

查看 sentinel.conf 配置

# grep -v "#" 去掉注释# grep -v "^$" 去掉换行cat /opt/redis-5.0.8/sentinel.conf | grep -v "#" | grep -v "^$"

# 端口port 26379# 守护模式启动 daemonize no# pid 文件位置pidfile /var/run/redis-sentinel.pid# 日志文件位置logfile ""# 数据保存位置dir /tmp# (核心) 语法:sentinel monitor (自定义)名字 masterIP master端口 多少个哨兵# 最后的 2 是指,当有两个哨兵检测到 master 宕机,就认为 master 宕机# 通常设置为 哨兵数量/2 + 1 (因此,哨兵通常设置单数个)sentinel monitor mymaster 127.0.0.1 6379 2# master 多长时间没响应,认为检测到 master 宕机 (名字与上面自定义名字相同)# 默认 30秒sentinel down-after-milliseconds mymaster 30000# 新master上任后,允许的同时同步数据量# 如果是 1 ,表示同时只能 1 台slave同步新的master数据sentinel parallel-syncs mymaster 1# 同步时间超过多少认为是超时(毫秒)# 默认 3分钟sentinel failover-timeout mymaster 180000sentinel deny-scripts-reconfig yes

修改配置

如果 master 没有自定义密码,那么不需要修改配置

如果 自定义了密码,需要添加:

# 语法:sentinel auth-pass 配置中的master名 master密码sentinel auth-pass mymaster 1

然后,同样的文件复制两份并修改全部端口

(下面可以用 shell 命令快捷完成)

sed 命令解释

# 同时复制并替换出一份26380配置的配置文件sed 's/26379/26380/g' sentinel26379.conf >sentinel26380.conf# 同时复制并替换出一份26381配置的配置文件sed 's/26379/26381/g' sentinel26379.conf >sentinel26381.conf

启动

先起 master (起了就不用再起)

再起 slave

最后起哨兵

# 没有开后台,需要起三个窗口,不喜欢就开后台/usr/local/redis/bin/redis-sentinel /usr/local/redis/sentinel26379.conf/usr/local/redis/bin/redis-sentinel /usr/local/redis/sentinel26380.conf/usr/local/redis/bin/redis-sentinel /usr/local/redis/sentinel26381.conf

哨兵客户端连接

/usr/local/redis/bin/redis-cli -p 26379

连接之后只能执行 哨兵对应的命令

info

这时,我们再看 哨兵的配置文件,可以发现配置文件中自动添加了 salve 的信息

# 问题 :开了多个哨兵,相互不能识别

哨兵是会相互自动识别的,不识别唯一的可能是ID重复了

把配置里面默认的 id 注释了就好了

# 模拟master宕机(日志分析,流程分析)

我们把 master kill 了

# 哨兵工作原理

主从切换

哨兵在进行主从切换过程中经历三个阶段

监控

同步信息通知

保持连通故障转移

发现问题

竞选负责人

选人新的 master

新 master 上任,其他 slave 切换 master,原master 作为 slave 故障恢复后连接

下面看每一步的细节

阶段一:监控阶段

用于同步各个节点的状态信息

获取各个sentinel 的状态(是否在线)

获取master 的状态

各个 slave 的详细信息

master 属性(runid、role:master)

获取所有 slave 状态(根据 master 中的 slave 信息)

slave 属性(runid、role:slave、master_host、master_port、offset、…)

阶段二:通知阶段

一个 sentinel 间建立长期信息对等的阶段

sentinel 间形成“朋友圈”网络,各自检测 master、slave 的工作状态,并把检测到的状态在“朋友圈”中发布

阶段三:故障转移阶段

如果 sentinel 发现无法连通 master 会在内部标记 断开记录S_DOWN(主观下线:猜测挂了)

在 sentinel 的“朋友圈” 发布 master 断开信息

(如下图)

其他 sentinel 看到 信息会去 “围观” master

把围观结果也发上 sentinel 的 专属“朋友圈”

如果有半数(可自定义)的sentinel 在 “朋友圈” 说 master 挂了,就会把 master 状态表示 从S_DOWN(主观下线:猜测挂)改为O_DOWN(客观下线:确认挂了)

(如下图)

sentinel 知道 master 挂了,要选取出新的 master

选举出 新 master 之前。sentinel 间要先选出一个 “主导者”(主导新master的诞生~)

因此,会先先投票选 主导的 sentinel

投票机制就是简单的 向其他sentinel 要票,最后票数过半的为主导者(如果没有过半结果会一直重复投票,因此sentinel要单数!)

(如下图)

sentinel 独裁者决定 新 master 的流程(排除法)

排除不在线的排除响应慢的断开与原master断开时间久的(性能可能比较差)看优先原则 排除优先级低的排除 offset 前的排除 runid 大的 (到这步,肯定只剩一个 slave 了,那人就当选master)

(下图)

选定 新 master 后,发送指令

向新的 master 发送 slaveof no one向其他 slave发送 slaveof 新masterIP 端口

slave:你说你是哨兵,原来是罗马教皇锕。。

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。