初识,Redis从单机到集群等模式

Redis从单机到集群等模式

单机模式

所谓的单机模式,就是仅部署一个单实例redis。或者说在一台计算机上只运行一个Redis进程,这也是我们学习Redis最开始的模式。在该种模式下,所有客户端连接都将与这台计算机建立连接并进行交互。

但随着发展,我们发现了一些问题,在单机模式下,所有状态都存储在一台计算机上,如果该Redis实例出现问题,甚至于这台计算机出现问题,那么整个系统的可用性就会受到影响。

于是我们开始考虑部署多个Redis实例,甚至在多台计算机上部署Redis。

主从模式

后来我们开始考虑部署多个Redis实例,并在多个实例中选取一个用于跟客户端进行交互,或者说进行读写数据,这个Redis也被称为主Redis,而其余的Redis则用于复制主Redis的数据,它们通常不与客户端进行交互,起到备份数据的作用,这些Redis也被称为从Redis

图模型如下图所示:

总结 :主从模式就是建立多个Redis实例,并指定其中一个为主Redis,其余为从Redis,主Redis支持数据的写入和读取等各项操作,而从Redis只支持与主Redis数据的同步和读取。

它实现了以下2点:

  • 提高数据安全性

通过主从模式我们实现了redis数据的备份,提高了数据的安全性

  • 读写分离

因为主从模式开启了多个Redis实例,以及它的特性(从Redis的数据和主Redis数据相同),所以它也可以实现读写分离,让主Redis只进行写操作,读操作则使用从Redis。这样也一定程度上提高了性能。

配置主从模式

接下来配置的主从模式是1主2从,因此需要3个配置文件,当然你也可以配置1主1从,或者1主n从。

  • 创建多个配置文件

首先创建一个文件夹来存放配置文件

bash 复制代码
 mkdir msconf
  • 配置主Redis配置文件
bash 复制代码
  cat redis.conf |grep -v "#" | grep -v "^$" > msconf/redis-master.conf

为了方便我们复制一个默认的配置文件redis.conf,并为了查看方便,我们使用管道命令去除配置文件中的注释以及空行

  • 配置从Redis配置文件
bash 复制代码
 sed 's/6380/6381/g' redis-master.conf > redis-slave1.conf
 sed 's/6380/6382/g' redis-master.conf > redis-slave2.conf

redis-master.conf文件内容中所有6380 都替换成6381 ,跟6382 ,并存储在redis-slave1.confredis-slave2.conf文件中

接着在从配置文件中,添加如下配置

bash 复制代码
 replicaof 127.0.0.1 6380

这样就明确了从redis应该从哪个主redis进行数据复制

在Redis5.0之前的版本,一直使用 SLAVEOF 作为复制命令,从5.0.0版本开始Redis正式将 SLAVEOF 命令改名为 REPLICAOF

  • 最后

启动三个redis实例即可,在成功启动从redis后,我们可以看到如下字样

bash 复制代码
 45163:S 22 Nov 2023 22:24:29.415 * Connecting to MASTER 127.0.0.1:6380
 45163:S 22 Nov 2023 22:24:29.415 * MASTER <-> REPLICA sync started
 45163:S 22 Nov 2023 22:24:29.415 * Non blocking connect for SYNC fired the event.
 45163:S 22 Nov 2023 22:24:29.416 * Master replied to PING, replication can continue...
 .........
 45163:S 22 Nov 2023 22:24:29.417 * Full resync from master: c111745490b5b3b94b1fcb109fb4019e2419c32e:0
 45163:S 22 Nov 2023 22:24:29.535 * MASTER <-> REPLICA sync: receiving 172 bytes from master to disk
 .......
 45163:S 22 Nov 2023 22:24:29.556 * MASTER <-> REPLICA sync: Finished with success

到这里主从模式,就配置成功了

不足

尽管从redis进行了数据备份,但主从模式有个最大的问题,它不具备自动容错和恢复功能,在主机故障的情况下需要人工干预才能恢复正常。

