1. 前言

和MySQL主从复制的原因一样,Redis虽然读取写入的速度都特别快,但是也会产生读压力特别大的情况。为了分担读压力,Redis支持主从复制,Redis主从复制可以根据是否是全量分为全量同步和增量同步。

2. 旧版复制功能实现

redis复制功能分为同步和命令传播两种操作:

(1)同步操作负责将从数据库的状态更新为和主数据库状态一致

(2)命令传播操作则用于当主服务器状态修改时,让从服务器状态重新回到一致

2.1 同步

同步操作由sync操作完成:

(1)从服务器向主服务器发送sync命令

(2)收到sync命令的主服务器执行BGSAVE命令,生成RDB文件,并使用一个缓冲区缓存生成RDB期间所有的写命令

(3)RDB生成完成时,发送RDB给从服务器,从服务器载入RDB,状态和主服务器一致

(4)然后主服务器将缓冲区中的写命令全部传给从服务器,状态一致

2.2 命令传播

同步操作完成后,主从状态一致,但是每当客户端向主服务器执行写命令时,主服务器会修改,和从服务器状态不一致,为了让主从状态重新回到一致,主服务器会发送写命令给从服务器,让从服务器回到和主服务器一致的状态。

2.3 旧版复制功能的不足之处

在redis2.8之前,主从服务器的复制会分为两种:

(1)初次复制:从服务器以前从没复制过其他主服务器,或者从服务器的主服务器换了

(2)断线后复制:处于命令传播阶段的主从服务器,发生了断线,重新连上后,从服务器继续复制主服务器

为什么说效率低呢?因为在旧版复制中,断线重新连接后进行的复制,是通过sync命令实现的,而之前说了sync命令实现是主服务器重新生成RDB文件,发送给从服务器,重新生成RDB是很低效的,而且主服务器生成RDB时是阻塞状态的,所以旧版复制是低效率的。

3. 新版复制功能实现

为了解决旧版复制低效问题,新版复制采用了psync命令来代替sync命令,psync命令具有完全重同步和部分重同步:

(1)完全重同步:和上面的sync一样

(2)部分重同步:专门用于负责处理断线后重连,通过重连后只执行断线期间的写命令而不是全同步来达到高效

3.1 部分重同步实现

部分重同步实现由以下三部分构成:

(1)主服务器的复制偏移量和从服务器的复制偏移量

(2)主服务器的复制积压缓冲区

(3)服务器运行ID

3.1.1 复制偏移量

主从服务器都会维持一个复制偏移量:

  • 主服务器每次向从服务器发送n个字节的命令,就在自己复制偏移量加n
  • 从服务器每次接收到n个字节数据,就在自己复制偏移量加n

例如,主从服务器当前偏移是100,主向从服务器发送33个字节命令,那么主从此时的复制偏移量都是133,所以判断主从当前状态是否一致,可以通过复制偏移量来判断:复制偏移量如果一样,就代表状态一致,否则不一致。如果断线时,从服务器因为收不到命令,而主服务器一直发送命令,这时的偏移量肯定不一样,所以状态不一致,那么如果让中间漏掉的命令重新传给从服务器呢,这和积压缓冲区有关。

3.1.2 复制积压缓冲区

复制积压缓冲区是一个主服务器维护的固定长度的先进先出队列。每当主服务器进行命令传播时,它不仅将命令传给从服务器,还会将命令写入到缓冲区:

如上图所示,就是一个积压缓冲区的现状,当从服务器重连后,向主服务器发送一个psycn命令,同时会将从服务器当前的复制偏移量(offset)带过去,主服务器会根据从服务器的offset,来决定是全同步还是部分同步:

(1)如果从服务器的offset是10086,那么此时要复制的偏移量应该是从10087开始,在缓冲区存在,将从10087开始往后所有数据都发送给从服务器,所以执行的是部分重同步

(2)相反的,如果不存在,就需要进行全同步了!

如下图:如果进行部分重同步,就向从服务器发送一个CONTINUE回复。

3.1.3 服务器运行ID

除了复制偏移量和复制积压缓冲区之外,实现部分重同步还需要用到服务器运行ID(run ID):

  • 每个Redis服务器,不论主服务器还是从服务,都会有自己的运行ID

当从服务器对主服务器进行初次复制时,主服务器会将自己的运行ID传送给从服务器,而从服务器则会将这个运行ID保存起来(注意哦,是从服务器保存了主服务器的ID)。

当从服务器断线并重新连上一个主服务器时,从服务器将向当前连接的主服务器发送之前保存的运行ID:

  • 如果从服务器保存的运行ID和当前连接的主服务器的运行ID相同,那么说明从服务器断线之前复制的就是当前连接的这个主服务器,主服务器可以继续尝试执行部分重同步操作;
  • 相反地,如果从服务器保存的运行ID和当前连接的主服务器的运行ID并不相同,那么说明从服务器断线之前复制的主服务器并不是当前连接的这个主服务器,主服务器将对从服务器执行完整重同步操作。

4. 心跳机制

