从一个事故中理解 Redis(几乎)所有知识点

从一个事故中理解Redis(几乎)所有知识点

作者:看破

一、简单回顾

事故回溯总结一句话:

(1)因为大 KEY 调用量,随着白天自然流量趋势增长而增长,最终在业务高峰最高点期占满带宽使用 100%。





(2)从而引发 redis 的内存使用率,在 5min 之内从 0%->100%。





(3)最终全面 GET SET timeout 崩溃(11 点 22 分 02 秒)。







(4)最终导致页面返回 timeout。

未解之谜

疑问点:内存使用率 100% 就等同于 redis 不可用吗?

解答:正常使用情况下,不是。

redis 有【缓存淘汰机制】,Redis 在内存使用率达到 100% 时不会直接崩溃。相反,它依赖内存淘汰策略来释放内存,确保系统的稳定性。





学习更多:24 替换策略:缓存满了怎么办?

24 | 替换策略:缓存满了怎么办?-Redis核心技术与实战-极客时间

这个配置在哪里?





大部分同学都是不会主动去调整这里的参数的。

因此大概率默认的是:volatile-lru

  • 行为:使用 LRU(Least Recently Used,最近最少使用)算法驱逐键。volatile-lru 仅驱逐设有过期时间的键,allkeys-lru 则驱逐所有键。

  • 适用场景:缓存场景,不介意丢失一些数据。

确保你根据实际需求配置适当的内存淘汰策略,以便在内存达到上限时,系统能够稳定地处理新请求,而不会出现写操作失败的情况(只要不是 noeviction)。

也就是说,照理 SET GET 都应该没啥问题才对(先不考虑其他复杂命令)。

  • 尽管 Redis 本身不会轻易崩溃,但如果内存耗尽且没有淘汰策略或者淘汰策略未能生效,Redis 可能拒绝新的写操作,并返回错误:OOM command not allowed when used memory > 'maxmemory'

  • 如果系统的配置或者操作系统的内存管理不当,可能会导致 Redis 进程被操作系统杀死。

疑问点:但是事故现象就是:内存使用率 100% 时,redis 不可用,怎么解释?

猜测 1:会是淘汰不及时导致的性能瓶颈吗?

也就是说:写入的速度>>淘汰的速度。

解答:如果是正常的业务写入,不可能!

  • redis 纯内存,淘汰速度是非常快的;

  • 这个业务特性,也并非高频写入;

这个 redis 实例其实里面存储的 KEY 很少,最终占了整个实例的内存使用率<5%。





不太符合正常使用下 KEY 不断增多,最终挤爆内存使用率的问题。

因此,初步结论:Redis 的崩溃一般不会是由于单纯写入速度超过淘汰速度引起的,尤其是使用了合理的内存淘汰策略时;如果写入速度非常高,而淘汰策略无法及时清除旧数据,Redis 可能会非常频繁地进行键的查找和淘汰操作,从而导致性能下降。

18 波动的响应延迟:如何应对变慢的 Redis?(上)

18 | 波动的响应延迟:如何应对变慢的Redis?(上)-Redis核心技术与实战-极客时间

具体机制如下:

过期 key 的自动删除机制。它是 Redis 用来回收内存空间的常用机制,应用广泛,本身就会引起 Redis 操作阻塞,导致性能变慢,所以,你必须要知道该机制对性能的影响。

Redis 键值对的 key 可以设置过期时间。默认情况下,Redis 每 100 毫秒会删除一些过期 key,具体的算法如下:

1.采样:

ACTIVE_EXPIRE_CYCLE_LOOKUPS_PER_LOOP 个数的 key,并将其中过期的 key 全部删除;

2.如果超过 25% 的 key 过期了,则重复删除的过程,直到过期 key 的比例降至 25% 以下。

ACTIVE_EXPIRE_CYCLE_LOOKUPS_PER_LOOP 是 Redis 的一个参数,默认是 20,那么,一秒内基本有 200 个过期 key 会被删除。这一策略对清除过期 key、释放内存空间很有帮助。如果每秒钟删除 200 个过期 key,并不会对 Redis 造成太大影响。

但是,如果触发了上面这个算法的第二条,Redis 就会一直删除以释放内存空间。注意,删除操作是阻塞的(Redis 4.0 后可以用异步线程机制来减少阻塞影响)。所以,一旦该条件触发,Redis 的线程就会一直执行删除,这样一来,就没办法正常服务其他的键值操作了,就会进一步引起其他键值操作的延迟增加,Redis 就会变慢。

那么,算法的第二条是怎么被触发的呢?其中一个重要来源,就是频繁使用带有相同时间参数的 EXPIREAT 命令设置过期 key,这就会导致,在同一秒内有大量的 key 同时过期。

可以类比 JVM 频繁 GC 造成的性能影响。



猜测 2:那就是写入太凶猛,且是【非正常业务写入】

那到底是什么导致了内存使用率激增呢??



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值