为了解决该问题,哨兵模式应运而生。

哨兵模式

哨兵模式是一种基于主从模式的高可用性解决方案,它在主从的基础上增加了哨兵,哨兵可以检测主Redis 是否处于正常状态,并在主Redis出现故障时自动从余下的从Redis(备用Redis)中选取一个转换为主Redis。

哨兵(Redis Sentinel):不是一个普通的 Redis 实例。它是一个专门设计用于监控和管理 Redis 高可用性的组件。Redis Sentinel 是一个独立的进程或服务.

它的作用是监控 Redis 主从集群的健康状况,并在主服务器不可用时执行故障转移,哨兵的出现进一步提高了redis系统的可用性和可靠性。

Redis开启哨兵模式(Redis Sentinel的部署)通常包括多个 哨兵(Sentinel) 实例,它们协同工作以确保 Redis 系统的高可用性。这些 Sentinel 进程会相互通信,共同决定何时进行故障转移,选择新的主服务器等。

注意:使用哨兵模式,Redis Sentinel的建议最少数量是3个实例。这是因为Redis Sentinel旨在提供高可用性,而使用奇数个哨兵实例有助于避免因网络分割或故障引起的投票决策的平局问题。

每个哨兵都有独立选主的能力,如果是偶数,则可能出现一半选A,一半选B的情况。关于哨兵选主的策略这里就不展开介绍了。

配置哨兵模式

在解压redis后,我们可以发现文件中有一个sentinel.conf,它就是用来启动redis的哨兵的文件,我们需要几个哨兵就创建几个配置文件,并启动即可。

  • 生成并修改sentinel配置文件

我们的目标是生成3个哨兵,于是需要创建三个配置文件。为了方便管理,我们建议先创建一个文件夹来存放sentinel.conf配置文件

bash 复制代码
 mkdir sentinelconf

接下来我们复制默认的sentinel.conf配置文件并进行修改,跟修改主从模式类似,我们在复制的时候,去掉配置文件中的注释跟换行

bash 复制代码
 sentinel.conf|grep -v "#" |grep -v "^$" > sentinelconf/sentinel_26380.conf
  • 继续创建sentinel配置文件
bash 复制代码
 sed "s/26380/26381/g" sentinel_26380.conf >sentinel_26381.conf 
 sed "s/26380/26382/g" sentinel_26380.conf >sentinel_26382.conf 

我们根据刚刚创建的sentinel_26380.conf,继续创建的sentinel_26381.conf 和sentinel_26382.conf

  • 修改配置文件

接下来,我们通过修改配置文件来指定哨兵监听的主Redis是哪个

bash 复制代码
 port 26380
 daemonize no   
 # 哨兵的启动模式,yes是后台启动
 ​
 pidfile /var/run/redis-sentinel.pid
 logfile ""
 dir /tmp
 sentinel monitor mymaster 127.0.0.1 6380 2
 # 哨兵监听的master数据库,mymaster是为主数据库起的名称,可以随便起个名字,后面是master的ip和端口
 # 最后的数字 表示需要多少个哨兵认为master挂了才认定master挂掉,这里我设定为2 大家自定设定
 ​
 sentinel down-after-milliseconds mymaster 30000
 # 30秒内 master无响应则认为master挂掉
 acllog-max-len 128
 sentinel parallel-syncs mymaster 1
 sentinel failover-timeout mymaster 180000
 #故障转移超时时间,指在该时间内如果故障转移没有成功,则会再发起一次故障转移  这里为180秒
 ​
 sentinel deny-scripts-reconfig yes
 SENTINEL resolve-hostnames no
 SENTINEL announce-hostnames no

sentinel parallel-syncs 参数指定在进行故障转移时,同时从新的主服务器同步数据的从服务器数量。

