Redis 7.x 系列【25】集群部署

有道无术,术尚可求,有术无道,止于术。

本系列Redis 版本 7.2.5

源码地址:https://gitee.com/pearl-organization/study-redis-demo

文章目录

    • 1. 概述
    • 2. 配置文件
      • 2.1 cluster-enabled
      • 2.2 cluster-config-file
      • 2.3 cluster-node-timeout
      • 2.4 cluster-port
      • 2.5 cluster-replica-validity-factor
      • 2.6 cluster-migration-barrier
      • 2.7 cluster-allow-replica-migration
      • 2.8 cluster-replica-no-failover
      • 2.9 cluster-allow-reads-when-down
      • 2.11 cluster-allow-pubsubshard-when-down
      • 2.12 cluster-link-sendbuf-limit
      • 2.13 cluster-announce-hostname
      • 2.14 cluster-announce-human-nodenam
      • 2.15 cluster-preferred-endpoint-type
      • 2.16 cluster-announce-*
    • 3. 搭建演示
      • 3.1 安装
      • 3.2 修改配置
      • 3.3 启动
      • 3.4 创建集群
      • 2.5 集群节点信息
      • 3.6 测试
    • 4. 注意事项
      • 4.1 使用限制
      • 4.2 多键操作
      • 4.3 避免合并操作
      • 4.4 写入丢失
      • 4.5 在从节点执行读操作
      • 4.6 分片发布订阅

1. 概述

官方文档

Redis Sentinel 模式是 Redis 高可用解决方案之一,由一个或多个哨兵节点,负责监控和管理多个 Redis 主从节点,当主节点出现故障时,能够自动将其中一个从节点提升为主节点,实现故障转移和自动切换,从而保证 Redis 服务的高可用性。

Redis Sentinel 基于主从复制,每个节点存储的是全量数据,因此当数据量较大时,单个复制数据集可能难以承担,从而造成系统的性能瓶颈,所以该模式只适用于数据量较小,但是对高可用性有一定要求的场景。

Redis 3.0 提供了分布式的高可用解决方案 ( Redis Cluster ),通过数据分片的方式,将数据分散存储在多个服务器节点,以支持更大的数据量和更高的并发请求。同时,集群能够自动进行数据的重新分配和故障恢复,保证整个集群的可用性和稳定性。

2. 配置文件

集群模式下的所有的配置都在 redis.conf 配置文件中:

