首页 > 数据库 >Redis 集群

Redis 集群

时间:2024-07-30 12:31:01浏览次数:7  
标签:clusterNode Redis CLUSTER 集群 节点 结构

Redis 集群

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

   下面会对集群的节点、槽指派、命令执行、重新分片、转向、故障转移、消息等各个方面进行介绍

   一、节点

   1. 连接节点

   一个Redis集群通常由多个节点(node)组成,在刚开始的时候,每个节点都是相互独立的,它们都处于一个只包含自己的集群当中,要组建一个真正可工作的集群,我们必须将各个独立的节点连接起来,构成一个包含多个节点的集群。

   连接各个节点的工作可以使用 CLUSTER MEET命令来完成。该命令的格式如下:

   CLUSTER MEET <ip> <port>

   向一个节点node发送CLUSTER MEET命令,可以让node节点与ip和port所指定的节点进行握手(handshake),当握手成功时,node节点就会将ip和port所指定的节点添加到node节点当前所在的集群中。

   例如:通过向节点7000发送以下命令,我们可以将节点7001添加到节点7000所在的集群里面

   127.0.0.1:7000> CLUSTER MEET 127.0.0.1 7001

   节点会继续使用redisServer结构来保存服务器的状态,使用redisClient结构来保存客户端的状态,至于那些只有在集群模式下才会用到的数据,节点将他们保存到了cluster.h/clusterNode结构、cluster.h/clusterLink结构,以及cluster.h/clusterState结构里面。

   2. 集群数据结构

   1)clusterNode结构

   clusterNode结构保存了一个节点的当前状态,比如节点的创建时间、节点的名字、节点当前的配置纪元、节点的IP地址和端口号等等。

   每个节点都会使用一个clusterNode结构来记录自己的状态,并为集群中所有其他节点(包括主节点和从节点)都创建一个相应的clusterNode结构,以此来记录其他节点的状态。

// 这是对集群节点的描述,是集群运作的基础
typedef struct clusterNode {
    // 节点创建时间
    mstime_t ctime; /* Node object creation time. */

    // 节点名称,也叫做节点ID,由40个十六进制字符组成
    // 启动后会存储在node.conf中,除非文件删除,否则不会改变
    char name[REDIS_CLUSTER_NAMELEN];

    // 节点标识
    // 使用各种不同的标识值记录节点的角色(比如主节点或者从节点)
    // 以及节点目前所处的状态(比如在线或者下线)
    int flags;    

    // 节点当前的配置纪元,用于实现故障转移
    uint64_t configEpoch;

    // 代表节点负责的哈希槽
    unsigned char slots[CLUSTER_SLOTS/8];

    // 节点负责哈希槽的数量
    int numslots;

    // 节点的复制偏移量
    long long repl_offset; 

    // 节点的ip地址
    char ip[NET_IP_STR_LEN];

    // 节点端口号
    int port;                  

    // 与节点的网络链接
    clusterLink *link;          

    // 报告此节点宕机的节点列表
    list *fail_reports; 

    // ...

}

   2)clusterLink结构

   clusterNode结构的 link 属性是一个clusterLink结构,该结构保存了连接节点所需的有关信息,比如套接字描述符,输入缓冲区和输出缓冲区。

 1 typedef struct clusterLink {
 2     // 连接的创建时间
 3     mstime_t ctime;   
 4 
 5     // TCP 套接字描述符
 6     int fd;
 7 
 8     // 与远程节点的网络链接
 9     connection *conn;
10 
11     // 输出缓冲区,保存着等待发送给其他节点的消息(message)
12     sds sndbuf; 
13 
14     // 输入缓冲区,保存着从其他节点接收到的消息
15     sds  rcvbuf;           
16 
17     // 与这个连接相关联的节点,如果没有的话就为NULL
18     struct clusterNode *node; 
19 
20 } clusterLink;

   clusterLink封装了远程节点实例,以及与其的网络链接、接收和发送数据包的信息,基于它两个节点之间就可以保持实时通信了。

   需要注意的是:集群总线中所使用的端口并不是我们之前熟悉的6379这样服务于客户端的端口,而是专用的;它不是我们手动设置的,而是由服务于客户端的端口通过偏移计算(+10000)而来。比如,服务于客户端的端口为6379,那么集群总线监听的端口就为16379。

   所以,若需要以集群模式部署Redis实例,我们必须保证主机上两个端口都是非占用状态,否则实例会启动失败。

   3) clusterState结构

   每个节点都保存着一个clusterState 结构,这个结构记录了在当前节点的视角下,集群目前所处的状态,例如集群是在线还是下线,集群包含多少个节点,集群当前的配置纪元,诸如此类:

 1 // 这个结构存储的是从当前节点视角,整个集群所处的状态
 2 typedef struct clusterState {
 3     // 指向当前节点的指针
 4     clusterNode *myself; 
 5 
 6     // 集群当前的配置纪元,用于实现故障转移
 7     uint64_t currentEpoch;
 8 
 9     // 集群当前的状态:是在线还是下线
10     int state;         
11 
12     // 集群中至少处理着一个槽的节点的数量
13     int size;             
14 
15     // 集群节点名单(包括myself节点)
16     // 节点字典:name->clusterNode(字典的键为节点的名字,字典的值为节点对应的clusterNode结构)
17     dict *nodes;
18 
19     //...
20 }clusterState;

 

 

