Redis 系列14--Redis Cluster

上一篇:https://blog.csdn.net/fengxianaa/article/details/124409445

1. 介绍

redis 主从和哨兵机制是为了解决 高可用、高并发读 的问题,但是不能解决:

  • 高并发写
  • 海量数据存储

使用 redis cluster 可以解决上面的问题,特征

  • 有多个 master ,每个都保存一部分的数据,所以只要 master 足够多,可以存无限数据
  • 每个 master 都有多个 slave 节点,master 宕机,slave顶上
  • 各个master之间通过ping,检测彼此的健康状态
  • 客户端随意访问任何一个 master,最后请求都会被路由到正确的master上

2. 搭建

我们搭建有 3 个 master 的集群,每个 master 只有一个 slave

7001、7002、7003 是 master

8001、8002、8003 是 salve

首先,清除之前的配置,再 /root/soft/redis 目录只保留下面的文件

创建目录

新建redis.conf,以 7001 为例:

# 端口号
port 7001
# 开启集群模式
cluster-enabled yes
# 集群内部的配置文件,不需要创建,由redis自己维护
cluster-config-file /root/soft/redis/7001/nodes.conf
# 节点心跳失败的超时时间,单位:毫秒,master宕机的话就会触发主备切换,slave宕机就不会提供服务
cluster-node-timeout 5000
# 持久化目录
dir /root/soft/redis/7001
# 绑定ip
bind 192.168.56.103 127.0.0.1
# 后台运行
daemonize yes
# 注册实例ip
replica-announce-ip 192.168.56.103
# 关闭保护模式
protected-mode no
# 数据库数量
databases 1
# 日志文件
logfile /root/soft/redis/7001/redis.log

把这个文件放到 /root/soft/redis 目录

将上面的文件复制到每个文件夹中:echo 7001 7002 7003 8001 8002 8003 | xargs -t -n 1 cp redis.conf

修改每个目录下的redis.conf,将其中的 7001 修改为跟目录一致

printf '%s\n' 7001 7002 7003 8001 8002 8003 | xargs -I{} -t sed -i 's/7001/{}/g' {}/redis.conf

启动服务:printf '%s\n' 7001 7002 7003 8001 8002 8003 | xargs -I{} -t redis-server {}/redis.conf

关闭所有进程:ps -ef | grep redis | awk '{print $2}' | xargs kill

或者:printf '%s\n' 7001 7002 7003 8001 8002 8003 | xargs -I{} -t redis-cli -p {} shutdown

3. 集群

执行命令:

redis-cli --cluster create --cluster-replicas 1 192.168.56.103:7001 192.168.56.103:7002 192.168.56.103:7003 192.168.56.103:8001 192.168.56.103:8002 192.168.56.103:8003

上面这个命令,只需要在第一次启动集群的时候使用,如果集群关闭后再次重启,只要执行:

printf '%s\n' 7001 7002 7003 8001 8002 8003 | xargs -I{} -t redis-server {}/redis.conf

命令解释:

  • redis-cli --cluster create :开始创建集群
  • --cluster-replicas 1:指定每个 master 的 salve 数量为 1,
    • 这时 节点总数 ➗ (replicas + 1)就得到master的数量,其他都是 slave 节点,随机分给某个master

结果:

可以看到 8001 挂到了7002 上,8002 挂到了7003 上,8003 挂到了7001 上,

在这里上图红框出输入 yes,回车:

集群创建成功

查看集群状态:redis-cli -p 7001 cluster nodes

4. hash slot

1. 介绍

在搭建集群的时候会发现有些 slots 信息,这就是 hash slot,也叫:散列插槽,一共有 16384 个

作用:在 redis cluster 模式下,会给每一个 master 分配一些 hash slot,在 set 的时候,

先对key计算,得出一个插槽值,最终确定把数据放到哪个 master上

在计算插槽值时,redis 会根据 key的有效部分计算:

  • key中没有"{}",那么整个key都是有效部分
  • key中有"{}",那么"{}"中的才是有效部分

例如:key 是 test,那么根据 test 计算,如果key是 {feng}test,就根据 feng 计算,

计算方式:利用CRC16算法得到一个 hash 值,然后对 16384 取余

