Redis的复制功能分为同步(sync)和命令传播(commandpropagate)两个操作
同步
从服务器对主服务器的同步操作需要通过向主服务器发送SYNC命令来完成,以下是SYNC命令的执行步骤:
1)从服务器向主服务器发送SYNC命令
2)收到SYNC命令的主服务器执行BGSAVE命令,在后台生成一个RDB文件,并使用一个缓冲区记录从现在开始执行的所有写命令
3)主服务器将BGSAVE命令生成的RDB文件发送给从服务器,从服务器接收并载入这个RDB文件,将自己的数据库状态更新至主服务器执行BGSAVE命令时的数据库状态
4)主服务器将记录在缓冲区里面的所有写命令发送给从服务器,从服务器执行这些写命令,将自己的数据库状态更新至主服务器数据库当前所处的状态
命令传播
在同步操作执行完毕之后,主从服务器两者的数据库将达到一致状态,但这种一致并不是一成不变的,每当主服务器执行客户端发送的写命令时,主服务器的数据库就有可能会被修改,并导致主从服务器状态不再一致
为了让主从服务器再次回到一致状态,主服务器需要对从服务器执行命令传播操作:
主服务器会将自己执行的写命令,也即是造成主从服务器不一致的那条写命令,发送给从服务器执行,当从服务器执行了相同的写命令之后,主从服务器将再次回到一致状态
主从通信中断后如何处理?
Redis2.8以前,主从间重新连接后,会重新执行一遍同步操作,master把自己的数据库保存为文件发送给slave
此方式效率较低,会消耗较多的CPU 内存 IO 网络资源,所以,2.8以后,使用了新的处理方式:PSYNC命令,支持部分重同步
部分重同步用于处理断线后重复制情况:master会记录断线后的写操作,当slave重新连接后,slave只需接收并执行这部分断线期间的写操作记录,就可以将数据库更新至主服务器当前所处的状态