Redis集群伸缩
Redis集群搭建
参考下Redis安装部署
伸缩原理
Redis提供了灵活的节点扩容和收缩方案。在不影响集群对外服务的情况下,可以为集群添加节点进行扩容也可以对下线节点进行缩容。
我们在Redis Cluster 介绍与搭建这篇文章中搭建了一个三主三从的redis集群(如下图所示)。在搭建 Redis Cluster 通信流程剖析这篇博客中根据源码详细剖析了搭建集群的流程。
我们先根据Redis Cluster 介绍与搭建将如图的集群搭建起来,查看搭建的效果。
对应的主节点负责的槽位信息,如下图所示:
扩容集群
扩容集群是分布式存储最常见的需求,Redis集群扩容可以分为如下步骤:
- 准备新节点
- 加入集群
- 迁移槽和数据
准备新节点
我们需要两个节点,
172.18.0.8:6379,172.18.0.9:6379
,配置和之前集群节点配置基本相同。
1 | docker run -d -p 7007:6379 --name redis07 --network docker-network -v /tmp/etc/redis/redis.conf:/etc/redis/redis.conf -v /tmp/data/redis/node7:/data redis redis-server /etc/redis/redis.conf |
启动两个节点
启动后的新节点会作为孤儿节点运行,没有和其他节点与之通信。
加入集群
我们可以通过
redis-cli --cluster add-node
命令将172.18.0.8:6379
节点加入到集群中
1 | docker exec -ti redis01 /bin/bash # 登录redis集群 |
通过
redis-cli cluster nodes
查看节点信息
新加入的节点都是主节点,因为没有负责槽位,所以不能接受任何读写操作,对于新加入的节点,我们可以有两个操作:
- 为新节点迁移槽和数据实现扩容。
- 作为其他主节点的从节点负责故障转移
注意: 将新的redis实例添加到集群之前,一定要确保这个redis实例没有存储过数据,也不能持久化的数据文件,否则在添加的时候会报错的!
迁移槽和数据
下边我们看一下如何分配哈希槽。我们随便进入一个客户端,然后我们执行 redis-cli –cluster reshard, 就可以看到如下图所示提示,问我们需要移动多少个哈希槽,我们在这里移动3000个。
1 | redis-cli --cluster reshard 172.18.0.2:6379 --cluster-from 10ac7df576168e7f6ec86b20b249e02b1fc13a25,43284b05c5a359b28507b49c29a49637f1f6312b,02a79c59682b7c05f13d41e46e814fc792fa2c50 --cluster-to 07e3416aba80cfb8a8ef81d27228559e5a9d6415 --cluster-slots 1024 |
参数说明
–cluster-from:表示slot目前所在的节点的node ID,多个ID用逗号分隔
–cluster-to:表示需要新分配节点的node ID(貌似每次只能分配一个)
–cluster-slots:分配的slot数量
添加从节点
开始的时候,我们加入了两个新节点到集群中,节点172.18.0.8已经迁移了槽位和数据作为主节点,但是该节点还不具有故障转移的能力。
此时,还需要将172.18.0.9节点作为172.18.0.8节点的从节点,从而保证集群的高可用。使用redis-cli --cluster
命令为主节点添加从节点。
1 | redis-cli --cluster add-node 172.18.0.9:6379 172.18.0.8:6379 --cluster-slave --cluster-master-id 07e3416aba80cfb8a8ef81d27228559e5a9d6415 |
到此就完成了集群的扩容。集群关系如下图所示:
查看节点信息
收缩集群
收缩集群以为着缩减规模,需要从集群中安全下线部分节点。需要考虑两种情况:
确定下线的节点是否有负责槽,如果是,需要把槽迁移到其他节点,保证节点下线后整个槽节点映射的完整性。
当下线节点不在负责槽或着本身是从节点时,就可以通知集群内其他节点忘记下线节点,当所有节点忘记该节点后就可以正常关闭。
删除slave节点
1 | redis-cli --cluster del-node 172.18.0.2:6379 a13308a51afcce0c3a6040842feb68c823d15b59 |
节点迁移
1 | redis-cli --cluster reshard 172.18.0.2:6379 --cluster-from 07e3416aba80cfb8a8ef81d27228559e5a9d6415 --cluster-to 02a79c59682b7c05f13d41e46e814fc792fa2c50 --cluster-slots 1024 --cluster-yes |
reshard子命令前面已经介绍过了,这里需要注意的一点是,由于我们的集群一共有四个主节点,而每次reshard只能写一个目的节点,因此以上命令需要执行三次(–cluster-to对应不同的目的节点)。
–cluster-yes:不回显需要迁移的slot,直接迁移。
查看一下结果:
删除master节点
1 | redis-cli --cluster del-node 172.18.0.2:6379 07e3416aba80cfb8a8ef81d27228559e5a9d6415 |
至此就是redis cluster 简单的操作过程
注意:当被删除掉的节点重新起来之后不能自动加入集群,但其和主的复制还是正常的,也可以通过该节点看到集群信息(通过其他正常节点已经看不到该被del-node节点的信息)。
如果想要再次加入集群,则需要先在该节点执行cluster reset,再用add-node进行添加,进行增量同步复制
平衡哈希槽
为了保证redis哈希槽的在每一个节点的均衡,需要对哈希槽进行均衡
1 | redis-cli --cluster rebalance 172.18.0.2:6379 |