################################ REDIS CLUSTER  ################################ Normal Redis instances can't be part of a Redis Cluster; only nodes that are
# started as cluster nodes can. In order to start a Redis instance as a
# cluster node enable the cluster support uncommenting the following:
#
# cluster-enabled yes# Every cluster node has a cluster configuration file. This file is not
# intended to be edited by hand. It is created and updated by Redis nodes.
# Every Redis Cluster node requires a different cluster configuration file.
# Make sure that instances running in the same system do not have
# overlapping cluster configuration file names.
#
# cluster-config-file nodes-6379.conf# Cluster node timeout is the amount of milliseconds a node must be unreachable
# for it to be considered in failure state.
# Most other internal time limits are a multiple of the node timeout.
#
# cluster-node-timeout 15000# The cluster port is the port that the cluster bus will listen for inbound connections on. When set 
# to the default value, 0, it will be bound to the command port + 10000. Setting this value requires 
# you to specify the cluster bus port when executing cluster meet.
# cluster-port 0# A replica of a failing master will avoid to start a failover if its data
# looks too old.
#
# There is no simple way for a replica to actually have an exact measure of
# its "data age", so the following two checks are performed:
#
# 1) If there are multiple replicas able to failover, they exchange messages
#    in order to try to give an advantage to the replica with the best
#    replication offset (more data from the master processed).
#    Replicas will try to get their rank by offset, and apply to the start
#    of the failover a delay proportional to their rank.
#
# 2) Every single replica computes the time of the last interaction with
#    its master. This can be the last ping or command received (if the master
#    is still in the "connected" state), or the time that elapsed since the
#    disconnection with the master (if the replication link is currently down).
#    If the last interaction is too old, the replica will not try to failover
#    at all.
#
# The point "2" can be tuned by user. Specifically a replica will not perform
# the failover if, since the last interaction with the master, the time
# elapsed is greater than:
#
#   (node-timeout * cluster-replica-validity-factor) + repl-ping-replica-period
#
# So for example if node-timeout is 30 seconds, and the cluster-replica-validity-factor
# is 10, and assuming a default repl-ping-replica-period of 10 seconds, the
# replica will not try to failover if it was not able to talk with the master
# for longer than 310 seconds.
#
# A large cluster-replica-validity-factor may allow replicas with too old data to failover
# a master, while a too small value may prevent the cluster from being able to
# elect a replica at all.
#
# For maximum availability, it is possible to set the cluster-replica-validity-factor
# to a value of 0, which means, that replicas will always try to failover the
# master regardless of the last time they interacted with the master.
# (However they'll always try to apply a delay proportional to their
# offset rank).
#
# Zero is the only value able to guarantee that when all the partitions heal
# the cluster will always be able to continue.
#
# cluster-replica-validity-factor 10# Cluster replicas are able to migrate to orphaned masters, that are masters
# that are left without working replicas. This improves the cluster ability
# to resist to failures as otherwise an orphaned master can't be failed over
# in case of failure if it has no working replicas.
#
# Replicas migrate to orphaned masters only if there are still at least a
# given number of other working replicas for their old master. This number
# is the "migration barrier". A migration barrier of 1 means that a replica
# will migrate only if there is at least 1 other working replica for its master
# and so forth. It usually reflects the number of replicas you want for every
# master in your cluster.
#
# Default is 1 (replicas migrate only if their masters remain with at least
# one replica). To disable migration just set it to a very large value or
# set cluster-allow-replica-migration to 'no'.
# A value of 0 can be set but is useful only for debugging and dangerous
# in production.
#
# cluster-migration-barrier 1# Turning off this option allows to use less automatic cluster configuration.
# It both disables migration to orphaned masters and migration from masters
# that became empty.
#
# Default is 'yes' (allow automatic migrations).
#
# cluster-allow-replica-migration yes# By default Redis Cluster nodes stop accepting queries if they detect there
# is at least a hash slot uncovered (no available node is serving it).
# This way if the cluster is partially down (for example a range of hash slots
# are no longer covered) all the cluster becomes, eventually, unavailable.
# It automatically returns available as soon as all the slots are covered again.
#
# However sometimes you want the subset of the cluster which is working,
# to continue to accept queries for the part of the key space that is still
# covered. In order to do so, just set the cluster-require-full-coverage
# option to no.
#
# cluster-require-full-coverage yes# This option, when set to yes, prevents replicas from trying to failover its
# master during master failures. However the replica can still perform a
# manual failover, if forced to do so.
#
# This is useful in different scenarios, especially in the case of multiple
# data center operations, where we want one side to never be promoted if not
# in the case of a total DC failure.
#
# cluster-replica-no-failover no# This option, when set to yes, allows nodes to serve read traffic while the
# cluster is in a down state, as long as it believes it owns the slots.
#
# This is useful for two cases.  The first case is for when an application
# doesn't require consistency of data during node failures or network partitions.
# One example of this is a cache, where as long as the node has the data it
# should be able to serve it.
#
# The second use case is for configurations that don't meet the recommended
# three shards but want to enable cluster mode and scale later. A
# master outage in a 1 or 2 shard configuration causes a read/write outage to the
# entire cluster without this option set, with it set there is only a write outage.
# Without a quorum of masters, slot ownership will not change automatically.
#
# cluster-allow-reads-when-down no# This option, when set to yes, allows nodes to serve pubsub shard traffic while
# the cluster is in a down state, as long as it believes it owns the slots.
#
# This is useful if the application would like to use the pubsub feature even when
# the cluster global stable state is not OK. If the application wants to make sure only
# one shard is serving a given channel, this feature should be kept as yes.
#
# cluster-allow-pubsubshard-when-down yes# Cluster link send buffer limit is the limit on the memory usage of an individual
# cluster bus link's send buffer in bytes. Cluster links would be freed if they exceed
# this limit. This is to primarily prevent send buffers from growing unbounded on links
# toward slow peers (E.g. PubSub messages being piled up).
# This limit is disabled by default. Enable this limit when 'mem_cluster_links' INFO field
# and/or 'send-buffer-allocated' entries in the 'CLUSTER LINKS` command output continuously increase.
# Minimum limit of 1gb is recommended so that cluster link buffer can fit in at least a single
# PubSub message by default. (client-query-buffer-limit default value is 1gb)
#
# cluster-link-sendbuf-limit 0# Clusters can configure their announced hostname using this config. This is a common use case for 
# applications that need to use TLS Server Name Indication (SNI) or dealing with DNS based
# routing. By default this value is only shown as additional metadata in the CLUSTER SLOTS
# command, but can be changed using 'cluster-preferred-endpoint-type' config. This value is 
# communicated along the clusterbus to all nodes, setting it to an empty string will remove 
# the hostname and also propagate the removal.
#
# cluster-announce-hostname ""# Clusters can configure an optional nodename to be used in addition to the node ID for
# debugging and admin information. This name is broadcasted between nodes, so will be used
# in addition to the node ID when reporting cross node events such as node failures.
# cluster-announce-human-nodename ""# Clusters can advertise how clients should connect to them using either their IP address,
# a user defined hostname, or by declaring they have no endpoint. Which endpoint is
# shown as the preferred endpoint is set by using the cluster-preferred-endpoint-type
# config with values 'ip', 'hostname', or 'unknown-endpoint'. This value controls how
# the endpoint returned for MOVED/ASKING requests as well as the first field of CLUSTER SLOTS. 
# If the preferred endpoint type is set to hostname, but no announced hostname is set, a '?' 
# will be returned instead.
#
# When a cluster advertises itself as having an unknown endpoint, it's indicating that
# the server doesn't know how clients can reach the cluster. This can happen in certain 
# networking situations where there are multiple possible routes to the node, and the 
# server doesn't know which one the client took. In this case, the server is expecting
# the client to reach out on the same endpoint it used for making the last request, but use
# the port provided in the response.
#
# cluster-preferred-endpoint-type ip# In order to setup your cluster make sure to read the documentation
# available at https://redis.io web site.########################## CLUSTER DOCKER/NAT support  ######################### In certain deployments, Redis Cluster nodes address discovery fails, because
# addresses are NAT-ted or because ports are forwarded (the typical case is
# Docker and other containers).
#
# In order to make Redis Cluster working in such environments, a static
# configuration where each node knows its public address is needed. The
# following four options are used for this scope, and are:
#
# * cluster-announce-ip
# * cluster-announce-port
# * cluster-announce-tls-port
# * cluster-announce-bus-port
#
# Each instructs the node about its address, client ports (for connections
# without and with TLS) and cluster message bus port. The information is then
# published in the header of the bus packets so that other nodes will be able to
# correctly map the address of the node publishing the information.
#
# If tls-cluster is set to yes and cluster-announce-tls-port is omitted or set
# to zero, then cluster-announce-port refers to the TLS port. Note also that
# cluster-announce-tls-port has no effect if tls-cluster is set to no.
#
# If the above options are not used, the normal Redis Cluster auto-detection
# will be used instead.
#
# Note that when remapped, the bus port may not be at the fixed offset of
# clients port + 10000, so you can specify any port and bus-port depending
# on how they get remapped. If the bus-port is not set, a fixed offset of
# 10000 will be used as usual.
#
# Example:
#
# cluster-announce-ip 10.1.1.5
# cluster-announce-tls-port 6379
# cluster-announce-port 0
# cluster-announce-bus-port 6380

