掘金 人工智能 17小时前
Redis 数据倾斜?别慌!从成因到解决方案,一文帮你搞定
index_new5.html
../../../zaker_core/zaker_tpl_static/wap/tpl_guoji1.html

 

本文深入探讨了Redis集群中数据倾斜的两种主要情况:数据量倾斜和数据访问倾斜。文章分析了导致数据倾斜的多种原因,如bigkey、Slot分配不均以及Hash Tag的使用,并针对不同情况提出了相应的应对策略,包括避免bigkey、均衡分配Slot、以及采用热点数据多副本等方法,旨在帮助读者优化Redis集群的性能和稳定性。

💥 数据量倾斜指的是数据在Redis集群的实例间分布不均,导致部分实例负载过重。其主要成因包括bigkey的存在、Slot分配不均衡以及Hash Tag的使用。

🔑 Bigkey是导致数据量倾斜的关键因素之一,大K的V值过大或包含大量集合元素,会使单个实例的数据量激增。应对方法是在业务层避免创建bigkey,或将集合类型的bigkey拆分成多个小集合,分散存储。

💡 Slot分配不均也会导致数据倾斜,若运维人员未均衡分配Slot,可能导致大量数据集中到同一实例。应对方法是制定运维规范,避免将过多Slot分配到同一实例,并通过迁移Slot来调整数据分布。

🔥 数据访问倾斜源于热点数据,大量访问请求集中到存储热点数据的实例上。针对此问题,可以采用热点数据多副本的策略,通过在key中添加随机前缀,将热点数据分散到不同Slot和实例,从而分担访问压力。

本文已收录在Github关注我,紧跟本系列专栏文章,咱们下篇再续!

分片集群中,数据会按一定分布规则分散到不同实例保存。如使用Redis Cluster,数据先CRC计算值对Slot(逻辑槽)取模,同时,所有Slot又会由运维管理员分配到不同实例。这样,数据就被保存到相应实例。这种方法实现简单,但易导致数据倾斜。

1 数据倾斜

若数据倾斜了,则保存大量数据或保存热点数据的实例的处理压力就会增大,速度变慢,甚至可能引起该实例的内存耗尽。

2 数据倾斜成因

数据倾斜时,数据在分片集群的多个实例上分布不均衡,大量数据集中到1或多个实例。

主要原因:某实例保存了bigkey、Slot分配不均衡及Hash Tag。

2.1 bigkey导致倾斜

2.1.1 某实例正好保存bigkey

大K的V值很大(String类型)或保存大量集合元素(集合类型),导致该实例的数据量增加,内存资源消耗严重。

大K操作一般都会造成实例I/O线程阻塞,若大K访问量较大,就会影响到这个实例上的其它请求的处理速度。

2.1.2 应对方法

在业务层生成数据时,尽量避免将过多数据保存在同一KV对。若大K是集合类型,还能把大K拆分成很多个小的集合类型数据,分散保存在不同实例。

假设Hash类型集合user:info保存100万个用户信息,是个大K。则可按用户ID范围,将该集合拆成10个小集合,每个集合只保存10万个用户信息(如小集1保存ID1~10w的用户信息,小集2保存ID10w零 ~ 20w用户)。这就把一个大K化整为零、分散保存,避免大K给单切片实例带来访问压力。

大K访问量较大时,也会造成数据访问倾斜。

2.2 Slot分配不均衡导致倾斜

若集群运维人员没有均衡地分配Slot,就会有大量数据被分配到同一Slot,而同一Slot只在一个实例上分布,导致大量数据被集中到一个实例。

假设Redis Cluster共16384个Slot,假设集群共5个实例,而实例1硬件配置较高,运维人员在给实例分配Slot时,就可能给实例1多分配Slot。

但我们不知道数据和Slot的对应关系,可能导致大量数据正好被映射到实例1的Slot,造成数据倾斜。

2.2.1 应对

可通过运维规范,在分配前,就避免将过多Slot分配到同一实例。

已分配好Slot的集群,可先查看Slot和实例的具体分配关系,从而判断是否有过多Slot集中到同一实例:

查看Slot分配情况:

如执行CLUSTER SLOTS查看Slot分配情况:

127.0.0.1:6379> cluster slots1) 1) (integer) 0   2) (integer) 4095   3) 1) "192.168.10.3"      2) (integer) 63792) 1) (integer) 12288   2) (integer) 16383   3) 1) "192.168.10.5"      2) (integer) 6379

若某实例上有太多Slot,则可用迁移命令把这些Slot迁移到其它实例。Redis Cluster可使用3个命令完成Slot迁移:

假设要把Slot 300从源实例(ID为3)迁移到目标实例(ID为5):

CLUSTER SETSLOT 300 IMPORTING 3
CLUSTER SETSLOT 300 MIGRATING 5
CLUSTER GETKEYSINSLOT 300 100
MIGRATE 192.168.10.5 6379 key1 0 timeout

Redis 3.0.6开始,也可使用KEYS选项,一次迁移多个key(key1、2、3),提升迁移效率。

MIGRATE 192.168.10.5 6379 "" 0 timeout KEYS key1 key2 key3