具体来说,sentinel parallel-syncs mymaster 1 中的数字 1 表示在进行同步时,最多只有一个从服务器可以同时与新的主服务器进行同步。这样的设置可以避免在故障转移期间对主服务器和网络造成过大的负担,因为同步过程可能会导致一些性能开销。

将三个的哨兵监听的redis指定为同一个即可

  • 启动与测试

接下来我们先启动三个redis实例,再启动哨兵

启动哨兵

bash 复制代码
 redis-sentinel sentinel_26380.conf

如果看到如下信息,则表明哨兵启动成功

bash 复制代码
 6345:X 23 Nov 2023 18:57:56.012 * Sentinel new configuration saved on disk
 6345:X 23 Nov 2023 18:57:56.012 # Sentinel ID is 1b14b4df6d230bfb96bdd9910f5244912e127299
 6345:X 23 Nov 2023 18:57:56.012 # +monitor master mymaster 127.0.0.1 6380 quorum 2
 6345:X 23 Nov 2023 18:57:56.013 * +slave slave 127.0.0.1:6381 127.0.0.1 6381 @ mymaster 127.0.0.1 6380
 6345:X 23 Nov 2023 18:57:56.034 * Sentinel new configuration saved on disk
 6345:X 23 Nov 2023 18:57:56.034 * +slave slave 127.0.0.1:6382 127.0.0.1 6382 @ mymaster 127.0.0.1 6380
 6345:X 23 Nov 2023 18:57:56.075 * Sentinel new configuration saved on disk

从上述信息中,我们可看到主Redis是谁,从Redis又是哪些

将三个哨兵都启动成功后,我们停掉主Redis,来看看会发生什么变化

bash 复制代码
 6345:X 23 Nov 2023 19:06:21.211 # +new-epoch 1
 6345:X 23 Nov 2023 19:06:21.211 # +try-failover master mymaster 127.0.0.1 6380
 6345:X 23 Nov 2023 19:06:21.247 * Sentinel new configuration saved on disk
 6345:X 23 Nov 2023 19:06:21.247 # +vote-for-leader 1b14b4df6d230bfb96bdd9910f5244912e127299 1
 6345:X 23 Nov 2023 19:06:21.247 # fb00360c897e0472b00340fa60737eb2892d6c03 voted for fb00360c897e0472b00340fa60737eb2892d6c03 1
 6345:X 23 Nov 2023 19:06:21.289 # 9f109a6ec10074ef8e5ecaa652956c89fe4ad478 voted for fb00360c897e0472b00340fa60737eb2892d6c03 1
 6345:X 23 Nov 2023 19:06:22.164 # +config-update-from sentinel fb00360c897e0472b00340fa60737eb2892d6c03 127.0.0.1 26382 @ mymaster 127.0.0.1 6380
 6345:X 23 Nov 2023 19:06:22.164 # +switch-master mymaster 127.0.0.1 6380 127.0.0.1 6382
 6345:X 23 Nov 2023 19:06:22.164 * +slave slave 127.0.0.1:6381 127.0.0.1 6381 @ mymaster 127.0.0.1 6382
 6345:X 23 Nov 2023 19:06:22.164 * +slave slave 127.0.0.1:6380 127.0.0.1 6380 @ mymaster 127.0.0.1 6382
 6345:X 23 Nov 2023 19:06:22.188 * Sentinel new configuration saved on disk

在到达我们设置的重试事件后,会看到哨兵-终端输出的如上信息;

switch-master mymaster 127.0.0.1 6380 127.0.0.1 6382

到此,哨兵实验成功,在主Redis挂的情况下,它实现了自行切换

注意:实际开发中,redis实例可以不在同一台电脑上

总结

通过哨兵模式可以实现监控、自行选主、自动恢复,它极大的减轻了开发人员的压力,同时提升故障恢复时效性。

它在主从的基础上,实现了高可用。即保证了redis⼀直处于可⽤状态,即时出现了故障也有备⽤⽅案可进行替换。但面对高并发的情况,还是有些捉襟见肘。

集群模式

