Redis的sync与psync命令

在日常开发中我们可能拿单台Redis测试,可能完全没有啥问题,当线上Reids读压力大的时候,我们可能会搭建Redis的主从,所有的服务都不是百分百可靠的,所以我们可能会往高可用方向发展如:哨兵,集群,在我们这些高可用的架构中都会有主服务器,主服务器下面可能有一台从服务器或者多台从服务器,这些都是为了避免单点故障和把master跟slave读写分离,提高相应速度,在高可用的架构中当有服务器故障的时候,其他的服务器也可以对外提供,提供了系统的可用性,避免了单点故障的问题。

Redis能实现读写分离又能实现故障切换是怎么实现的呢(故障切换在后面的章节说),在读写分离的时候master会把自己数据库更新的数据也会在slave服务器中更新,如图:

redis的主从同步.png

在Redis的读写分离中:

  • master既可以读也可以写,slave一般进行读操作,当master写操作导致数据变化时会自动将数据同步给slave数据库。

  • 一个master可以拥有多个slave,而一个salve只能拥有一个master。

  • slave下面也可以有slave,级联结构同步数据

在Redis2.8之前只能使用sync命令来主从同步数据就是全量复制,sync命令会在不管slave是第一次启动还是断线重连都会全量的去复制数据,在Redis2.8之后使用psync命令来完成主从数据同步,psync弥补对sync只能全量同步数据的问题,psync的同步过程分为全量复制跟增量复制。

同步场景

sync全量同步

Redis的同步数据在主从初次启动psync跟sync命令都是全量复制。当服务器断线重连时,sync采用的是全量复制而psync采用的是增量复制

2.8版本之前的同步方式

redis的sync.png

2.8 之前的同步数据是sync命令的全量复制,在同步过程中主要就俩个初始化的时候同步跟增量同步(初始化之后的同步数据,断线重连也就全量复制了)

总结下Redis的sync同步数据过程:

  • 当slave启动后或者断开重连后,会向master发送sync命令。
  • master节点收到sync命令后会开始在后台保存快照(即RDB持久化,在主从复制时,会无条件触发RDB),并将保存快照期间接收到的命令缓存起来。
  • master节点执行RDB持久化完后,向所有slave节点发送快照RDB文件,并在发送快照期间继续记录被执行的写命令。
  • slave节点收到快照文件后丢弃所有旧数据(会清空所有数据),载入收到的快照。
  • master节点快照发送完毕、slave节点载入快照完毕后,master节点开始向slave节点发送缓冲区中的写命令。
  • master节点完成对快照的载入,开始接收命令请求,并执行来自主数据库缓冲区的写命令。(从数据库初始化完成)
  • master节点每执行一个写命令就会向slave节点发送相同的写命令,slave节点接收并执行收到的写命令。(命令传播操作,slave节点初始化完成后的操作)

总结需要注意的点:

  1. slave在同步时,会清空所有数据,slave在与master进行初连接时,slave中的所有数据都将丢失,替换成master发送的数据。

  2. Redis不支持主主复制。

  3. 主从复制不会阻塞master(不会阻塞master处理客户端请求),因为RDB是异步进行的;相反slave在初次同步数据时会阻塞,不能处理客户端读请求。

  4. 当多个slave尝试连接同一个主服务器的时候,就会出现以下两种情况:

    一是:如果master节点保存快照还未执行,所有从服务器都会接收到相同的快照文件和相同缓冲区写命令。

       二是:master节点保存快照正已经执行完毕,当master与较早的slave完成以上全部步骤之后,master会跟新连接的slave重新执行RDB保存快照。
    

如果slave连接的时机不凑巧的话,进行多次RDB保存快照,会大量消耗master资源(CPU、内存和磁盘I/O资源)。

psync增量同步

redis2.8之前的版本中断线情况下SYNC进行全量同步的低效问题,在Redis 2.8之后使用psync命令代替sync命令执行同步操作,psync具备了数据全量重同步 和 部分重同步模式

  • 全量重同步:跟redis2.8之前的版本一样全量复制。

  • 部分重同步:salve断开又重新连时,在命令传播阶段,只需要发送与master断开这段时间执行的写命给slave即可,可以理解为增量同步

PSYNC执行过程中比较重要的概念有3个:runid、offset(复制偏移量)以及复制积压缓冲区。

1.runid

   每个Redis服务器都会有一个表明自己身份的ID。在PSYNC中发送的这个ID是指之前连接的Master的ID,如果没保存这个ID,PSYNC的命令会使用”PSYNC ? -1” 这种形式发送给Master,表示需要全量复制。

2.offset(复制偏移量)

   在主从复制的Master和Slave双方都会各自维持一个offset。Master成功发送N个字节的命令后会将Master里的offset加上N,Slave在接收到N个字节命令后同样会将Slave里的offset增加N。

Master和Slave如果状态是一致的那么它的的offset也应该是一致的。

3.复制积压缓冲区

  复制积压缓冲区是由Master维护的一个固定长度环形积压队列(FIFO队列),它的作用是缓存已经传播出去的命令。当Master进行命令传播时,不仅将命令发送给所有Slave,还会将命令写入到复制积压缓冲区里面。

怎么配置复制积压区

