前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >《Redis设计与实现》读书笔记(二十五) ——Redis主从复制具体过程

《Redis设计与实现》读书笔记(二十五) ——Redis主从复制具体过程

作者头像
用户1327360
发布2018-03-07 16:10:23
7710
发布2018-03-07 16:10:23
举报
文章被收录于专栏:决胜机器学习决胜机器学习

《Redis设计与实现》读书笔记(二十五)

——Redis主从复制具体过程

(原创内容,转载请注明来源,谢谢)

一、PSYNC命令执行过程

psync是新版redis复制使用的命令,下面讨论其执行过程。

psync命令调用方法有两种:

1)从服务器以前如果没有复制过任何主服务器,或者执行过slaveof no one命令,则第一次复制会发送psync ? -1命令,表示强制要求主服务器进行完全重同步。

2)如果从服务器以前复制过主服务器,则会发送psync <runid> <offset>,将主服务器的运行ID和从服务器当前自身复制偏移量发送给主服务器,由主服务器判断是要部分重同步还是完全重同步。

主服务器的回复有三种:

1)+fullresync<runid> <offset>,则表示要完全重同步。从服务器会记录runid,作为下次断线重连发送的内容;将offset作为从服务器当前的偏移量。

2)+continue,表示部分重同步,从服务器只需要等待主服务器将缺少的部分发送过来,再进行同步即可。

3)-err,表示主服务器版本低于2.8,不支持psync,则从服务器会再发送sync命令,进行完整同步。

如下图所示:

二、复制的实现

复制采用的命令是slaveof<masterip> <masterport>,详细实现步骤如下:

1、设置主服务器的ip和端口

执行上述命令后,从服务器会将主服务器的ip和端口设置在自身redisServer结构体中的属性中,ip设置到char数组的masterhost名称,port设置到int的masterport。

设置完成后,从服务器会向客户端返回OK。

2、建立套接字连接

执行slaveof命令后,从服务器将根据ip和端口号,与主服务器建立套接字连接。

从服务器成功连接主服务器后,从服务器将为该连接专门创建一个用于复制工作的文件事件处理器,这个处理器接收rdb文件、处理主服务器的命令传播等。

主服务器接收到从服务器的套接字连接后,为套接字创建相应的状态,并将从服务器看作一个连接到主服务器的客户端,此时从服务器同时具有客户端和服务器两个身份,从服务器可以向主服务器发送命令请求,主服务器会向从服务器发送命令回复。

3、发送PING命令

从服务器连接上主服务器后,会先发送一个PING命令,具有两个作用:

1)检查主从服务器的套接字读写状态是否正常。

2)检查主服务器当前可以正常处理请求。

从服务器会收到主服务器的三种回复的一种:

1)主服务器向从服务器回复内容,从服务器不能在规定时限内读取命令内容,则认为主从服务器当前网络不佳,无法处理后续的同步工作。从服务器会断开套接字,再自动重连并重新创建向主服务器的套接字。

2)主服务器向从服务器回复一个错误,表示主服务器当前无法处理从服务器的请求,从服务器会断开并重新创建向主服务器的套接字。

3)从服务器接收到主服务器的PONG回复,表示主从服务器网络正常,主服务器当前可以处理从服务器的命令,则从服务器会进入后续的步骤。

PING命令判断流程如下:

4、身份验证

从服务器收到PONG后,将进入身份验证阶段。

如果其有设置masterauth选项,则开始身份验证,否则不验证。如果需要验证,则从服务器接下来会给主服务器发送auth命令,并带上masterauth选项的值作为参数。

身份验证阶段会有以下几个结果:

1)主服务器没有设置requirepass选项,从服务器也没有设置masterauth,则跳过身份验证。

2)主服务器没有设置requirepass,而从服务器设置masterauth,会报noauth错误。

3)主服务器设置requirepass,而从服务器没有设置masterauth,会报nopassword is set错误。

所有错误都会终止当前的复制工作,并从创建套接字开始重新执行复制,直到验证通过。

5、发送端口信息