2.1 cluster-enabled

是否开启集群模式。

# cluster-enabled yes

2.2 cluster-config-file

指定节点使用的集群配置文件名。

# cluster-config-file nodes-6379.conf

在集群中,每个节点都有一个集群配置文件,由 Redis 节点自动创建和更新的。包含了集群的当前状态信息,如节点的ID、角色(主节点或从节点)、与其他节点的连接信息等。

如果在同一个系统上运行多个 Redis 实例作为集群节点,需要确保每个实例的 cluster-config-file 配置项都指向一个不同的文件名。确保每个节点都能正确地存储和更新自己的集群状态信息,而不会与其他节点的信息混淆。

2.3 cluster-node-timeout

集群节点超时时间(以毫秒为单位),超过这个时间长度后,该节点将被视为处于失败状态。

# cluster-node-timeout 15000

默认为 15 秒,集群中的每个节点,在尝试与另一个节点通信时,但在 15 秒内没有收到任何响应,另一个节点会被视为已经失败。

2.4 cluster-port

指定集群总线端口,用于集群之间进行通信,当设置为默认值 0 时,会在客户端连接端口上 +10000

# cluster-port 0

2.5 cluster-replica-validity-factor

配置判断从节点是否有效的计算因子,当主节点发生故障时,如果从节点的数据过于陈旧,则不会进行故障转移。

# cluster-replica-validity-factor 10

判断从节点数据是否陈旧很难有一个准确的度量标准,因此会执行以下两项检查:

  1. 如果有多个能够执行故障转移的从节点,它们会交换消息,根据复制偏移量进行排名(偏移量越高,则复制的数据越完整)
  2. 每个从节点都会计算其与主节点最后一次交互的时间,可以是接收到的最后一个 ping 或命令的时间,或者是自与主节点断开连接后的持续时间。如果从节点与主节点的最后一次交互时间过长,它将不会尝试进行故障转移。

对于第二项检查,可以进行配置,如果从节点与主节点的最后一次交互以来经过的时间大于以下值时,它将不会执行故障转移:

(节点超时时间 * 集群从节点有效性因子) + 复制心跳间隔

例如,如果节点超时时间为 30 秒,集群从节点有效性因子为 10 ,并且假设默认的复制心跳间隔为 10 秒,则从节点如果与主节点断开连接超过 310 秒,将不会尝试进行故障转移。

为了实现最大的可用性,可以将集群从节点有效性因子设置为 0 ,这意味着从节点将始终尝试对主节点进行故障转移,无论它们最后一次与主节点交互的时间是什么时候(还是会根据其偏移量排名优先)。

2.6 cluster-migration-barrier

