redis-trib.rb 使用详解

redis-trib.rb是官方提供的Redis Cluster的管理工具,无需额外下载,默认位于源码包的src目录下,但因该工具是用ruby开发的,所以需要准备相关的依赖环境。

1. 准备redis-trib.rb的运行环境

wget https://cache.ruby-lang.org/pub/ruby/2.5/ruby-2.5.1.tar.gz

yum -y install zlib-devel
tar xvf ruby-2.5.1.tar.gz

cd ruby-2.5.1/
./configure -prefix=/usr/local/ruby
make
make install
cd /usr/local/ruby/
cp bin/ruby /usr/local/bin
cp bin/gem /usr/local/bin
安装rubygem redis依赖
wget http://rubygems.org/downloads/redis-3.3.0.gem
gem install -l redis-3.3.0.gem

2. 命令简介

# redis-trib.rb help
Usage: redis-trib <command> <options> <arguments ...>

  create          host1:port1 ... hostN:portN
                  --replicas <arg>
  check           host:port
  info            host:port
  fix             host:port
                  --timeout <arg>
  reshard         host:port
                  --from <arg>
                  --to <arg>
                  --slots <arg>
                  --yes
                  --timeout <arg>
                  --pipeline <arg>
  rebalance       host:port
                  --weight <arg>
                  --auto-weights
                  --use-empty-masters
                  --timeout <arg>
                  --simulate
                  --pipeline <arg>
                  --threshold <arg>
  add-node        new_host:new_port existing_host:existing_port
                  --slave
                  --master-id <arg>
  del-node        host:port node_id
  set-timeout     host:port milliseconds
  call            host:port command arg arg .. arg
  import          host:port
                  --from <arg>
                  --copy
                  --replace
  help            (show this help)

For check, fix, reshard, del-node, set-timeout you can specify the host and port of any working node in the cluster.
支持的操作如下:

- create:创建集群
- check:检查集群
- info:查看集群信息
- fix:修复集群
- reshard:在线迁移slot
- rebalance:平衡集群节点slot数量
- add-node:添加新节点
- del-node:删除节点
- set-timeout:设置节点的超时时间
- call:在集群所有节点上执行命令
- import:将外部redis数据导入集群

3. 常用命令详解

  • 创建集群
redis-trib.rb create --replicas 1 127.0.0.1:6379 127.0.0.1:6380 127.0.0.1:6381 127.0.0.1:6382 127.0.0.1:6383 127.0.0.1:6384

--replicas参数指定集群中每个主节点配备几个从节点,这里设置为1
关于主从节点的选择及槽的分配,其算法如下:

 - 把节点按照host分类,这样保证master节点能分配到更多的主机中。
 - 遍历host列表,从每个host列表中弹出一个节点,放入interleaved数组。直到所有的节点都弹出为止。
 - 将interleaved数组中前master个数量的节点保存到masters数组中。
 - 计算每个master节点负责的slot数量,16384除以master数量取整,这里记为N。
 - 遍历masters数组,每个master分配N个slot,最后一个master,分配剩下的slot。
 - 接下来为master分配slave,分配算法会尽量保证master和slave节点不在同一台主机上。
 - 对于分配完指定slave数量的节点,还有多余的节点,也会为这些节点寻找master。分配算法会遍历两次masters数组。
 - 第一次遍历master数组,在余下的节点列表找到replicas数量个slave。每个slave为第一个和master节点host不一样的节点,如果没有不一样的节点,则直接取出余下列表的第一个节点。
 - 第二次遍历是分配节点数除以replicas不为整数而多出的一部分节点。
  • 检查集群状态
redis-trib.rb check 127.0.0.1:6379

指定任意一个节点即可。
  • 查看集群信息
redis-trib.rb info 127.0.0.1:6383
  • 修复集群
redis-trib.rb fix 127.0.0.1:6379

目前fix命令能修复两种异常
- 节点中存在处于迁移中(importing或migrating状态)的slot。
- 节点中存在未分配的slot。

其它异常不能通过fix命令修复。
  • 迁移slot
redis-trib.rb reshard 127.0.0.1:6379

redis-trib.rb reshard host:port --from <arg> --to <arg> --slots <arg> --yes --timeout <arg> --pipeline <arg>

redis-trib.rb reshard --from a8b3d0f9b12d63dab3b7337d602245d96dd55844 --to f413fb7e6460308b17cdb71442798e1341b56cbc  --slots 10923 --yes --pipeline 20 127.0.0.1:6383

