您的位置:首页 > 数据库 > Redis

Redis之十七 集群

2016-08-12 20:10 169 查看

1 简介

Redis集群是Redis提供的分布式数据库方案,集群通过分片来进行数据共享,并提供复制和故障转移功能。

2 CLUSTER MEET命令的实现

通过向节点A发送CLUSTERMEET命令,客户端可以让接收到命令的节点A将节点B添加到节点A所在的集群中,受到命令的节点A将与节点B进行握手,一次来确认彼此的存在,为将来的进一步通信打好基础:

1)       节点A会为节点B创建一个clusterNode结构,并将该结构添加到自己的clusterState.nodes字典里面。

2)       节点A将根据CLUSTERMEET命令给定的IP地址和端口后,向节点B发送一条MEET消息。

3)       如果一切顺利,节点B将接收到节点A发送的MEET消息,节点B会为节点A创建一个ClusterNode结构,并将该结构添加到自己的clusterState.nodes字典里面

4)       节点B将向节点A返回一条PONG消息

5)       节点A将接收到节点B返回的PONG消息,通过这条PONG消息节点A可知道节点B已经成功地接收到自己发送的MEET信息

6)       节点A将向节点B返回一条PING信息

7)       如果一切顺利,节点B将接收到节点A返回的PING信息,通过这条PING信息节点B可以知道节点A已经成公敌接收到了自己返回的PONG消息,握手成功

3 槽指派

Redis集群通过分片的方式保存数据库中的键值对:集群的整个数据库被分为16384槽,数据库中的每个键都属于这16384个槽中的一个,集群中的每个节点都可以处理0个或最多16384个槽。

当数据库中的16384个槽都有节点在处理时,集群处于上线状态,如果数据库中有任何一个槽没有得到处理,那么集群处于下线状态。

4 传播节点的槽指派信息

一个节点除了会将自己负责处理的槽记录在clusterNode结构的slots属性和munslots属性之外,它还会将自己的slots数组通过消息发送给集群中的其他节点,以此来告知其他节点自己目前处理的那些槽。因为集群中的每个节点都会讲自己的slots数组通过消息发送给集群中的其他节点,并且每个接收到slots数组的节点都会讲数组保存到相应节点的clusterNode结构里面,因此,集群中的每个节点都会知道数据库中的16384个槽分别被指派给集群中的哪些节点。

5 重新分片

Redis集群的重新分片操作可以将任意数量已经指派给某个节点的槽改为指派给另一个节点,并且相关槽所属的键值对也会从源节点被移动到目标节点。重新分片操作可以在线进行,在重新分片的过程中,集群不需要下线,并且源节点和目标节点都可以继续处理命令请求。

5.1 ASK错误

容易出现错误场景:

     在重新分片期间,源节点向目标节点迁移一个槽的过程中,可能会出现这样一种情况,属于被迁移槽的一部分键值对保存在源节点里面,而另一部分键值对保存在目标节点里面。

针对于上述场景的解决方法如下:

当客户端向源节点发送一个与数据库键有关的命令,并且命令要处理的数据库键恰好就属于正在被迁移的槽时:

1)       源节点会首先在自己的数据库里面查找指定的键,如果找到的话,就直接执行客户端发送的命令。

2)       如果源节点没能在自己数据库中找到指定的键,那么这个键就有可能已经迁移到目标节点,源节点向客户端返回一个ASK错误,指引客户端转向正在导入槽的目标节点,并在此发送之前想要执行的命令。

6 故障检测

集群中每个节点都会定期地向集群中的其他节点发送PING消息,以此来检测对象是否在线,如果接受PING消息的节点没有在规定的时间内,向发送PING消息的节点返回PONG消息,那么发送PING消息的节点就会将接收PING消息的节点标记为疑似下线。

7 故障转移

当一个从节点发现自己正在复制的主节点进入了已下线的状态,从节点将开始对下线主节点进行故障检测,以下是故障转移的执行步骤:

1)       复制下线主节点所有从节点里面,会有一个从节点被选中。

2)       被选中的从节点会执行性命令,成为新的主节点

3)       新的主节点会撤销所有对已下线主节点的槽指派,并将这些槽全部指派给自己

4)       新的主节点向集群广播一条PONG消息,这条PONG消息可以让集群中的其他节点立即知道这个节点已经由从节点变为主节点,并且这个主节点已经接管了原本由已经下线节点负责处理的槽

5)       新的主节点开始接受和自己负责处理的槽相关的命令请求,故障转移完成

 
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  redis 分布式