定义了当一个主节点需要为其分配从节点时,该主节点至少需要保留的从节点数量。这个值是一个迁移的临界值,用于防止主节点在分配从节点后变为“裸奔”状态(即没有任何从节点)。

# cluster-migration-barrier 1

默认值为 1 ,表示只有当主节点至少保留一个从节点时,从节点才会迁移。要禁用迁移,只需将其设置为一个非常大的值,或将 cluster-allow-replica-migration 设置为 no

可以将值设置为 0 ,仅适用于调试,在生产环境中是危险的。

2.7 cluster-allow-replica-migration

用于控制是否允许从节点的迁移。

cluster-allow-replica-migration yes

默认值为 yes ,允许集群在特定条件下自动迁移从节点到不同的主节点下。

2.8 cluster-replica-no-failover

配置当主节点宕机时,是否阻止其对应的从节点自动进行故障转移。

cluster-replica-no-failover no

当此选项设置为 yes 时,会阻止从节点在主节点故障时尝试对其进行故障转移,可以进行手动故障转移。

2.9 cluster-allow-reads-when-down

配置集群中的节点因为某些原因(如节点故障、网络分区等)被标记为不可用,或者集群无法连接到足够的法定主节点以保证数据的一致性,那么集群是否停止接受任何读取请求。

cluster-allow-reads-when-down no

当此选项设置为 yes 时,允许节点在集群处于关闭状态时处理读取流量。

2.11 cluster-allow-pubsubshard-when-down

用于控制当集群因主节点数量达不到最小值,或者哈希槽没有完全分配而被标记为失效时,是否允许发布/订阅功能继续运行。

cluster-allow-pubsubshard-when-down yes

当设置为 no 时,如果集群被标记为失效(例如,由于主节点数量不足或哈希槽分配不完全),发布/订阅功能将停止工作,订阅了相关频道的客户端将无法接收到任何消息。

2.12 cluster-link-sendbuf-limit

用于限制集群节点间通信时发送缓冲区(send buffer)的大小。当发送缓冲区中的数据量超过这个限制时,Redis 会采取一些措施来避免内存过度使用,比如断开连接或释放部分数据。

cluster-link-sendbuf-limit 0

这主要是为了防止向慢速的链路上(例如 PubSub 消息堆积)的发送缓冲区无限制地增长。建议的最小限制为 1GB,以便集群链路缓冲区能够默认容纳至少一条 PubSub 消息。

2.13 cluster-announce-hostname

指定集群中每个节点在集群元数据中公布的主机名或IP地址。这个参数对于确保集群节点之间能够正确地相互发现和通信至关重要。

cluster-announce-hostname ""

没有默认值,将尝试自动检测并使用它的 IP 地址(取决于它是如何绑定到网络接口的)。然而,在某些情况下(如使用 NAT 或容器化部署时),自动检测可能无法返回集群中其他节点可以访问的正确地址。

2.14 cluster-announce-human-nodenam

配置一个可选的节点名称,该名称除了节点 ID 外,还用于调试和管理信息。这个名称会在节点之间广播,因此在报告跨节点事件(如节点故障)时,除了节点 ID 外,还会使用此名称。

cluster-announce-human-nodename ""

2.15 cluster-preferred-endpoint-type

用于设置告诉客户端使用何种方式连接集群。例如,在 MOVED/ASKING 请求、 CLUSTER SLOTS 命令时会返回。

cluster-preferred-endpoint-type ip

可配置项说明:

  • ip:使用 IP 地址作为集群节点的连接端点。
  • hostname:使用主机名作为集群节点的连接端点。
  • unknown-endpoint:集群不知道客户端如何连接到集群。

2.16 cluster-announce-*

cluster-announce 开头的配置,用于支持在DockerNAT 环境下进行相关的网络配置。

在某些部署中,集群节点的地址发现(自动获取IP)会失败,因为地址被 NAT 转换或端口被转发(典型情况是 Docker 和其他容器)。

为了使集群在这样的环境中工作,需要一个静态配置,其中每个节点都知道其公共地址。以下四个选项用于此目的:

  • cluster-announce-ipIP
  • cluster-announce-port:客户端端口,默认 6379
  • cluster-announce-tls-portTLS 客户端端口
  • cluster-announce-bus-port:集群消息总线端口,默认客户端端口 +10000

这些配置信息将发布在总线数据包的头部,以便其他节点能够正确映射发布信息的节点的地址。

3. 搭建演示

根据 Redis Cluster 设计的槽位(slots)数量,决定了其最多可以配置 16384 个主节点,但是节点越多,管理运维成本越高,也会增加节点之间的网络通信开销,影响集群的整体性能。所以官方建议主节点最大数量为 1000 个,就算是十亿的用户会话数据,分摊到每个节点也就 100 W ,对于 Redis 来说,洒洒水啦!
在这里插入图片描述