复制积压缓冲区本质上是一个固定长度的循环队列,默认情况下积压队列的大小为1MB,可以通过配置文件设置队列大小:

设置复制积压缓冲区大小,积压队列越大,允许主从数据库断线的时间就越长

repl-backlog-size 10mb

Redis同时也提供了当没有slave需要同步的时候,多久可以释放环形队列,默认一小时:

没有salve连接时,多久释放一次复制积压缓冲区

repl-backlog-ttl 3600

psync的执行过程

psync流程图.jpg

如上图,PSYNC执行过程和SYNC的区别在于:salve连接时,判断是否需要全量同步,全量同步的逻辑过程和SYNC一样。PSYNC执行步骤如下:

1.客户端向服务器发送SLAVEOF命令,即salve向master发起连接请求时,slave根据自己是否保存Master runid来判断是否是第一次连接。

2.如果是第一次同步则向Master发送 PSYNC ? -1 命令来进行完整同步;如果是重连接,会向Master发送PSYNC runid offset命令(runid是master的身份ID,offset是从节点同步命令的全局迁移量)。

3.Master接收到PSYNC 命令后,首先判断runid是否和本机的id一致,如果一致则会再次判断offset偏移量和本机的偏移量相差有没有超过复制积压缓冲区大小,如果没有那么就给Slave发送CONTINUE,此时Slave只需要等待Master传回失去连接期间丢失的命令。

如果runid和本机id不一致或者offset差距超过了复制积压缓冲区大小,那么就会返回FULLRESYNC runid offset,Slave将runid保存起来,并进行全量同步。

主节点在命令传播时,主数据库会将每一个写命令传递给从数据库的同时,都会将写命令存放到积压队列,并记录当前积压队列中存放命令的全局偏移量offset。当salve重连接时,master会根据从节点传的offset在环形积压队列中找到断开这段时间执行的命令,并同步给salve节点,达到增量同步结果。

乐观复制

Redis采用了乐观复制的策略,也就是在一定程度内容忍主从数据库的内容不一致,但是保持主从数据库数据的最终一致性。具体来说,Redis在主从复制的过程中,本身就是异步的,在主从数据库执行完客户端请求后会立即将结果返回给客户端,并异步的将命令同步给从数据库,但是这里并不会等待从数据库完全同步之后,再返回客户端。这一特性虽然保证了主从复制期间性能不受影响,但是也会产生一个数据不一致的时间窗口,如果在这个时间窗口期间网络突然断开连接,就会导致两者数据不一致。如果不在配置文件中添加其他策略,那就默认会采用这种方式,乐观二字也就体现在这里。  当然了,上面这种方式并不是绝对的,只要牺牲一点性能,还是可以避免上述问题。在配置文件中:

<pre class="cm-s-default" style="color: rgb(89, 89, 89); margin: 0px; padding: 0px; background: none 0% 0% / auto repeat scroll padding-box border-box rgba(0, 0, 0, 0);"> #代表至少N台从服务器完成复制,才允许主服务器可写入,否则会返回错误。 min-slaves-to-write 3 #允许从服务器断开连接的时间(单位s) min-slaves-max-lag 10</pre>

扩展面试题:

Redis的哨兵是怎么通信的?

扩展二:

Redis不管是旧版还是新版,复制的实现都可以分为下面几个步骤

建立套接字连接

从服务器根据设置的套接字创建连向主服务器的套接字连接,主服务器接收从服务器的套接字连接之后,为该套接字创建响应的客户端状态,并将此时的从服务器看做是主服务器的客户端,也就是该从服务器同时具备服务器与客户端两个身份。

发送PING命令

PING命令主要有两种作用:虽然建立了套接字连接,但是还未使用过,通过发送PING命令检查套接字的读写状态是否正常;通过发送PING命令检查主服务器能否正常处理命令请求,能处理主服务器回复PONG。

身份验证

从服务器接收到主服务器返回的“PONG”回复,接下来就需要考虑身份验证的事。如果从服务器设置了masterauth选项,那么进行身份验证,如果从服务器没有设置masterauth选项,那么不进行身份验证。

发送端口信息

在身份验证步骤之后,从服务器将执行命令REPLCONF listening-port <port>,向主服务器发送从服务器的监听端口号。

同步

从服务器向主服务器发送SYNC命令、PSYNC命令,执行同步操作。

命令传播

主从服务器就会进入命令传播阶段,主服务器只要将自己执行的写命令发送给从服务器,而从服务器只要一直执行并接收主服务器发来的写命令。

总结:主从刚刚连接的时候,会进行全量同步;全同步结束后,进行增量同步。当然,如果有需要slave 在任何时候都可以发起全量同步。Redis的策略是,无论如何,首先会尝试进行增量同步,如不成功,要求从机进行全量同步。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 194,911评论 5 460
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 82,014评论 2 371
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 142,129评论 0 320
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,283评论 1 264
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 61,159评论 4 357
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,161评论 1 272
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,565评论 3 382
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,251评论 0 253
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,531评论 1 292
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,619评论 2 310
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,383评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,255评论 3 313
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,624评论 3 299
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 28,916评论 0 17
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,199评论 1 250
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,553评论 2 342
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,756评论 2 335

推荐阅读更多精彩内容