Loading... <p><strong style="background-color: transparent;border: 0px;margin: 0px;padding: 0px;vertical-align: baseline;line-height: 40px">1、redis主从复制过程</strong><br />先不解释replication buffer和replication backlog,而先看看redis主从复制的过程。</p> <p>redis的主从复制分为两个阶段:</p> <p>1)同步(sync rdb snapshot):slave复制master的某时间点(t)的全量数据,t为master接收到slave的sync命令后执行rdb bgsave的时间点。2.8增加psync,支持full resync和partial resync命令。master发送rdb文件到slave,slave读取rdb把数据加载到内存。</p> <p>2)命令传播(commands propagation):同步时间点t后master上的数据更新到slave上, 发送的数据是redis的命令。</p> <p><strong style="background-color: transparent;border: 0px;margin: 0px;padding: 0px;vertical-align: baseline;line-height: 40px">2、replication buffer的作用</strong><br />redis的slave buffer(replication buffer,master端上)存放的数据是下面三个时间内所有的master数据更新操作。</p> <p>1)master执行rdb bgsave产生snapshot的时间</p> <p>2)master发送rdb到slave网络传输时间</p> <p>3)slave load rdb文件把数据恢复到内存的时间</p> <p><span style="color:red;background-color: transparent;border: 0px;margin: 0px;padding: 0px;vertical-align: baseline">replication buffer太小会引发的问题:</span></p> <p>replication buffer由client-output-buffer-limit slave设置,当这个值太小会导致主从复制链接断开。</p> <p>1)当master-slave复制连接断开,server端会释放连接相关的数据结构。replication buffer中的数据也就丢失了,此时主从之间重新开始复制过程。</p> <p>2)还有个更严重的问题,主从复制连接断开,导致主从上出现rdb bgsave和rdb重传操作无限循环。<br />查看[top redis headaches for devops – replication buffer]<br />因而推荐把slave replication buffer的hard/soft limit设置成512M</p> <pre class="brush:python;toolbar:false">config set client-output-buffer-limit "slave 536870912 536870912 0"</pre> <p><strong style="background-color: transparent;border: 0px;margin: 0px;padding: 0px;vertical-align: baseline;line-height: 40px">3、replication backlog的出现</strong></p> <p>在2.8版本,redis使用了新的复制方式,引入了复制积压缓冲(replication backlog)。<br />查看[Designing Redis replication partial resync]<br /><img src="//cto.wang/usr/uploads/2016/07/20160703180938-10.png" title="1428030898189458.png" alt="1.png" /></p> <p>上图来自《redis设计与实现》<br />当主服务器进行命令传播的时候,maser不仅将所有的数据更新命令发送到所有slave的replication buffer,还会写入replication backlog。当断开的slave重新连接上master的时候,slave将会发送psync命令(包含复制的偏移量offset),请求partial resync。如果请求的offset不存在,那么执行全量的sync操作,相当于重新建立主从复制。</p> <p><strong style="background-color: transparent;border: 0px;margin: 0px;padding: 0px;vertical-align: baseline;line-height: 40px">4、区分replication buffer 和 replication backlog</strong></p> <p>1) replication buffer对应于每个slave,通过config set client-output-buffer-limit slave 设置。</p> <p>2) replication backlog是一个环形缓冲区,整个master进程中只会存在一个,所有的slave公用。backlog的大小通过repl-backlog-size参数设置,默认大小是1M,其大小可以根据每秒产生的命令、(master执行rdb bgsave) +( master发送rdb到slave) + (slave load rdb文件)时间之和来估算积压缓冲区的大小,repl-backlog-size值不小于这两者的乘积。</p> <p><strong style="background-color: transparent;border: 0px;margin: 0px;padding: 0px;vertical-align: baseline;line-height: 40px">参考资料:</strong></p> <p>[1] redis设计与实现(黄健宏)</p> <p>[2] redis replication(http://redis.io/topics/replication)</p> <p>[3] [Designing Redis replication partial resync](http://antirez.com/news/31)</p> 最后修改:2021 年 12 月 10 日 10 : 53 AM © 允许规范转载 赞赏 如果觉得我的文章对你有用,请随意赞赏 赞赏作者 支付宝微信