集群中的节点也分为主节点和从节点,只有主节点负责读写请求和集群信息的维护,从节点只进行主节点数据和状态信息的备份。这里使用三主三从的部署架构,包含三个主节点,每个主又包含一个从节点:

在这里插入图片描述

所有节点网络访问地址如下 :

  • 主节点一:192.168.56.101:6379
  • 主节点二:192.168.56.102:6379
  • 主节点三:192.168.56.103:6379
  • 从节点一:192.168.56.104:6379
  • 从节点二:192.168.56.105:6379
  • 从节点三:192.168.56.106:6379

3.1 安装

Redis 7.x 系列【2】单机部署
Redis 7.x 系列【21】主从复制

安装方法和普通的 Redis 一样,参考上面的文档,在六台服务器上安装即可。

3.2 修改配置

Redis Cluster 所有的配置都在 redis.conf 配置文件中,复制到配置目录:

[root@localhost /]# mkdir /etc/redis
[root@localhost /]# cp ~/redis-7.2.5/redis.conf /etc/redis/
[root@localhost bin]# vim redis.conf

修改基础配置:

# 允许其他地址访问
#bind 127.0.0.1 -::1
# 数据库数量为 1
databases 1
# 关闭保护模式
protected-mode no
# 允许后台启动
daemonize yes
# 当前节点的认证密码
requirepass cluster123456
# 主节点的认证密码
masterauth cluster123456

修改集群相关的配置:

# 启用 Redis 集群模式
cluster-enabled yes
# 这是指定 Redis 集群配置文件的路径和文件名
cluster-config-file nodes-6379.conf
# 集群节点之间通信的超时时间,单位为毫秒
cluster-node-timeout 15000

如果是在同一台服务器安装多个节点,还需要修改:

# 启动端口
port 6380
# PID 文件
pidfile ./redis_6380.pid
# 日志文件
logfile "./cluster_6380.log"
# RDB 文件名
dbfilename cluster_6380_dump.rdb
# 这是指定 Redis 集群配置文件的路径和文件名
cluster-config-file nodes-6380.conf

3.3 启动

这里直接使用命令启动,依次启动所有节点:

[root@localhost bin]# cd /usr/local/bin
[root@localhost bin]# ./redis-server /etc/redis/redis.conf
[root@localhost bin]# ps -ef | grep redis 
root      2586     1  0 21:28 ?        00:00:00 ./redis-server *:6379 [cluster]
root      2625  2380  0 21:31 pts/2    00:00:00 grep --color=auto redis

3.4 创建集群

节点启动以后是相互独立的,并不知道其他节点存在,需要创建集群。

集群的管理命令是 redis-cli --cluster ,可以输入 help 查看帮助:

在这里插入图片描述
创建集群的命令是 create

  create  host1:port1 ... hostN:portN--cluster-replicas <arg>

create 命令参数说明:

  • host1:port1:将哪些主机和端口加入到集群中
  • --cluster-replicas <arg>:是指定每个主节点应该有多少个副本节点,当前安装了六个数据节点,每个主节点有一个从节点,所有需要设置 arg1

执行创建集群:

[root@localhost bin]# redis-cli  -a cluster123456 --cluster create 192.168.56.101:6379 192.168.56.101:6379 192.168.56.101:6379 192.168.56.101:6379 192.168.56.101:6379 192.168.56.101:6379 --cluster-replicas 1 

命令执行后,会打印主节点分配的哈希槽,以及建立主从关系:

Master[0] -> Slots 0 - 5460
Master[1] -> Slots 5461 - 10922
Master[2] -> Slots 10923 - 16383
Adding replica 192.168.56.101:6379 to 192.168.56.102:6379
Adding replica 192.168.56.103:6379 to 192.168.56.105:6379 
Adding replica 192.168.56.104:6379 to 192.168.56.106:6379 

如果没有问题,需要输入 yes ,同意使用上面的方式创建集群:

Can I set the above configuration? (type 'yes' to accept): 

创建成功提示:

[OK] All nodes agree about slots configuration.
>>> Check for open slots...
>>> Check slots coverage...
[OK] All 16384 slots covered.

2.5 集群节点信息

集群创建完成后,第一次启动时,会生成一个 160 位随机数十六进制的节点 ID ,作为在集群中的唯一名称。会一直保存在节点配置文件中,除非删改配置文件,或者使用 CLUSTER RESET 进行重置。

节点 ID 是全局唯一的,用于在整个集群中唯一标识每个节点,某个节点可以在不更改节点 ID 的情况下更改其 IP 地址,此外集群还能够通过在集群总线相关协议,检测到 IP和端口的变化并重新配置。

此外,节点还会维护其他与之关联的信息:

  • 其他节点:节点IDIP地址和端口号、标识(主从角色)、最后一次 PING 时间、最后一次接收 PONG 时间、配置纪元、链路状态、最后一组服务的哈希槽等
  • 本地特有:最后一次被 PING 的时间

