[redis] 主从复制原理

全复制流程

  • 当 从服务器第一次复制主服务器,从服务器(slave)使用 SLAVEOF host port 命令,向主服务器(master)发送复制请求, master 收到后返回 OK;

    slave 保存 master  信息,结构 server.h/redisServer 结构中 masterhost, masterport
    
  • 异步执行复制工作,内部流程如下,(runid:master 运行 ID) (offect:复制偏移量):

    • slave 使用 socket 连接 master 节点,连接建立成功后,发送 PING 命令,
      如没有得到 PONG 命令响应(代表 master 目前不能正常处理),继续重连。
    • 如果 slave 设置了masterauth,则需要进行权限验证;
    • 通过权限验证后,slave 执行 REPLCONF listening-port ,向 master 提供 slave 监听端口号,
      端口号会被 master 保存至 server.h/client slave_listening_port 中,可以使用 INFO REPLICATION 查看(port值);
    • slave 向 master 发送 PSYNC <? > <-1>,代表全量复制;PSYNC <runid> <offect>。
    • master 接收到请求后,调用 replication.c/slaveTryPartialResynchronization() 并生成 runid 和 offect;
    • master 返回 +FULLRESYNC <runid> <offect> 其中 offect 为 master 当前的复制偏移量。
    • slave 保存 runid 及 offect 当做 slave 的当前复制偏移量,此时 master 调用 BGSVAE 生成 RDB 文件。
    • RDB 生成好之后, master 发送 RDB 文件到 slave;
    • slave 接收到 RDB 后进行处理(加载到内存中),处理完成后 slave 会进行 PSYNC runid offect 请求,此时为<部分重同步>

部分复制流程

  • 因网络或其他问题导致 slave 与 master 的 offect 不一致

    • slave 会发送 PSYNC <runid> <offect>
    • master 接收到 PSYNC 请求后,对照 offect
    • 如果 slave 的 offect 之后的数据(offect + 1) 仍然存在于 master 的复制积压缓冲区中,则执行部分复制;否则进行全复制流程
    • 如果 slave 请求的 runid 与 master 的 runid 不一致也执行全复制流程
  • 可以通过 info replication 命令查看偏移量;master_repl_offset(主服务器偏移量) 、slave_repl_offset(从服务器偏移量)

心跳检测

  • slave 以默认 1 秒的频率,向 master 发送命令:REPLCONF ACK <replication_offect> 其中(replication_offect 为 slave offect),命令作用如下
    • 检测主从服务器网络状态
    • 辅助实现 min-slaves 实现
      • 可以设置 master 达到一定的条件拒绝执行写命令(min-slaves-to-write、min-slaves-max-lag)
    • 检测命令丢失
      • 如果检测到命令丢失,master 将会向 slave 补发缺失数据
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章