2. 演示

使用 redis-cli 连接集群,注意:需要加上 -c

设置几个值

上图红框出,执行 set test hahaha 命令,对 test 计算,得出的 slot 是 6918,所以把它放到 7002 上,而且,命令行也切换到了 7002 节点

再次执行 get fengxiansheng 命令

对 fengxiansheng 计算,得出的 slot 是 1605,所以切换到 7001 节点,记住这个值,后面要用到

3. 将同一类数据放到一个 master 上

让这类数据的 key 都加上一个统一的前缀,比如:{fengxiansheng}

5. 集群伸缩

1. 添加 master

向集群中添加 master ,需要使用 add-node 命令

解释:

  • new_host:new_port: 需要加入集群的ip和端口
  • existing_host:existing_port: 已经在集群中存在的ip和端口
  • --cluster-slave: 作为一个从节点加入集群
  • --cluster-master-id <arg>:指定作为哪一个 master 的 salve
  • 注意:没有后两个参数,新加的节点默认是 master

再 /root/soft/redis 目录中,新建 7004,并设置redis.conf(此处省略)

启动 7004

但,7004 还没有加入集群,执行下面命令,加进来

可以看到,已经添加成功,再查看一下集群状态

但是,7004 目前没有分配插槽,下面分配一下

2. 分配 slot

使用 reshard 命令

提示要移动多少个 slot,我们移动 2000个

又问,移动到哪个节点?我们移动到 7004 节点,从上图的红框出可以找到 7004 的node ID

  • all: 从所有主节点(7001,7002,3003)中分别抽取相应的槽数指定到新节点中,总槽数为2000
  • done: 需要先指定的 node ID,就会从这个 node 迁移 2000个slot 到 7004

又问,是否执行这个计划,yes

最终移动 0-1999 到 7004

再查看一下集群状态

之前 fengxiansheng 这个key 计算的 slot 是 1605,存放在 7001上,现在应该在 7004 上

3. 删除节点

使用 del-node 命令

  • host:port: ip和端口
  • node_id: 通过redis-cli -p 7001 cluster nodes 可以查看 node ID
    • 为了防止误删,node_id 必须 ip:port保持一致,如果不一致会报错;

删除 7004,在删除一个 master 前,必须把它的slot移动到其他 master上,否则

转移 slot

然后删除

再查看集群信息,已经没有 7004

6. 故障转移

集群中,如果某个 master 宕机,那么它的 slave 会自动升级为 master

1. 演示

执行命令,监控集群的状态:watch redis-cli -p 7001 cluster nodes

结果:

新建一个窗口,关闭 7002 :redis-cli -p 7002 shutdown,然后查看集群状态:

在执行命令后,可以看到 7002 disconnected

等待一下就发现,7002 fail,它的 slave ,8001 成为 master

重新启动 7002 ,发现成为 slave

2. 手动宕机

可以利用 cluster failover 命令,手动让某个 master 宕机,执行命令的 slave 节点升级为 master

好处:可以实现数据的无感知迁移

流程:

failover 命令还有几个参数

  • 缺省:就是上面的流程
  • force :忽略数据同步,直接故障转移,需要大多数 master 节点有效,以便对这次切换进行验证
    • 使用场景是 master 节点 down 的情况下的人工故障转移
  • takeover:直接执行第5步,忽略主备同步,忽略集群其他master的投票
    • 使用场景:集群中主节点和从节点在不同的数据中心,当所有主节点 down 掉或被网络分区隔离

在 7002 上执行 cluster failover 命令,恢复 master 地位

这时集群状态

7. RedisTemplate

RedisTemplate 底层基于 lettuce 实现了对 redis cluster 的支持,实现步骤跟哨兵一致

只需要删除哨兵的配置,配置下面地址

# 集群地址
spring.redis.cluster.nodes[0]=192.168.56.103:7001
spring.redis.cluster.nodes[1]=192.168.56.103:7002
spring.redis.cluster.nodes[2]=192.168.56.103:7003
spring.redis.cluster.nodes[3]=192.168.56.103:8001
spring.redis.cluster.nodes[4]=192.168.56.103:8002
spring.redis.cluster.nodes[5]=192.168.56.103:8003

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值