在任意节点上,使用 cluster nodes 命令:

[root@localhost redis]# redis-cli -a cluster123456 cluster nodes
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
ce27fa445e987f75bddeeb68fc6fe440678ad1bb 192.168.56.101:6379@16382 slave 724c7b874dc0c37a462cd5ab59325203344f8008 0 1720707068964 1 connected
b5bde236f14f21f530a7095aaef3a98109009324 192.168.56.102:6379@16383 slave e909dc338f4c2fc7687cf4426d3b95956a90a8a8 0 1720707070969 2 connected
724c7b874dc0c37a462cd5ab59325203344f8008 192.168.56.103:6379@16379 myself,master - 0 1720707068000 1 connected 0-5460
e909dc338f4c2fc7687cf4426d3b95956a90a8a8 192.168.56.104:6379@16380 master - 0 1720707069966 2 connected 5461-10922
9f9c30c3f73106e256fdec27264fc8129e1287fd 192.168.56.105:6379@16381 master - 0 1720707068000 3 connected 10923-16383
0f1d8d6459ac4252636cb4b8e1764de9e277411c 192.168.56.106:6379@16390 slave 9f9c30c3f73106e256fdec27264fc8129e1287fd 0 1720707070000 3 connected

还可以使用 INFO REPLICATION 查看主从复制信息:

主节点(192.168.56.101:6379)>INFO REPLICATION
Replication
role:master
connected_slaves:1
master_failover_state:no-failover
master_replid:d81b2d93e7dc67a80b81673117fdc17adc9a0fb1
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:0
second_repl_offset:-1
repl_backlog_active:0
repl_backlog_size:1048576
repl_backlog_first_byte_offset:0
repl_backlog_histlen:0

使用 CLUSTER INFO 查看集群信息:

主节点(192.168.56.101:6379)>CLUSTER INFO
# 集群状态
cluster_state:ok
# 哈希槽
cluster_slots_assigned:16384
cluster_slots_ok:16384
cluster_slots_pfail:0
cluster_slots_fail:0
# 节点数
cluster_known_nodes:6
# 主节点数
cluster_size:3
cluster_current_epoch:6
cluster_my_epoch:1
cluster_stats_messages_ping_sent:1271
cluster_stats_messages_pong_sent:1533
cluster_stats_messages_sent:2804
cluster_stats_messages_ping_received:1528
cluster_stats_messages_pong_received:1271
cluster_stats_messages_meet_received:5
cluster_stats_messages_received:2804
total_cluster_links_buffer_limit_exceeded:0

3.6 测试

使用管理工具连接两个节点,在一个节点上执行命令后,在另外一个节点的连接中也可以查看到:

在这里插入图片描述
可以使用 cluster keyslot 命令查看 key 分配的哈希槽:

主节点(192.168.56.101:6379)>cluster keyslot aa
"1180"

4. 注意事项

4.1 使用限制

集群不支持多个数据库,仅支持数据库 0 ,不允许使用 SELECT 命令。

对于单个键的操作命令,集群模式和非集群版本是没有区别的。

4.2 多键操作

集群中的每个键都通过哈希函数映射到一个特定的哈希槽上,这些槽分布在不同的节点上。对于同时操作多个键的命令(如集合的并集、交集等),这些键可能分布在不同的节点上。

Redis 集群实现了一个称为哈希标签(hash tags)的概念,可用于强制某些键存储在同一个哈希槽中。然而,在手动重新分片期间,多键操作可能会有一段时间不可用。

例如,下面两个 key 的槽和节点都不同,执行 mget 命令将会报错:

主节点(192.168.56.101:6381)>cluster keyslot aa
"1180"
主节点(192.168.56.101:6381)>cluster keyslot bb
"8620"
主节点(192.168.56.101:6381)>mget aa bb
"CROSSSLOT Keys in request don't hash to the same slot"

这时,可以使用 {hashtag} 指定一个哈希标签,示例:

主节点(192.168.56.101:6380)>mset {tag}.aa 123 {tag}.bb 456
"OK"

可以看到哈希槽是一样的,并且可以使用 mget 命令:

主节点(192.168.56.101:6380)>cluster keyslot {tag}.aa 
"8338"
主节点(192.168.56.101:6380)>cluster keyslot {tag}.bb
"8338"
主节点(192.168.56.101:6380)>mget {tag}.aa {tag}.bb1)  "123"2)  "456"

4.3 避免合并操作

Redis 中的值通常非常大,例如常见的包含数百万元素的列表或有序集合。此外,数据类型在语义上也相对复杂。传输和合并这类值可能会成为主要的瓶颈,或者可能需要应用端逻辑的复杂参与、额外的内存来存储元数据等。

4.4 写入丢失

