文章插图
最后计算结果就会落到 0-16383 之间去 。
当 Redis Cluster 的客户端来连接集群时 , 它也会得到一份集群的槽位配置信息并将其缓存在客户端本地 。这样当客户 端要查找某个 key 时 , 可以直接定位到目标节点 。同时因为槽位的信息可能会存在客户端与服务器不一致的情况 , 还需 要纠正机制来实现槽位信息的校验调整 。
集中式集群和分片式集群
Redis 节点之间使用的是 gossip 协议进行通信 , 每个节点之间都会互相通信 。
gossip 协议包含多种消息 , 包括 ping , pong , meet , fail 等等 。
ping :每个节点都会频繁给其他节点发送 ping , 其中包含自己的状态还有自己维护的集群元数据 , 互相通过 ping 交换元数据;
pong: 返回 ping 和 meet , 包含自己的状态和其他信息 , 也可以用于信息广播和更新;
fail: 某个节点判断另一个节点 fail 之后 , 就发送 fail 给其他节点 , 通知其他节点 , 指定的节点宕机了 。
meet :某个节点发送 meet 给新加入的节点 , 让新节点加入集群中 , 然后新节点就会开始与其他节点进行通信 , 不需要发送形成网络的所需的所有 CLUSTER MEET 命令 。发送 CLUSTER MEET 消息以便每个节点能够达到其他每个节点只需通 过一条已知的节点链就够了 。由于在心跳包中会交换 gossip 信息 , 将会创建节点间缺失的链接 。
gossip 协议的优点在于元数据的更新比较分散 , 不是集中在一个地方 , 更新请求会陆陆续续 , 打到所有节点上去更新 , 有一定的延时 , 降低了压力;缺点在于元数据更新有延时可能导致集群的一些操作会有一些滞后 。
就是自己提供服务的端口号 +10000 , 比如 6379 , 那么用于节点间通信 的就是 16379 端口 。每个节点每隔一段时间都会往另外几个节点发送 ping 消息 , 同时其他几点接收到 ping 消息之后返回 pong 消息 。
还有就是集中式的 , 比如 ZK 集群
集中式的有点在于数据的更新和读取 , 时效性非常好 , 一旦元数据出现变更立即就会更新到集中式( master )的存储中 , 其他节点读取的 时候立即就可以立即感知到;不足在于所有的元数据的更新压力全部集中在一个地方 , 可能导致元数据的存储压力 。
Redis 集群选举机制
当 slave发现自己的master变为FAIL状态时 , 便尝试 发起选举 , 以期成为新的 master 。由于挂掉的master可能会有 多个 slave , 从而存在多个slave竞争成为master节点的过程 , 其过程如下:
1.slave发现自己的master变为FAIL
2.将自己记录的集群currentEpoch(选举轮次标记)加1 , 并广播信息给集群中其他节点
3.其他节点收到该信息 , 只有master响应 , 判断请求者的合法性 , 并发送结果
4.尝试选举的slave收集master返回的结果 , 收到 超过半数 master的统一 后变成新 Master
5.广播Pong消息通知其他集群节点 。
如果这次选举不成功 , 比如三个小的主从 A,B,C组成的集群 , A的master挂了 , A的两个小弟发起选举 , 结果B的master投给A的小弟A1 , C的master投给了A的小弟A2 , 这样就会发起第二次选举 , 选举轮次标记+1继续上面的流程 。事实上从节点并不是在主节点一进入 FAIL 状态就马上尝试发起选举 , 而是有一定延迟 , 一定的延迟确保我们等待FAIL状态在集群中传播 , slave如果立即尝试选举 , 其它masters或许尚未意识到FAIL状态 , 可能会拒绝投票 。同时下面公式里面的随机数 , 也可以有效避免slave同时发起选举 , 导致的平票情况 。
【Redis集群搭建及选举原理】•延迟计算公式:
DELAY = 500ms + random(0 ~ 500ms) + SLAVE_RANK * 1000ms
•SLAVE_RANK表示此slave已经从master复制数据的总量的rank 。Rank越小代表已复制的数据越新 。这种方式下 , 持有最新数据的slave将会首先发起选举(理论上) 。
前面说到这种分片的集群模式的集群可以部分提供服务 , 当 redis.conf的配置cluster-require-full-coverage为no时 , 表示当一个小主从整体挂掉的时候集群也可以用 , 也是说 0-16383个槽位中 , 落在该主从对应的slots上面的key是用不了的 , 但是如果key落在其他的范围是仍然可用的 。
推荐阅读
- 大厂Redis 性能优化的 13 条军规!收好了
- 分布式系统ID的生成方法之UUID、数据库、算法、Redis、Leaf方案
- Redis02-Redis高性能与epoll
- 为什么单线程的Redis能够达到百万级的QPS?
- Redis 位图基础到统计活跃用户
- redis cli命令详解
- 轻松搭建基于 Serverless 的 ThinkPHP 应用
- 直播流 nginx+ffmpeg搭建流媒体服务器
- Redis 数据迁移方法
- redis的多路复用是什么鬼