在命令传播阶段时,从服务器每隔一秒都会向主服务器发送命令:REPLCONF ACK <replication_offset>,每发送一次这个命令从服务器都会向主服务器报告一次自己的复制偏移量,如果超过一秒,就代表主从连接出了问题。那此时尽管主服务器发送给从服务器的SET key value丢失了。也无所谓,主服务器马上就知道了,但是要注意,这时的偏移量不一致,并不是断线导致的,而是以为主服务器传给从服务器的命令丢失了,连接情况还是正常的,这种称之为命令丢失。

redis的主从复制原理的更多相关文章

  1. 5.如何保证 redis 的高并发和高可用?redis 的主从复制原理能介绍一下么?redis 的哨兵原理能介绍一下么?

    作者:中华石杉 面试题 如何保证 redis 的高并发和高可用?redis 的主从复制原理能介绍一下么?redis 的哨兵原理能介绍一下么? 面试官心理分析 其实问这个问题,主要是考考你,redis ...

  2. Redis 主从复制原理及雪崩 穿透问题

    定义: Redis是一个开源的使用ANSI C语言编写.支持网络.可基于内存亦可持久化的日志型.Key-Value数据库,并提供多种语言的API.从2010年3月15日起,Redis的开发工作由VMw ...

  3. Redis主从复制原理总结

    和Mysql主从复制的原因一样,Redis虽然读取写入的速度都特别快,但是也会产生读压力特别大的情况.为了分担读压力,Redis支持主从复制,Redis的主从结构可以采用一主多从或者级联结构,Redi ...

  4. 【*】深入理解redis主从复制原理

    1.复制过程 从节点执行 slaveof 命令. 从节点只是保存了 slaveof 命令中主节点的信息,并没有立即发起复制. 从节点内部的定时任务发现有主节点的信息,开始使用 socket 连接主节点 ...

  5. 深入Redis 主从复制原理

    原文:深入Redis 主从复制原理 1.复制过程 2.数据间的同步 3.全量复制 4.部分复制 5.心跳 6.异步复制 1.复制过程 从节点执行 slaveof 命令. 从节点只是保存了 slaveo ...

  6. redis之(十四)redis的主从复制的原理

    一:redis主从复制的原理,步骤.   第一步:复制初始化 --->从redis启动后,会根据配置,向主redis发送SYNC命令.2.8版本以后,发送PSYNC命令. --->主red ...

  7. Redis面试篇 -- Redis主从复制原理

        Redis一般是用来支撑读高并发的,为了分担读压力,Redis支持主从复制.架构是主从架构,一主多从, 主负责写,并且将数据复制到其它的 slave 节点,从节点负责读. 所有的读请求全部走从 ...

  8. Redis主从复制以及主从复制原理

    Redis 是一个开源的使用 ANSI C 语言编写.支持网络.可基于内存亦可持久化的日志型.Key-Value 数据库,并提供多种语言的 API.从 2010年 3 月 15 日起,Redis 的开 ...

  9. 彻底搞懂Redis主从复制原理及实战

    欢迎关注公众号:「码农富哥」,致力于分享后端技术 (高并发架构,分布式集群系统,消息队列中间件,网络,微服务,Linux, TCP/IP, HTTP, MySQL, Redis), Python 等 ...

随机推荐

  1. Nginx用法详解

    nginx作为一个高性能的web服务器,想必大家垂涎已久,蠢蠢欲动,想学习一番了吧,语法不多说,网上一大堆.下面博主就nginx的非常常用的几个功能做一些讲述和分析,学会了这几个功能,平常的开发和部署 ...

  2. JS基础_立即执行函数

    <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title> ...

  3. 在QT中添加LIB的方法

    注意:-L后面跟着的目录不能用空格,否则会出现读不到的情况. 例如win32下添加D:\app\my.lib   就 pro文件中 LIBS += -LD:\app\debug\ -lmy

  4. 面试之HTML5 Web存储

    前几天面试遇到了一个题是问localStorage和sessionStorage的区别,当时的回答不是很全面,今天就针对这个问题做一下整理(概念,用法,区别) HTML5 Web存储,一个比 cook ...

  5. vuex数据传递的流程

    当组件修改数据的时候必须通过store.dispacth来调用actions中的方法. 当actions中的方法被触发的时候通过调用commit的方法来触发mutations里面的方法 mutatio ...

  6. java 日期。时间

    友情链接: https://www.cnblogs.com/wanson/articles/10818955.html

  7. BootStrap【一、概述】

    4月底出去浪了一圈,回来收了一周的心才收回来,5.12,重启自学 今天早上总算大概把JAVASpring相关的东西过了一边,Spring基础.IOC.AOP,看的有些头晕脑胀 公司项目除了Spring ...

  8. (十五)连接网络adb,android模拟器打开

    第一步:Android开发板连接usb和网线 adb shell setprop service.adb.tcp.port 5555 adb shell stop adbdadb shell star ...

  9. c#中打开视频,word

    打开所有的文件的 代码,包括word/ppt/txt/xls/mp3/视频文件 添加using using System.Diagnostics; string fileName = @"D ...

  10. 算法笔记--CDQ分治 && 整体二分

    参考:https://www.luogu.org/blog/Owencodeisking/post-xue-xi-bi-ji-cdq-fen-zhi-hu-zheng-ti-er-fen 前置技能:树 ...