二、槽指派

Redis集群通过分片的方式来保存数据库中的键值对:集群的整个数据库被分为16384个槽(slot),数据库中的每个键都属于这16384个槽的其中一个,集群中的每个节点可以处理0个或最多16384个槽。
当数据库中的16384个槽都有节点在处理时,集群处于上线状态(ok);相反地,如果数据库中有任何一个槽没有得到处理,那么集群处于下线状态(fail)。通过向节点发送CLUSTER ADDSLOTS命令, 我们可以将一个或多个槽指派(assign)给节点负责。例如:执行以下命令可以将槽0至槽5000指派给节点7000负责:

127.0.0.1:7000> CLUSTER ADDSLOTS 0 1 2 3 4 ... 5000


参考资料:

《Redis设计与实现》

标签:clusterNode,Redis,CLUSTER,集群,节点,结构
From: https://www.cnblogs.com/hld123/p/18332094

相关文章

  • redis 表的统计信息
    redis表的统计信息要获取Redis表的统计信息,您可以使用INFO命令,该命令返回有关Redis服务器的各种信息和统计数据。例如,要获取关于键空间的统计信息,可以使用以下命令:  redis-cliINFOkeyspace这将返回类似以下内容的信息:  #Keyspacedb0:keys=10,expi......
  • Redis
    Redis快速入门Redis的常见命令和客户端使用初识RedisRedis前世今生,作者是一个以色列人,曾经在做一个关于广告业务,需要使用一款内存数据库,市面没有,自己就写了一个,Redis诞生。Redis是一款基于内存的数据存储结构!【内存】存储介质:半导体。​ 特点:存储效率高,断电数据丢失,存储......
  • 手搓Lock注解,一举解决redisson分布式锁
    最近闲来时间,写了个redis-lock-stater,在pom中引入即可,直接在所要加锁的函数中使用@lock注解即可1、首先需要了解什么是分布式锁分布式锁是控制分布式系统之间同步访问共享资源的一种方式。在分布式系统中,常常需要协调他们的动作,若不同的系统或是同一个系统的不同主机之间共享了......
  • 《Redis设计与实现》读书笔记-客户端
    目录1.Client简介2.客户端属性1)(本文重点)比较通用的属性2)(后续分享)另外一类是和特定功能相关的属性2.1套接字文件描述符2.2名字2.3标志(flag)2.4输入缓冲区2.5命令参数和个数2.6命令函数2.7输出缓冲区3.总结1.Client简介Redis服务器是典型的一对多服务器程序:一个......
  • Redis快速入门
    一、简介redis为非关系型数据库,将数据以key-value(键值对)的形式存入内存基于内存存储,读写性能更高存储热点信息(短时间内存储大量数据)企业应用广泛官网Redis-TheReal-timeDataPlatform中文网Redis中文网二、下载与安装下载地址https://github.com/microsoftarc......
  • RabbitMQ实战——rabbitmq高可用集群搭建
    本文详细介绍了如何在CentOS7系统上部署RabbitMQ高可用集群,包括安装ERlang和RabbitMQ服务器,设置Web客户端,配置主机名映射,同步cookie,加入和退出集群,以及使用镜像队列实现数据同步。摘要由CSDN通过智能技术生成前言本节内容是关于rabbitmq高可用集群的部署搭建,使用的是centos7系统,......
  • (六)Redis 消息队列 List、Streams
    Redis适合做消息队列吗?有什么解决方案?首先要明白消息队列的消息存取需求和工作流程。1、消息队列我们一般把消息队列中发送消息的组件称为生产者,把接收消息的组件称为消费者,下图是一个通用的消息队列的架构模型:消息队列在存取消息时,必须要满足三个需求,分别是消息保序、处理重......
  • tidb集群部署
    ####################################################集群IP例子172.21.243.141172.21.243.69172.21.243.47172.21.243.33172.21.243.184172.21.243.64172.21.243.223机器配置我这边是7台机器,每台2c8g100g####################################################离线部署方......
  • Elasticsearch跨集群搜索
    Elasticsearch(简称ES)是一种基于Lucene的搜索引擎,以其高性能、可扩展性和实时搜索能力而广受欢迎。在大型分布式系统中,跨集群搜索成为了一个重要的需求,它允许用户从多个Elasticsearch集群中联合查询数据,以提高搜索效率和数据一致性。ES|QL(ElasticsearchQueryLanguage)作为一......
  • elasticsearch8单机/集群部署
    目录一、ES8单节点部署集群架构1.环境准备2.创建用户和目录3.下载解压安装包3.1下载es83.2解压安装3.3授权目录4.修改配置文件5.使用system启动es5.1使用oracle-jdk启动(二选一)6.查看日志7.访问验证8.重置elastic密码8.1重置随机密码8.2自定义密码9.jvm内存调整9.1重启验证......