2、缓存击穿问题概述:定义、热点Key失效瞬间、与穿透的区别、对一致性的冲击

2.1 缓存击穿的定义与本质

缓存击穿(Cache Breakdown)是指当缓存中的某个热点 Key 在失效的瞬间,大量并发请求同时穿透缓存,直接涌向后端数据库或服务层,导致数据库瞬间负载激增,甚至引发雪崩效应。

与缓存穿透不同,击穿针对的是存在但恰好失效的热点数据。其本质是:单点失效 + 高并发读的组合攻击。

核心特征:热点 Key 在失效窗口期内,所有请求都无法命中缓存,全部回源到数据库。

2.2 热点 Key 失效瞬间的流量冲击模型

假设一个热点商品 Key product:1001 的 TTL 为 3600 秒。在失效前的瞬间,所有请求都能命中缓存;失效后的第一个请求触发回源,但在此期间涌入的数千个并发请求都会重复回源。

下图展示了热点 Key 失效瞬间的流量冲击路径:

热点 Key 失效瞬间流量冲击模型 客户端集群 N 个并发请求 缓存层(Redis) Key 已过期 / 被删除 数据库(DB) 瞬时负载飙升 全部 MISS 全部回源 时间轴:热点 Key 失效窗口 T0: Key 过期 → T0+1ms: 第1个请求回源 → T0+10ms: 1000个请求同时回源 冲击效果 DB QPS 瞬间从 10 → 10000+ 连接池耗尽,响应超时 正常情况 缓存命中率 > 99% DB 负载平稳可控 结论:热点 Key 失效瞬间,缓存层形同虚设,所有压力直接传导至数据库 必须通过互斥锁、预热、永不过期等机制进行保护

2.3 缓存击穿与缓存穿透的区别

两者虽然名称相似,但成因、影响范围和治理手段完全不同。下表从多个维度进行对比:

对比维度 缓存击穿 缓存穿透
数据是否存在 数据真实存在(如热点商品) 数据根本不存在(如非法ID)
失效原因 Key 过期 / 被淘汰 / 主动删除 缓存未命中 + 数据库无记录
并发特征 高并发集中攻击单个 Key 大量不同 Key 或随机 Key
数据库影响 瞬时峰值极高,持续短 持续低效查询,累积压力
治理核心 互斥锁、预热、永不过期 布隆过滤器、空值缓存
典型场景 秒杀商品、热搜榜单 恶意攻击、爬虫遍历
常见误区:很多团队将击穿和穿透混为一谈,使用布隆过滤器治理击穿问题。布隆过滤器只能拦截不存在的数据,对真实存在的热点 Key 失效毫无作用。必须根据问题本质选择正确的保护算法。

2.4 缓存击穿对一致性的冲击

缓存击穿不仅导致性能问题,还会对缓存一致性产生严重冲击,主要体现在以下三个层面:

  • 数据不一致窗口扩大:在击穿瞬间,多个线程同时回源数据库,各自执行查询并回写缓存。由于回写顺序不确定,可能导致缓存中写入的是旧版本数据,而数据库已更新为新版本。
  • 缓存与数据库的版本冲突:当击穿发生时,如果数据库在并发回源期间发生了更新操作,部分线程可能读到旧数据并覆盖缓存,导致缓存长期落后于数据库。
  • 级联失效放大不一致:一个热点 Key 的击穿可能触发关联 Key 的连锁失效。例如商品详情页的击穿导致库存、价格、描述等多个关联 Key 同时回源,回源顺序混乱进一步加剧不一致。

下图展示了击穿导致的数据不一致演化路径:

缓存击穿导致的数据不一致演化路径 阶段1:Key 失效 缓存中热点 Key 过期 所有请求 MISS 阶段2:并发回源 N 个线程同时查询 DB 回写顺序不可控 阶段3:版本覆盖 旧版本数据覆盖缓存 新版本被丢弃 最终结果:缓存中为旧数据,数据库中为新数据 一致性窗口从毫秒级扩大到秒级甚至分钟级 一致性治理要点 1. 使用互斥锁保证同一时刻只有一个线程回源写缓存 2. 引入版本号或时间戳,回写时校验数据新鲜度

2.5 击穿场景下的一致性治理挑战

在实际生产环境中,缓存击穿对一致性的冲击往往被低估。以下是三个典型的治理挑战:

挑战 具体表现 影响等级
回源竞态 多个线程同时回源,后回源的线程可能用旧数据覆盖新写入的缓存 高
缓存与数据库更新顺序颠倒 先更新数据库后删除缓存,但击穿期间删除操作被跳过 中
关联数据不一致 商品主数据击穿后,关联的库存、价格、描述等 Key 各自独立回源,导致数据不同步 高
实践建议:在治理缓存击穿时,不能只关注性能保护(防止 DB 被打垮),还必须同步设计一致性保护策略。推荐采用“互斥锁 + 版本号”的组合方案:互斥锁保证单点回源,版本号保证回写数据的新鲜度。

2.6 本章小结

  • 缓存击穿是热点 Key 失效 + 高并发共同作用的结果,与缓存穿透有本质区别。
  • 失效瞬间的流量冲击模型显示,所有请求同时回源,数据库负载呈指数级上升。
  • 击穿对一致性的冲击主要体现在回源竞态和版本覆盖,导致缓存与数据库长期不一致。
  • 治理必须同时兼顾性能保护和一致性保护两个维度,缺一不可。