上述的2种模式都只有一个Redis实例进行读写操作,尽管redis的性能很好,但随着发展,也出现了高并发的问题。于是,集群模式(Redis Cluster)又站了出来。

Redis集群是指将多个Redis实例集合在一起,通过网络组成一个分布式缓存系统,从而实现高可用性和扩展性的目的。

它有具有如下特点:

  • Redis集群中每个节点(实例)是对等的,⽆中⼼结构
  • 它们都可以读写数据,节点本身不与外界进行交互,而是通过统一的接口cluster进行交互,而cluster也复杂管理众多的redis实例,负责在背后管理节点的发现、命令路由和重定向,这使得对外界而言,访问集群与单个Redis相似
  • 使用槽(slot)的概念来对数据进行分片。每个节点负责存储一部分槽的数据,提高了并行处理能力和系统的负载均衡
  • 集群每个节点通过主从(哨兵模式)实现了其⾼可⽤性,

总体而言,Redis集群是对哨兵模式的再一次升级,它提供了一个高度可扩展、高可用性、自动化的分布式存储解决方案,适用于需要处理大规模数据和需要横向扩展的场景。

配置集群

在Redis的配置文件redis.conf中就有对应的配置跟讲解,只不过被注释了:

bash 复制代码
 ################################ 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
  • 创建cluster_conf目录

这里创建目录,同时是为了方便管理

bash 复制代码
 mkdir cluster_conf
  • 创建配置文件

复制redis中的默认配置文件,并添加对应的集群配置

bash 复制代码
  cat redis.conf | grep -v "#"|grep -v "^$" > cluster_conf/redis-7001.conf

添加对应的集群配置

bash 复制代码
 cluster-enabled yes
 cluster-config-file nodes-7001.conf
 cluster-node-timeout 5000

继续创建另外几个配置文件

bash 复制代码
 sed 's/7001/7002/g' redis-7001.conf > redis-7002.conf
 sed 's/7001/7003/g' redis-7001.conf > redis-7003.conf
 sed 's/7001/7004/g' redis-7001.conf > redis-7004.conf
 sed 's/7001/7005/g' redis-7001.conf > redis-7005.conf
 sed 's/7001/7006/g' redis-7001.conf > redis-7006.conf
  • 启动这6个redis实例
bash 复制代码
 redis-server redis-7001.conf
 redis-server redis-7002.conf
 redis-server redis-7003.conf
 redis-server redis-7004.conf
 redis-server redis-7005.conf
 redis-server redis-7006.conf

这几个redis实例启动成功后,启动集群

  • 启动集群
bash 复制代码
 redis-cli --cluster create 127.0.0.1:7001 127.0.0.1:7002
 127.0.0.1:7003 127.0.0.1:7004 127.0.0.1:7005 127.0.0.1:7006 --cluster-replicas 1
  • redis-cli:这是 Redis 客户端的命令行工具
  • --cluster create:创建 Redis Cluster 的参数
  • --cluster-replicas 1: 指定每个主节点的从节点数量

使用以上6个节点进行redis集群的创建,并指定每个主节点都有一个从节点。

该命令执行后,程序会进行集群的创建,创建成功后程序会提示你确认"它创建的主从数量是否正确",

bash 复制代码
 Can I set the above configuration?(type 'yes' to accept):

此时,输入yes,继续等待集群创建即可。

bash 复制代码
 [OK] All nodes agree about slots configuration.
 >>> Check for open slots...
 >>> Check slots coverage...
 [OK]All 16384 slots covered.

稍等片刻后,出现如上字样,Redis集群便创建成功

验证集群

使用 redis-cli 工具连接到其中一个节点,并执行 cluster nodes 命令查看集群状态。

bash 复制代码
 redis-cli -p 7001
 127.0.0.1:7000> cluster nodes

正常情况下,我们便可看到所有的节点信息。接下来,我们便可以像操作单redis那样进行操作了。

