Redis Cluster:实现 Redis 高可用

508 阅读3分钟

这是我参与8月更文挑战的第4天,活动详情查看:8月更文挑战

搭建Redis Cluster,实现 Redis 的集群存储,实现高可用。 为什么要搭建Redis Cluster?

Redis Cluster能实现 Redis 的集群存储,实现高可用。
主从复制单机的QPS无法满足日益增长的业务需求。
基于数据量的考虑,单台服务器内存无法满足业务数据的需求时,需考虑集群,把数据分布到不同服务器上。

Redis Cluster的分区方案

虚拟槽分区是Redis Cluster采用的分区方案。预设虚拟槽的范围为 0 到 16383。

(将数据打散,又可以保证数据分配均匀)

image.png 数据分配步骤:

1. 把 16383 按照槽节点平均分配。
2. 对每个 key 按照 CRC16 规则进行 hash 运算
3. hash 值对 16383 取余,将结果发送到节点
4. 节点接收到数据,验证是否在自己管理的槽编号的范围 
如果在自己管理的槽编号范围内,则把数据保存到数据槽中,然后返回执行结果 
如果在自己管理的槽编号范围外,则会向客户端返回 moved 重定向异常
如果客户端收到 moved 重定向,会从中获取目标节点的信息,客户端会向目标节点获取信息。

Redis Cluster的节点之间会共享消息,每个节点都会知道是哪个节点负责哪个范围内的数据槽。

在对集群进行扩容和缩容时,需要对槽及槽中数据进行迁移。如果此时正在进行集群扩展或者缩空操作,当客户端向正确的节点发送命令时,槽及槽中数据已经被迁移到别的节点了,就会返回ask,这就是ask重定向机制。

image.png

故障发现

Redis Cluster通过ping/pong消息实现故障发现。

ping/pong不仅能传递节点与槽的对应消息,也能传递其他状态,比如:节点主从状态,节点故障等。

1.节点1定期发送ping消息给节点2 
2.如果发送成功,代表节点2正常运行,节点2会响应PONG消息给节点1,节点1更新与节点2的最后通信时间 
3.如果发送失败,则节点1与节点2之间的通信异常判断连接,在下一个定时任务周期时,仍然会与节点2发送ping消息 
4.如果节点1发现与节点2最后通信时间超过cluster-node-timeout,则把节点2标识为pfail状态,即节点2主观下线。

集群内的节点会通过ping/pong交流,如果发现集群内半数以上持有槽的主节点都标记某节点pfail状态时,该节点会客观下线。集群会向广播下线节点的消息,并选举从节点替换主节点

节点选举

如果某个主节点没有从节点,那么当它发生故障时,则整个集群会处于完全不可用的状态。

由于挂掉的master可能会有多个slave,从而存在多个slave竞争成为master节点的过程, 其过程如下:

1.slave发现自己的master变为FAIL
2.将自己记录的集群currentEpoch(选举轮次标记)加1,并广播信息给集群中其他节点 
3.其他节点收到该信息,只有master响应,判断请求者的合法性,并发送结果
4.尝试选举的slave收集master返回的结果,收到超过【主节点数/2+1】的数量master的统一后变成新Master
5.广播Pong消息通知其他集群节点。