Redis Cluster 中的节点之间使用异步复制来同步数据(最终一致性),当主节点接收到写入请求时,它会先将数据写入本地,然后异步将数据复制到从节点。异步复制机制提高了系统的性能,因为它减少了主节点等待从节点确认的时间。然而,它也带来了数据丢失的风险。

如果主节点在写入操作完成但尚未复制到从节点时发生故障,那么这些写入操作可能会丢失。当发生故障转移时,会有一从节点被提升为主节点,这个新选出的主节点会拥有最新的数据集(不一定是最完整的,有可能丢失部分数据),集群中的所有节点都会以这个新主节点的数据集为准。

4.5 在从节点执行读操作

在从节点上执行读取命令时,通常情况下,会将客户端重定向到涉及给定命令中的哈希槽的主节点,但是客户端可以使用从节点来执行读操作。READONLY 命令告诉 Redis Cluster 的副本节点,客户端可以读取可能不是最新的数据,并且不会执行写入查询。只读状态可以通过 READWRITE 命令来清除。

可能发生的情况包括:

  • 客户端发送了一个命令,该数据的哈希槽不在当前从节点关联的主节点上。
  • 集群被重新配置(例如重新分片),副本不再能够为特定哈希槽的命令提供服务。

当发生这种情况时,客户端应更新本地的哈希槽映射表。

4.6 分片发布订阅

Redis Cluster 大规模的集群模式下,pubsub 中的消息发布会导致广播风暴。即当一个节点发布消息到某个频道时,该消息会被广播到集群中的所有节点,即使只有少数节点订阅了该频道。这种广播方式极大地浪费了网络、CPU 等资源。

Redis 7.0 引入了 sharded-pubsub 功能,使用分片算法,将通道映射到具体的节点,分片消息只能发送到拥有当前分片通道的节点。客户端只能订阅特定分片通道的节点,从而避免了资源的浪费。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/382213.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

HAL库源码移植与使用之RTC时钟