Codis可以执行下面的命令进行数据迁移。其中,我们把dashboard组件的连接地址设置为ADDR,并且把Slot 300迁移到编号为6的codis server group上。

codis-admin --dashboard=ADDR -slot-action --create --sid=300 --gid=6

2.3 Hash Tag导致倾斜

加在KV对key中的一对花括号{},把K的一部分括起来,客户端在计算K的CRC16值时,只对Hash Tag花括号中的部分K内容进行计算。

不用Hash Tag,则客户端计算整个K的CRC16的值。

如K=user:info:3231,把3231作为Hash Tag,K就变成user:info:{3231}。客户端计算该K的CRC16,就只会计算3231的。否则会计算整个user:info:3231的CRC16值。

2.3.1 好处

若不同K的Hash Tag内容相同,则这些K所对应数据会被映射到同一Slot,同时会被分配到同一实例。使用Hash Tag后,数据被映射到相同Slot的情况:

数据key哈希计算对应的Slot
user:profile:{3231}CRC16('3231') mod 163841024
user:profile:{5328}CRC16('5328') mod 163843210
user:order:{3231}CRC16('3231') mod 163841024
user:order:{5328}CRC16('5328') mod 163843210

user:profile:{3231}user:order:{3231}的Hash Tag一样,CRC16计算值对16384取模后的值也一样,所以映射到相同的1024Slot。

2.3.2 应用场景

主要用在Redis Cluster,支持事务操作和范围查询。因为Redis Cluster本身不支持跨实例的事务操作和范围查询,当业务应用有这些需求时,就只能:

这很麻烦,所以,可使用Hash Tag把要执行事务操作或范围查询的数据映射到同一实例,就能轻松实现事务或范围查询。

2.3.3 Hash Tag潜在问题

大量数据可能被集中到一个实例上,导致数据倾斜,集群负载不均衡。

应对

需在范围查询、事务执行的需求和数据倾斜带来的访问压力之间,取舍!

2.3.4 最佳实践

若使用Hash Tag进行切片的数据会带来较大访问压力,优先考虑避免数据倾斜,最好不要使用Hash Tag进行数据切片。因为事务和范围查询都还可以放在客户端来执行,而数据倾斜会导致实例不稳定,造成服务不可用。

3 数据访问倾斜的成因

根因:实例上存在热点数据(如热点新闻内容、热销商品信息)。

一旦热点数据被存在某实例,则该实例的请求访问量就会远高于其它实例,访问压力很大:

3.1 应对

不同于数据量倾斜,热点数据通常是一或多个数据,所以,直接重新分配Slot也无法解决。

一般热点数据主要服务读操作,可使用热点数据多副本:把热点数据复制多份,在每个数据副本的key中增加一个随机前缀,使其和其它副本数据不会被映射到同一Slot。如此,热点数据既有多个副本可同时服务请求,这些副本数据的key又不同,会被映射到不同Slot。在给这些Slot分配实例时,注意把它们分到不同实例,则热点数据的访问压力就被分散到不同实例。

热点数据的多副本方法只针对只读热点数据。

若热点数据有读有写,就不适合了,因为要保证多副本间数据一致性。要给实例本身增加资源,如使用配置更高机器,应对大量访问压力。

总结

数据倾斜的两种情况:

导致数据量倾斜的主要原因:

数据访问倾斜主要原因:有热点数据存在,导致大量访问请求集中到了热点数据所在的实例上。

应对数据倾斜问题:

倾斜类型倾斜成因应对方法
数据量倾斜存在bigkey业务层避免创建bigkey 把集合类型的bigkey拆分成多个小集合,分散保存
同上Slot手工分配不均制定运维规范,避免把过多Slot分配到一个实例上
同上使用Hash Tag,导致大量数据集中到一个Slot如果Hash Tag会造成数据倾斜,优先避免数据倾斜,不使用Hash Tag
数据访问倾斜存在热点数据采用带有不同key前缀的多副本方法

Q:有数据访问倾斜时,若热点数据突然过期,而 Redis 中数据是缓存,数据的最终值保存在后端DB,会发生啥问题?

A:缓存击穿。Redis 很多性能问题,如导致 Redis 阻塞的场景:bigkey、集中过期、大实例 RDB等都与数据倾斜类似,都因数据集中、处理逻辑集中导致的耗时变长。解决思路类似,把集中变分散,如 bigkey 拆分为小 key、单个大实例拆分为分片集群等。

软件架构演进过程,从单机到分布式,再到MQ、负载均衡,都为将请求压力分散开,避免数据集中、请求集中,既能让系统承载更大的请求量,还保证系统稳定性。

本文由博客一文多发平台 OpenWrite 发布!

Fish AI Reader

Fish AI Reader

AI辅助创作,多种专业模板,深度分析,高质量内容生成。从观点提取到深度思考,FishAI为您提供全方位的创作支持。新版本引入自定义参数,让您的创作更加个性化和精准。

FishAI

FishAI

鱼阅,AI 时代的下一个智能信息助手,助你摆脱信息焦虑

联系邮箱 441953276@qq.com

相关标签

Redis 数据倾斜 集群 bigkey Hash Tag
相关文章