Redis从入门到放弃(9):集群模式
前面文章我们介绍了Redis的主从模式是一种在Redis中实现高可用性的方式,但也存在一些缺点。
1、主从模式缺点
写入单点故障:在主从模式中,写入操作只能在主节点进行,如果主节点宕机,写入将无法执行。虽然可以通过升级从节点为主节点来解决,但这会增加故障切换的复杂性。
写入压力分摊:当写入操作较多时,写入压力无法分摊,可能成为性能瓶颈。
水平扩容问题:水平扩容牵涉到数据的迁移和访问代理问题。
2、集群的原理
Redis集群是3.0版本提出的一种分布式解决方案。其大致原理是通过分片(Sharding)和数据复制来实现数据的分布和高可用性。下面是Redis集群的基本原理:
数据分片: Redis集群使用哈希槽(hash slot)分片策略,将整个数据空间划分为固定数量的哈希槽。每个节点负责管理一部分哈希槽,而不是管理具体的键值对。
数据分布: 客户端将键通过哈希函数映射到某个哈希槽,然后找到负责该哈希槽的节点。这样,数据被均匀地分布在不同的节点上。
数据复制: 为了提供高可用性,每个主节点都有多个从节点。主节点会将自己的数据异步复制到从节点,以保持数据的一致性。从节点可以处理读请求,也可以在主节点宕机时升级为新的主节点。
故障检测与转移: Redis集群引入了哨兵(Sentinel)节点,用于监控主节点的状态。当主节点宕机或无法访问时,哨兵会发起选举,选择一个从节点升级为新的主节点,从而实现故障转移。
故障恢复: 当主节点恢复时,它会成为从节点,从新的主节点进行数据同步。这种方式可以确保在节点故障恢复后,数据能够重新同步,保持一致性。
动态扩展: 当需要扩展集群规模时,可以增加新的节点,调整哈希槽的分配信息,并在新节点上进行数据迁移。这样集群可以根据需求进行动态扩展,以适应不断增长的数据和流量。
节点通信:集群中每个节点都需要知道其他所有节点的状态信息,包括当前集群状态、集群中各节点负责的哈希槽、集群中各节点的master-slave状态、集群中各节点的存活状态等。Redis集群中,节点之间通过建立TCP连接,使用gossip协议来传播集群的信息。
3、数据分区原理
分布式数据存储首先要解决整个数据集如何按照分区规则划分到多个节点问题,每个节点负责整个数据集的子集。常见的分区规则有3种:哈希取余分区、一致性哈希算法分区和哈希槽分区。
3.1、哈希取余分区
这是最简单的分区方案。数据的键(Key)通过哈希函数得到一个哈希值,然后将哈希值与节点数量(N)取余,以确定数据属于哪个节点。公式:hash(Key) % N
- 优点
这种方式的优点是 简单,一般采用 预分区 的方式,提前根据 数据量 规划好 分区数,比如划分为 512
或 1024
张表,保证可支撑未来一段时间的 数据容量。扩容时通常采用 翻倍扩容,避免 数据映射 全部被 打乱,导致 全量迁移 的情况。常用于 数据库 的 分库分表。
- 缺点
当 节点数量 变化时,如 扩容 、**收缩 **、 宕机 节点,数据节点 映射关系 需要重新计算,会导致数据的 重新迁移。
3.2、一致性哈希算法分区
一致性哈希算法就是将整个哈希值空间组织成一个虚拟的圆环,哈希函数的值空间为0~2^32-1(即哈希值是一个32位无符号整形)。
上图为将node1、node2、node3服务器的IP作为唯一关键字,使用Hash(IP)进行哈希,这样每台机器就能确定其在哈希环上的位置。
key落键规则:当我们需要存储一个kv键值对时,首先计算key的hash值(hash(key))将这个key使用相同的哈希函数计算出哈希值,并确定此数据在环上的位置,从此位置沿环顺时针“行走”,第一台遇到的服务器就是其应该定位到的服务器,并将该键值对存储在该节点上,如上图所示。
- 优点
容错性:若node2挂掉,受影响的数据只有node1和node2之间的数据,且这些数据会转移到node3存储。
扩展性:若在node1和node2之间增加一台node4,受影响的数据只有node1和node4,重写把node1到node4的数据录入到node4即可。
不会导致hash取余数据重新洗牌计算。
- 缺点
数据倾斜:若节点太少且分布不均匀时,会造成大部分数据集中存放在某一台上的问题,如下图所示,大部分数据都会存放在node1上:
3.3、 哈希槽分区(Redis集群方案)
为了解决数据倾斜的问题,Redis3.0中引入了哈希槽的概念。
Redis集群有16384个哈希槽,集群会先给每个master节点分配一部分哈希槽。比如当前集群有3个master节点:
- master1节点包含0~5500号哈希槽
- master2节点包含5501~1000号哈希槽
- master3节点包含11001~16384号哈希槽
进行set操作时,每个key会通过CRC16校验后再对16384取模来决定放置在哪个槽,比如 CRC16(key) % 16384 = 777,那么这个key就会被分配到master1节点上,如下图:
4、Redis集群的MOVED重定向
因为Redis客户端可以向集群中的 **任意节点 **发送指令,那么如果数据没有存放在接收到指令的节点上,怎么办呢?
MOVED重定向:
当Redis节点接收到相关指令时,会先计算key落在哪个哈希槽上,如果恰好在自己节点上,那么就直接处理指令并返回结果;
如果key计算出的哈希槽不在自己节点上,那么当前节点就会查看它内部维护的 **哈希槽 **与 **节点ID **之间的映射关系,然后给客户端返回一个MOVED错误:
- MOVED [哈希槽] [节点IP:端口]
这个错误包含操作的key所属的 **哈希槽 **和能处理这个请求的Redis节点的 **IP **和 **端口号 **,例如“MOVED 3999 127.0.0.1:6379”,客户端需要根据这个信息重新发送查询指令到给定的IP和端口的Redis节点。就完成了MOVED重定向操作。
5、配置集群
准备6台机器,三主三从。
5.1、删除持久化文件
删除原目录下的RDB、AOF格式的文件。
cd /home/redis
rm *.rdb *.aof
5.2、配置redis.conf
对6各节点的redis.conf都做如下配置:
# 开启集群模式
cluster-enabled yes
# 每一个节点需要有一个配置文件,需要6份。每个节点处于集群的角色都需要告知其他所有节点,彼此知道,这个文件用于存储集群模式下的集群状态等信息,这个文件是由redis自己维护,我们不用管。如果你要重新创建集群,那么把这个文件删了就行
cluster-config-file nodes-6379.conf
# 超时时间,超时则认为master宕机,随后主备切换
cluster-node-timeout 5000
5.3、启动所有服务
cd src
redis-server ../redis.conf
5.4、创建集群
执行命令:redis-cli
#####
# 注意1:如果你使用的是redis3.x版本,需要使用redis-trib.rb来构建集群
# 注意2:以下为新版的redis构建方式
#####
# 创建集群,-a 123456是指redis密码, cluster-replicas是指主节点和从节点比例为1,1-3为主,4-6为从,一个主节点对应一个从节点,这也是最经典用的最多的集群模式
redis-cli -a 123456 --cluster create 192.168.1.201:6379 192.168.1.202:6379 192.168.1.203:6379 192.168.1.204:6379 192.168.1.205:6379 192.168.1.206:637 --cluster-replicas 1
6、SpringBoot 2.X 集成Redis集群
spring:
application:
name: test.redis
redis:
jedis:
pool:
#最大连接数据库连接数,设 0 为没有限制
max-active: 8
#最大等待连接中的数量,设 0 为没有限制
max-idle: 8
#最大建立连接等待时间。如果超过此时间将接到异常。设为-1表示无限制。
max-wait: -1ms
#最小等待连接中的数量,设 0 为没有限制
min-idle: 0
lettuce:
pool:
max-active: 8
max-idle: 8
max-wait: -1ms
min-idle: 0
shutdown-timeout: 1000ms
cluster:
# 此处需要配置每个实例的节点
nodes: 192.168.1.201:6379 192.168.1.202:6379 192.168.1.203:6379 192.168.1.204:6379 192.168.1.205:6379 192.168.1.206:637
#密码
password: 123456
server:
port: 8080
Redis从入门到放弃(9):集群模式的更多相关文章
- Redis系列5:深入分析Cluster 集群模式
Redis系列1:深刻理解高性能Redis的本质 Redis系列2:数据持久化提高可用性 Redis系列3:高可用之主从架构 Redis系列4:高可用之Sentinel(哨兵模式) 1 背景 前面我们 ...
- Linux--6 redis订阅发布、持久化、集群cluster、nginx入门
一.redis发布订阅 Redis 通过 PUBLISH .SUBSCRIBE 等命令实现了订阅与发布模式. 其实从Pub/Sub的机制来看,它更像是一个广播系统,多个Subscriber可以订阅多个 ...
- redis 5.0.3 讲解、集群搭建
REDIS 一 .redis 介绍 不管你是从事Python.Java.Go.PHP.Ruby等等... Redis都应该是一个比较熟悉的中间件.而大部分经常写业务代码的程序员,实际工作中或许只用到了 ...
- Redis 5.0.7 讲解,单机、集群模式搭建
Redis 5.0.7 讲解,单机.集群模式搭建 一.Redis 介绍 不管你是从事 Python.Java.Go.PHP.Ruby等等... Redis都应该是一个比较熟悉的中间件.而大部分经常写业 ...
- redis解决方案之三种集群模式的概念与部署
上篇文章为大家总结了redis命令并讲述了持久化,今天我们来看一下redis的三种集群模式:主从复制,哨兵集群,Cluster集群 本篇文章先介绍redis-cluster集群模式,然后再依次介绍它的 ...
- Redis学习笔记~conf自主集群模式
回到目录 Redis自主提供了集群模式,当然也只是比较简单的读写分离模式,或者叫主从模式,它在各个redis服务端自己做数据同步机制,当然就是将主服务端的信息同步到各个slave服务器上,在客户端集成 ...
- 就publish/subscribe功能看redis集群模式下的队列技术(一)
Redis 简介 Redis 是完全开源免费的,是一个高性能的key-value数据库. Redis 与其他 key - value 缓存产品有以下三个特点: Redis支持数据的持久化,可以将内存中 ...
- Redis进阶实践之十 Redis主从复制的集群模式
一.引言 Redis的基本数据类型,高级特性,与Lua脚本的整合等相关知识点都学完了,说是学完了,只是完成了当前的学习计划,在以后的时间还需继续深入研究和学习.从今天开始来讲一下有关Re ...
- Redis进阶实践之十 Redis哨兵集群模式
一.引言 上一篇文章我们详细的讲解了Redis的主从集群模式,其实这个集群模式配置很简单,只需要在Slave的节点上进行配置,Master主节点的配置不需要做任何更改,但是有一 ...
- 深入剖析Redis系列: Redis集群模式搭建与原理详解
前言 在 Redis 3.0 之前,使用 哨兵(sentinel)机制来监控各个节点之间的状态.Redis Cluster 是 Redis 的 分布式解决方案,在 3.0 版本正式推出,有效地解决了 ...
随机推荐
- 简单工厂模式(Static Factory Method)
创建性设计模式--简单工厂模式(Static Factory method) 模式动机 只需要知道参数的名字则可得到相应的对象 软件开发时,有时需要创建一些来自于相同父类的类的实例.可以专门定义一个类 ...
- 分享一个提高运维效率的 Python 脚本
哈喽大家好我是咸鱼,今天给大家分享一个能够提升运维效率的 python 脚本 咸鱼平常在工作当中通常会接触到下面类似的场景: 容灾切换的时候批量对机器上的配置文件内容进行修改替换 对机器批量替换某个文 ...
- react之todoList基础小项目
1.项目最终成品和项目目录快照如图: 2.context.js文件 // 使用context进行多级传递数据 // 1. createContext 创建一个可以多级传递的context数据 // 2 ...
- docker安装kibana,报错Kibana server is not ready yet,未解决
1.命令 docker run -d -e ELASTICSEARCH_URL=http://192.168.101.158:9200 -p 5601:5601 --name kibana kiban ...
- Python忽略NoData计算多张遥感影像的像元平均值:whitebox库
本文介绍基于Python中whitebox模块,对大量长时间序列栅格遥感影像的每一个像元进行忽略NoData值的多时序平均值求取. 在文章Python ArcPy批量计算多时相遥感影像的各像元 ...
- C# 中的“智能枚举”:如何在枚举中增加行为
目录 枚举的基本用法回顾 枚举常见的设计模式运用 介绍 智能枚举 代码示例 业务应用 小结 枚举的基本用法回顾 以下是一个常见的 C# 枚举(enum)的示例: enum Weekday { Mond ...
- 记一次 Oracle 下的 SQL 优化过程
1. 介绍 事情是这样的,UAT 环境的测试小伙伴向我扔来一个小 bug,说是一个放大镜的查询很慢,转几分钟才出数据,我立马上开发环境试了一下,很快啊我说,放大镜的数据立马就出来了,然后我登录 UAT ...
- Netty实战(二)
一.环境准备 Netty需要的运行环境很简单,只有2个. JDK 1.8+ Apache Maven 3.3.9+ 二.Netty 客户端/服务器概览 如图,展示了一个我们将要编写的 Echo 客户端 ...
- Net 如何获取私有属性
.Net的私有属性.成员变量.方法,都可以通过反射获取调用,当然正常我们不会这么操作 此章只是做一个反射科普,像EFCore从数据库取值的底层框架就是通过反射直接操作私有的成员变量,而不是方法. 直接 ...
- 生信服务器 | 更改 CentOS/RHEL 6/7 中的时区
这几天在学习折腾 docker 的时候遇到一个很常见的问题,就是 run container 的时候发现大部分 image 默认使用的时间都是 UTC (Universal Time Coordin ...