注意:当你连接到 Redis 集群中的某个节点,并执行像 SET 这样的写操作时,实际上,这个节点可能并不是存储这个键(k1)的主节点。Redis 集群使用了数据分片的概念,将所有的数据划分到不同的槽(slots)中,也就是存储在其他节点上。

但是,当你执行读操作时,可能会涉及到主从复制。即使你连接到的是某个节点的从节点,该节点也会将读请求转发到主节点上执行。这确保了读操作的一致性,因为所有节点的数据都来自于主节点。

总结:虽然你连接到的节点可能不是主节点,但 Redis 集群会确保写操作路由到负责该槽的主节点,以保持数据的一致性。读操作会在必要时通过主从复制确保数据的一致性。

扩展

Redis集群可以进行动态扩容,自由的增删节点,以及平衡节点的数据槽等操作,这里就不展开了。

在集群模式的构建中,我们并没有去创建哨兵,这是因为Redis Cluster已经提供了分布式协调机制来保证数据的一致性和安全性。但对于大型的Redis集群应用,仍建议每个节点都有自己的 Sentinel 监控系统。这样做的好处是可以更好地检测和恢复局部故障,提高整个系统的稳定性和可靠性。而且,由于每个Sentinel只需要监视自己所在节点的健康状况,所以它的资源开销相对较小,不会给系统带来太大的负担。

虽然 Sentinel 和 Redis Cluster 都是为了实现 Redis 的高可用性而设计的,但它们并不是同一级别的概念。简单来说,Sentinel 是一种监控 Redis 主服务器是否可用的系统,而 Redis Cluster 则是一种 Redis 分布式系统的解决方案。

springboot连接集群、哨兵模式

无论是哨兵模式还是集群模式都需要引入对应依赖

xml 复制代码
 <!--spirngboot springdata提供了对redis的支持-->
 <dependency>
     <groupId>org.springframework.boot</groupId>
     <artifactId>spring-boot-starter-data-redis</artifactId>
 </dependency>
  • 哨兵模式配置
yaml 复制代码
 spring:
   redis:
     sentinel:
       master: your-master-name
       nodes: sentinel-host1:port,sentinel-host2:port
       password: your-redis-password

上述是哨兵有密码且相同的情况,如果哨兵密码不同,则用下面的配置

yaml 复制代码
 spring:
   redis:
     sentinel:
       master: your-master-name
       nodes: sentinel-host1:port,sentinel-host2:port
       node-passwords:
         - host: sentinel-host2
           port: port
           password: sentinel1-password
         - host: sentinel-host2
           port: port
           password: sentinel2-password
  • 集群配置
yaml 复制代码
 spring:
   redis:
     cluster:
       nodes: cluster-host1:port1,cluster-host2:port2,cluster-host3:port3
       max-redirects: 3

max-redirects 是指客户端在尝试连接 Redis Cluster 时允许的最大重定向次数。

到此,对Redis的哨兵跟集群的初步介绍就结束。

相关推荐
长栎4 分钟前
写 for 循环写了十年,你却从没用过迭代器模式最狠的那一面
后端
LiaCode8 分钟前
Redis 在生产项目的使用
前端·后端
用户5598224812212 分钟前
Docker Compose Down 导致容器数据误删——ext4 日志恢复全记录
后端
LiaCode13 分钟前
一天学完 redis 的爽翻版核心知识总结
前端·后端
大刚测试开发实战14 分钟前
如何内网穿透访问本地私有化部署的TestHub
前端·后端·github
xiaodaoluanzha33 分钟前
迄今為止,最簡單的編程語言 Nolang
前端·后端
Csvn33 分钟前
Docker 容器管理入门 — 从镜像到容器编排
后端
用户7623524259138 分钟前
ShardingJDBC
后端
行者全栈架构师39 分钟前
IDEA 中 Maven 项目的 15 个红色报错快速解决方法
java·后端
Colin草率地做慢慢地改43 分钟前
关于QuickStore这个项目的重构(2)- 数据库建表文件
后端·面试·架构