文章目录
一、单点Redis的问题
- 数据丢失问题
实现Redis数据持久化。 - 并发能力问题
搭建主从集群,实现读写分离。 - 故障恢复问题
利用reids哨兵,实现健康检查和自动恢复。 - 存储能力问题
单键分片集群,利用插槽机制实现动态扩容。
二、主从架构
1、概述
单节点Redis的并发能力是有上限的,要进一步提高Redis的并发能力,就需要搭建主从集群,实现读写分离(主要应用于读多写少的情况)。
2、集群结构
3、主从数据同步原理
(1)全量同步
主从第一次建立连接时,会执行全量同步,将master节点的所有数据都拷贝到slave节点。这里有一个问题,master如何得知salve是第一次来连接呢,有几个概念,可以作为判断依据:
- Replication Id
简称replid,是数据集的标记,id一致则说明是同一数据集。每一个master都有唯一的replid,slave则会继承master节点的replid。 - offset
偏移量,随着记录在repl_baklog中的数据增多而逐渐增大。slave完成同步时也会记录当前同步的offset。如果slave的offset小于master的offset,说明slave数据落后于master,需要更新。 - 判断流程
slave做数据同步,必须向master声明自己的replication id 和offset,master才可以判断到底需要同步哪些数据。因为slave原本也是一个master,有自己的replid和offset,当第一次变成slave,与master建立连接时,发送的replid和offset是自己的replid和offset。master判断发现slave发送来的replid与自己的不一致,说明这是一个全新的slave,就知道要做全量同步了。master会将自己的replid和offset都发送给这个slave,slave保存这些信息。以后slave的replid就与master一致了。因此,master判断一个节点是否是第一次同步的依据,就是看replid是否一致。 - 完整流程描述
- slave节点请求增量同步。
- master节点判断replid,发现不一致,拒绝增量同步。
- master将完整内存数据生成RDB,发送RDB到slave。
- slave清空本地数据,加载master的RDB。
- master将RDB期间的命令记录在repl_baklog,并持续将log中的命令发送给slave。
- slave执行接收到的命令,保持与master之间的同步。
(2)增量同步
- 为什么需要增量同步
全量同步需要先做RDB,然后将RDB文件通过网络传输给slave,成本太高。因此除了第一次做全量同步,其她大多数时候slave与master都是做增量同步。 - 什么是增量同步
只更新slave与master存在差异的部分数据
4、总结
(1)全量同步和增量同步的区别
- 全量同步:master将完整内存数据生成RDB,发送RDB到slave。后续命令则记录在repl_baklog,逐个发送给slave。
- 增量同步:slave提交自己的offset到master,master获取repl_blaklog中从offset之后的命令给slave。
(2)什么时候执行全量同步
- slave节点第一次连接master节点时
- slave几点断开时间太久,repl_baklog中的offset已经被覆盖。
(3)什么时候执行增量同步
slave节点断开又恢复,并且在repl_baklog中能找到offset时。
三、Redis哨兵
1、介绍
Redis提供了哨兵(Sentienl)机制来实现主从集群的自动故障恢复。
2、哨兵原理
(1)集群结构
(2)哨兵的作用
-
监控
Sentinel会不断检查master和slave是否按预期工作
- 集群监控原理
Sentinel基于心跳机制监测服务状态,每隔1秒向集群的每个实例发送ping命令。- 主观下线
如果某sentinel节点发现某实例未在规定时间响应,则认为改实例主观下线。 - 客观下线
若超过指定数量(quorum)的sentinel都认为该实例主观下线,则该实例客观下线。quorum值最好超过Sentinel实例数量的一半。
- 主观下线
- 集群监控原理
-
自动故障恢复
- 如果master故障,Sentinel会将一个slave提升为master。当故障实例恢复后以新的master为主
- 集群故障恢复原理
-
一旦发现master故障,sentinel需要在salve中选择一个作为新的master,选择依据:
- 首先会判断slave节点与master节点断开时间长短,如果超过指定值(down-after-millisconds * 10)则会排除该slave节点。
- 然后判断slave节点的slave-priority值,越小优先级越高,如果是0则永不参与选举
- 如果slave-priority一样,则判断slave节点的offset值,越大说明数据越新,优先级越高
- 最后是判断slave几点的运行id大小,越小优先级越高
-
当选出一个新的master后,该如何实现切换:
- sentinel给备选的slave1节点发送slaveof no one命令,让该节点成为master。
- sentinel给所有其它slave发送slaveof 192.168.150.101 7002 命令,让这些slave成为新master的从节点,开始从新的master上同步数据。
- 最后,sentinel将故障节点标记为slave,当故障节点恢复后会自动成为新的master的slave节点。
-
-
通知
Sentinel充当Redis客户端的服务发现来源,当集群发生故障转移时,会将最新信息推送给Redis的客户端。
四、Redis分片集群
1、概述
主从和哨兵可以解决高并发读、高可用的问题。但是仍然有两个问题没有解决:
- 海量数据存储问题
- 高并发写的问题
使用分片集群可以解决上述问题。
2、分片集群介绍
(1)架构
(2)分片集群特征
- 集群中有多个master,每个master保存不同数据。
- 每个master,都可以有多个slave节点。
- master之间通过ping监测彼此健康状态
- 客户端请求可以访问集群任意节点,最终都会被转发到正确的节点。