其中

host:port:必传参数,集群内任意节点地址,用来获取整个集群信息。
--from:源节点id,如果有多个源节点,使用逗号分隔,如果是all,则源节点为集群内出目标节点外的其它所有主节点。
--to:目标节点id,只能填写一个。
--slots:需要迁移槽的总数量。
--yes:迁移无需用户手动确认。
--timeout:控制每次migrate操作的超时时间,默认为60000毫秒。
--pipeline:控制每次批量迁移键的数量,默认为10。
  • 平衡集群节点slot数量
rebalance host:port --weight <arg>
                    --auto-weights
                    --use-empty-masters
                    --timeout <arg>
                    --simulate
                    --pipeline <arg>
                    --threshold <arg>
其中,

--weight <arg>:节点的权重,格式为node_id=weight,如果需要为多个节点分配权重的话,需要添加多个--weight <arg>参数,即--weight b31e3a2e=5 --weight 60b8e3a1=5,node_id可为节点名称的前缀,只要保证前缀位数能唯一区分该节点即可。没有传递–weight的节点的权重默认为1。
--auto-weights:自动将每个节点的权重默认为1。如果--weight和--auto-weights同时指定,则--auto-weights会覆盖前者。
--threshold <arg>:只有节点需要迁移的slot阈值超过threshold,才会执行rebalance操作。
--use-empty-masters:默认没有分配slot节点的master是不参与rebalance的。如果要让其参与rebalance,需添加该参数。
--timeout <arg>:设置migrate命令的超时时间。
--simulate:设置该参数,只会提示用户会迁移哪些slots,而不会执行真正的迁移操作。
--pipeline <arg>:定义cluster getkeysinslot命令一次取出的key数量,不传的话使用默认值为10。
  • 删除节点
redis-trib.rb del-node host:port node_id

在删除节点之前,其对应的槽必须为空,所以,在进行节点删除动作之前,必须使用redis-trib.rb reshard将其迁移出去。
需要注意的是,如果某个节点的槽被完全迁移出去,其对应的slave也会随着更新,指向迁移的目标节点。
  • 添加新节点
redis-trib add-node new_host:new_port existing_host:existing_port --slave --master-id <arg>

new_host:new_port:待添加的节点,必须确保其为空或不在其它集群中。
existing_host:existing_port:集群中任意一个节点的地址。


如果添加的是主节点,只需指定源节点和目标节点的地址即可。
redis-trib.rb add-node 127.0.0.1:6379 127.0.0.1:6384


如果添加的是从节点,其语法如下,
redis-trib.rb add-node --slave --master-id f413fb7e6460308b17cdb71442798e1341b56cbc 127.0.0.1:6379 127.0.0.1:6384
注意:
--slave和--master-id必须写在前面
添加从节点,可不设置--master-id,此时会随机选择主节点

线上建议使用redis-trib.rb添加新节点,因为其会对新节点的状态进行检查。如果手动使用cluster meet命令加入已经存在于其它集群的节点,会造成被加入节点的集群合并到现有集群的情况,从而造成数据丢失和错乱,后果非常严重,线上谨慎操作。
  • 设置节点的超时时间
redis-trib.rb set-timeout host:port milliseconds

其实就是批量修改集群各节点的cluster-node-timeout参数。
  • 在集群所有节点上执行命令
redis-trib.rb call host:port command arg arg .. arg
  • 外部redis数据导入集群
redis-trib.rb import --from 127.0.0.1:6378 127.0.0.1:6379

其内部处理流程如下:

- 通过load_cluster_info_from_node方法加载集群信息,check_cluster方法检查集群是否健康。
- 连接外部redis节点,如果外部节点开启了cluster_enabled,则提示错误([ERR] The source node should not be a cluster node.)
- 通过scan命令遍历外部节点,一次获取1000条数据。
- 遍历这些key,计算出key对应的slot。
- 执行migrate命令,源节点是外部节点,目的节点是集群slot对应的节点,如果设置了--copy参数,则传递copy参数,其会保留源节点的key,如果设置了--replace,则传递replace参数。如果目标节点中存在同名key,其值会被覆盖。两个参数可同时指定。
- 不停执行scan命令,直到遍历完所有key。
- 迁移完成。

参考:

redis-trib.rb命令详解

上一篇:小众且好用的 Python 爬虫库 RoboBrowser


下一篇:Linux内核红黑树使用