身份验证通过后,从服务器会向主服务器发送replconf listening-port <port-number>命令,向从服务器监听端口号。

主服务器接收到端口号后,会将其记录在对应客户端redisClient结构体中的属性中,类型是int,名称是slave-listening-port。该属性目前唯一作用是主服务器执行info replication命令时,打印出从服务器的端口号。

6、同步

完成上述步骤后,从服务器会发送psync给主服务器。

在同步操作之前,只有从服务器是主服务器的客户端,而同步之后,主服务器也是从服务器的客户端,即互为客户端。

这样主服务器才可以将保存在缓冲区的写命令(完整重同步)、保存在复制积压缓冲区(部分重同步)中的写命令发给从服务器。

7、命令传播

完成同步后,后续只要主服务器状态改变,都会给从服务器发送写命令,从服务器执行写命令后,就保证主从一致性。

六、心跳检测

在命令传播阶段,从服务器默认每秒1次的频率,向主服务器发送如下命令:

代码语言:javascript
复制
         replconfack <replication_offset>

replication_offset是从服务器的偏移量,发送此命令有三个作用:

1、检测主从服务器网络状态。

如果主服务器超过1秒没有接收到从服务器的replconfack命令,表示主从间的连接出问题了。info replication命令可以查看从服务器最后一次发送该命令的时间,属性值是lag,即lag大于1表示出问题了。

2、辅助实现min-slaves选项。

redis的min-slaves-to-write和min-slaves-max-lag两个选项可以在主服务器不安全的情况下,防止执行客户端的写命令。

例如min-slaves-to-write3,min-slaves-max-lag 10,表示少于3个从服务器或三个从服务器的延迟(lag)值都大于等于10秒,主服务器将拒绝执行写命令。

3、检测命令丢失。

由于每次发送replconfack命令,都带上当前的偏移量,这样就可以保证如果主服务器发送给从服务器的命令传播,由于网络问题导致数据丢失的问题能1秒内被主服务器发现。主服务器发现后,会将相应偏移量的内容从复制积压缓冲区取出,并发送给从服务器。

replconfack命令和复制积压缓冲区的概念,都是从redis2.8开始有的,在此之前的版本,主服务器无法发现从服务器的数据丢失。因为使用主从的情况下,为了数据一致性,尽量使用2.8以上版本的redis。

七、总结

1、redis2.8之前的版本,主从复制中,每次从服务器断线重连后,都要进行整个服务器的同步;而2.8版本开始,在一定情况下,可以实现部分重同步。

2、部分重同步是通过复制偏移量来判断是否需要,通过复制积压缓冲区来取出偏移量范围内的全部数据,通过从服务器发送给主服务器的主服务器运行ID来判断上一次从服务器连接的主服务器与此次连接是否一致。

3、如果复制偏移量超出复制积压缓冲区,或者从服务器发送的运行ID和主服务器当前运行ID不一致,或者主服务器的redis版本在2.8之前,都会进行完全重同步。

4、复制刚开始,从服务器是客户端,到开始同步的时候,主从服务器互为客户端。

5、复制过程包括:从服务器设置主服务器ip和端口;建立套接字;发送PING命令;身份验证;发送端口信息;同步;命令传播。

6、当主从进入命令传播阶段,从服务器每秒(时间可配置)给主服务器发送一条命令,内容是当前从服务器的偏移量,以确保主从网络正常,并且如果偏移量和主服务器当前的不一致,也便于主服务器再次发送偏移数据,以保证主从数据一致性。

7、由于效率以及数据一致性,如果要采用主从同步,建议使用redis2.8或以上的版本。

——written by linhxx 2017.09.12

本文参与 腾讯云自媒体分享计划,分享自微信公众号。
原始发表:2017-09-12,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 决胜机器学习 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
云数据库 Redis
腾讯云数据库 Redis(TencentDB for Redis)是腾讯云打造的兼容 Redis 协议的缓存和存储服务。丰富的数据结构能帮助您完成不同类型的业务场景开发。支持主从热备,提供自动容灾切换、数据备份、故障迁移、实例监控、在线扩容、数据回档等全套的数据库服务。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档