网站用单页面框架做,石家庄全网推广,北京网站模板建设,响应式网站 解决方案Redis集群的主从复制原理-全量复制和增量复制-哨兵机制
作用
数据备份 这一点直观,因为现在有很多节点,每个节点都保存了原始数据的备份. 读写分离 这一点主要是当发生读写的时候#xff0c;读数据的操作大部分都会进入到从节点#xff0c;而写数据的操作都会进入到主节点读数据的操作大部分都会进入到从节点而写数据的操作都会进入到主节点之后主节点将数据修改的部分同步到从节点这样就降低了主节点的压力。 知识
run id 每一个节点都会有一个idoffset 偏移量主节点和从节点通过偏移量确定当前进行了多少数据的复制以及下一次应该从哪一个位置进行开始。
全量复制 首先从节点发起全量复制但是从节点不知道主节点的runid会发送一个偏移量使用1进行表示发送psync指令 runid offset 1。主节点收到请求发现runid是1说明这一次是全量复制后fork一个后台进程然后执行bgsave命令将主节点的数据全部生成一个RDB文件。RDB文件完毕之后发送给从节点从节点首先将本地数据全部请求然后将RDB文件加载到内存中。在主节点生成RDB文件的过程中如果这时候来了写进程主节点会将所有数据都写入到缓存中当从节点加载完成之后再将这个缓存文件发送给从节点如此实现了主从一致性。
增量复制 重新建立连接之后从节点发送psync指令runid 1 offset 600。主节点收到这个psync指令如果发现这个runid并不是自己的runid就会直接进行全量复制。这是因为从节点原来的主节点和现在的主节点是不相同的。主节点会将新写入的文件放入到一个环形缓冲区如果发现从节点发送的offset在环形缓冲区中那么就继续宁增量复制否则直接进行全量复制。将offset往后一直到环形队列底部的数据全部同步给从节点。
主从复制存在的问题 Redis主从复制模式下一旦主节点宕机不能提供服务需要人工讲从节点晋升为主节点同时还需要通知应用方更新主节点地址对于很多应用场景这种故障的处理方式不可接受。而且如果客户端发送的都是读操作请求那还可以由从库继续提供服务这在纯读的业务场景下还能被接受。但是一旦有写操作请求了按照主从库模式下的读写分离要求需要由主库来完成写操作。此时也没有实例可以来服务客户端的写操作请求了。 所以就需要一个模式来自动感知主库的状态并可以进行自动化切换此时哨兵模式就应运而生了。 哨兵机制的流程
哨兵其实就是一个运行在特殊模式下的 Redis 进程主从库实例运行的同时它也在运行。哨兵主要负责的就是三个任务监控、选主选择主库和通知。
我们先看监控。监控是指哨兵进程在运行时周期性地给所有的主从库发送 PING 命令检测它们是否仍然在线运行。如果从库没有在规定时间内响应哨兵的 PING 命令哨兵就会把它标记为“下线状态”同样如果主库也没有在规定时间内响应哨兵的 PING 命令哨兵就会判定主库下线然后开始自动切换主库的流程这个流程首先是执行哨兵的第二个任务选主。主库挂了以后哨兵就需要从很多个从库里按照一定的规则选择一个从库实例把它作为新的主库。这一步完成后现在的集群里就有了新主库。然后哨兵会执行最后一个任务通知。在执行通知任务时哨兵会把新主库的连接信息发给其他从库让它们执行 replicaof 命令和新主库建立连接并进行数据复制。同时哨兵会把新主库的连接信息通知给客户端让它们把请求操作发到新主库上。 问题 哨兵如何判断主库下线 主观下线哨兵进程会使用 PING 命令检测它自己和主、从库的网络连接情况用来判断实例的状态。如果哨兵发现主库或从库对 PING 命令的响应超时了那么哨兵就会先把它标记为“主观下线”。 客观下线由于哨兵都是集群部署所以只有当大部分哨兵都判断为“主观下线”的情况才会将其标记为“客观下线” 简单来说“客观下线”的标准就是当有 N 个哨兵实例时最好要有 N/2 1 个实例判断主库为“主观下线”才能最终判定主库为“客观下线”。这样一来就可以减少误判的概率也能避免误判带来的无谓的主从库切换。当然有多少个实例做出“主观下线”的判断才可以可以由 Redis 管理员自行设定。 问题 如何选择新主库 第一轮优先级最高的从库得分高。 用户可以通过 slave-priority 配置项给不同的从库设置不同优先级。比如你有两个从库它们的内存大小不一样你可以手动给内存大的实例设置一个高优先级。在选主时哨兵会给优先级高的从库打高分如果有一个从库优先级最高那么它就是新主库了。如果从库的优先级都一样那么哨兵开始第二轮打分。
第二轮和旧主库同步程度最接近的从库得分高。 就是说为去判断从库的偏移量offset。主库会用 master_repl_offset 记录当前的最新写操作在 repl_backlog_buffer 中的位置而从库会用 slave_repl_offset 这个值记录当前的复制进度slave_repl_offset越接近master_repl_offset的数据也就越新就会被选择成为主库。
第三轮ID 号小的从库得分高。 每个实例都会有一个 ID这个 ID 就类似于这里的从库的编号。目前Redis 在选主库时有一个默认的规定在优先级和复制进度都相同的情况下ID 号最小的从库得分最高会被选为新主库。这个也比较好理解ID越小代表着从库加入的时间越早在同分的情况下代表着运行时间越久也就说在一定程度上更加稳定。