实时时钟(Real Time Clock&#xff0c;RTC)&#xff0c;本质是一个计数器&#xff0c;计数频率常为秒&#xff0c;专门用来记录时间。 普通定时器无法掉电运行&#xff01;但RTC可由VBAT备用电源供电&#xff0c;断电不断时 这里讲F1系列的RTC 可以产生三个中断信号&#xff…

TYPE-C接口PD取电快充协议芯片ECP5701:支持PD 2.0和PD 3.0(5V,9V,12V,15V,20V)

随着智能设备的普及&#xff0c;快充技术成为了越来越多用户的刚需。而TYPE-C接口作为新一代的USB接口&#xff0c;具有正反插、传输速度快、充电体验好等优点&#xff0c;已经成为了快充技术的主要接口形式。而TYPE-C接口的PD&#xff08;Power Delivery&#xff09;取电快充协…

poi库简单使用(java如何实现动态替换模板Word内容)

目录 Blue留言&#xff1a; Blue的推荐&#xff1a; 什么是poi库&#xff1f; 实现动态替换 第一步&#xff1a;依赖 第二步&#xff1a;实现word模板中替换文字 模板word&#xff1a; 通过以下代码&#xff1a;&#xff08;自己建一个类&#xff0c;随意取名&#xf…

[排序]hoare快速排序

今天我们继续来讲排序部分&#xff0c;顾名思义&#xff0c;快速排序是一种特别高效的排序方法&#xff0c;在C语言中qsort函数&#xff0c;底层便是用快排所实现的&#xff0c;快排适用于各个项目中&#xff0c;特别的实用&#xff0c;下面我们就由浅入深的全面刨析快速排序。…

JVM监控及诊断工具-命令行篇--jcmd命令介绍

JVM监控及诊断工具-命令行篇5-jcmd&#xff1a;多功能命令行 一 基本情况二 基本语法jcmd -ljcmd pid helpjcmd pid 具体命令 一 基本情况 在JDK 1.7以后&#xff0c;新增了一个命令行工具jcmd。它是一个多功能的工具&#xff0c;可以用来实现前面除了jstat之外所有命令的功能…

简历网站分享

作者本人自己编写了一个简历站点&#xff0c;分享给大家。在线链接 &#xff0c; github仓库

从PyTorch官方的一篇教程说开去(3.3 - 贪心法)

您的进步和反馈是我最大的动力&#xff0c;小伙伴来个三连呗&#xff01;共勉。 贪心法&#xff0c;可能是大家在处理陌生问题时候&#xff0c;最容易想到的办法了吧&#xff1f; 还记得小时候&#xff0c;国足请了位洋教练发表了一句到现在还被当成段子的话&#xff1a;“如…

【深入C++】map和set的使用

文章目录 C 中的容器分类1. 顺序容器2. 关联容器3. 无序容器4. 容器适配器5. 字符串容器6. 特殊容器 set1.构造函数2.迭代器3.容量相关的成员函数4.修改器类的成员函数5.容器相关操作的成员函数 multiset1.equal_range map1.初始化相关的函数2.迭代器3.容量相关的成员函数4.访问…

58. 不理解竞态问题

内容 竞态问题可能程序员面临的最困难和最隐蔽的错误之一。作为 Go 开发者&#xff0c;必须理解数据竞争和竞态条件等关键方面&#xff0c;包括它们可能产生的影响以及如何避免。接下来将首先讨论数据竞争与竞态条件的区别&#xff0c;然后研究 Go 内存模型及其重要性。 数据…

SpringBoot常用功能实现

1. 配置文件多环境配置 1.1 创建不同环境配置文件 文件名前缀和后缀为标准固定格式&#xff0c;不可以改变。 1.2 pom中加入文件配置 可以使用<activation>标签设置默认环境。 <profiles><profile><id>dev</id><activation><active…

Typora 1.5.8 版本安装下载教程 (轻量级 Markdown 编辑器),图文步骤详解,免费领取(软件可激活使用)

文章目录 软件介绍软件下载安装步骤激活步骤 软件介绍 Typora是一款基于Markdown语法的轻量级文本编辑器&#xff0c;它的主要目标是为用户提供一个简洁、高效的写作环境。以下是Typora的一些主要特点和功能&#xff1a; 实时预览&#xff1a;Typora支持实时预览功能&#xff0…

在 CentOS 7 上安装 Docker 并安装和部署 .NET Core 3.1

1. 安装 Docker 步骤 1.1&#xff1a;更新包索引并安装依赖包 先安装yum的扩展&#xff0c;yum-utils提供了一些额外的工具&#xff0c;这些工具可以执行比基本yum命令更复杂的任务 sudo yum install -y yum-utils sudo yum update -y #更新系统上已安装的所有软件包到最新…

【spring boot】初学者项目快速练手

项目视频&#xff1a;一小时带你从0到1实现一个SpringBoot项目开发_哔哩哔哩_bilibili 注解视频&#xff1a;10、Java高级技术&#xff1a;注解&#xff1a;认识注解_哔哩哔哩_bilibili 一、基础知识 1.注解Annotation &#xff08;1&#xff09;定义 注解是Java代码里的特…

Golang | Leetcode Golang题解之第257题二叉树的所有路径

题目&#xff1a; 题解&#xff1a; func binaryTreePaths(root *TreeNode) []string {paths : []string{}if root nil {return paths}nodeQueue : []*TreeNode{}pathQueue : []string{}nodeQueue append(nodeQueue, root)pathQueue append(pathQueue, strconv.Itoa(root.V…

干货-并发编程提高——线程切换基础(一)

现在的时分&#xff08;time-sharing&#xff09;多任务&#xff08;multi-task&#xff09;操作系统架构通常都是用所谓的“时间分片&#xff08;time quantum or time slice&#xff09;”方式进行抢占式&#xff08;preemptive&#xff09;轮转调度&#xff08;round-robin式…

HydraRPC: RPC in the CXL Era——论文阅读

ATC 2024 Paper CXL论文阅读笔记整理 问题 远程过程调用&#xff08;RPC&#xff09;是分布式系统中的一项基本技术&#xff0c;它允许函数在远程服务器上通过本地调用执行来促进网络通信&#xff0c;隐藏底层通信过程的复杂性简化了客户端/服务器交互[15]。RPC已成为数据中心…

【iOS】内存五大分区

目录 堆&#xff08;Heap&#xff09;是什么五大分区栈区堆区全局/静态区常量区&#xff08;即.rodata&#xff09;代码区&#xff08;.text&#xff09; 函数栈堆和栈的区别和联系图解 OC语言是C语言的超集&#xff0c;所以先了解C语言的内存模型的内存管理会有很大帮助。C语言…

PHP接入consul,注册服务和发现服务【学习笔记】

PHP接入consul,注册服务和发现服务 consul安装 链接: consul安装 启动consul C:\Users\14684>consul agent -dev安装TP5 composer create-project topthink/think5.0.* tp5_pro --prefer-dist配置consul 创建tp5_pro/application/service/Consul.php <?php /*****…

《昇思25天学习打卡营第25天|文本解码原理--以MindNLP为例》

文本解码是自然语言处理&#xff08;NLP&#xff09;中的一个关键步骤&#xff0c;用于将模型生成的向量表示转化为可读的文本。 文本解码的基本原理 在 NLP 中&#xff0c;解码过程通常从模型输出的概率分布或嵌入向量开始&#xff0c;通过某种策略将这些概率或嵌入转化为…

html改写vue日志

本人最近学了vue&#xff0c;想着练手的方法就是改写之前在公司开发的小系统前端&#xff0c;将前端的AJAXJSThymeleaf改为axiosvue。 改写html 将<html>中的<head>和<body>结构移除&#xff0c;将css部分移入<style>&#xff0c; 重新定义了全局的&…