当前位置: 首页 > news >正文

缓存击穿,缓存穿透,缓存雪崩的原因和解决方案(或者说使用缓存的过程中有没有遇到什么问题,怎么解决的)

  1. 缓存穿透:
    是指查询一个不存在的数据,由于缓存无法命中,将去查询数据库,但是数据库也无此记录,并且出于容错考虑,我们没有将这次查询的null写入缓存,这将导致这个不存在的数据每次请求都要到存储层去查询,失去了缓存的意义。在流量大时,可能DB就挂掉了,要是有人利用不存在的key频繁攻击我们的应用,这就是漏洞。

解决方案:空结果也进行缓存,可以设置一个空对象,但它的过期时间会很短,最长不超过五分钟。 或者用布隆过滤器也可以解决,Redisson框架中有布隆过滤器。

  1. 缓存雪崩:
    是指在我们设置缓存时采用了相同的过期时间,导致缓存在某一时刻同时失效,请求全部转发到DB,DB瞬时压力过重雪崩。

解决方案:原有的失效时间基础上增加一个随机值,比如1-5分钟随机,这样每一个缓存的过期时间的重复率就会降低,就很难引发集体失效的事件。

  1. 缓存击穿
    是指对于一些设置了过期时间的key,如果这些key可能会在某些时间点被超高并发地访问,是一种非常“热点”的数据。这个时候,需要考虑一个问题:如果这个key在大量请求同时进来之前正好失效,那么所有对这个key的数据查询都落到DB,我们称为缓存击穿。

解决方案:在分布式的环境下,应使用分布式锁来解决,分布式锁的实现方案有多种,比如使用Redis的setnx、使用Zookeeper的临时顺序节点等来实现

在使用缓存(如 Redis、Memcached 等)提升系统性能时,经常会遇到一些典型问题,包括 缓存击穿、缓存穿透、缓存雪崩。这些问题如果不妥善处理,可能导致数据库压力骤增,甚至服务崩溃。下面分别介绍它们的 原因、影响及解决方案


一、缓存击穿(Cache Breakdown)

原因:

某个 热点 key(访问非常频繁的 key)在缓存中突然失效(过期),此时大量并发请求同时访问这个 key,由于缓存中没有,这些请求都会直接打到数据库,造成数据库瞬时压力过大,就像“击穿”了缓存保护层。

影响:

  • 数据库压力骤增,可能引起慢查询甚至宕机。
  • 影响系统整体响应速度与稳定性。

解决方案:

  1. 设置热点数据永不过期
    对于访问特别频繁的数据(比如热门商品信息),不设置过期时间,而是通过后台异步更新缓存,确保缓存一直有效。

  2. 使用互斥锁(Mutex Lock)
    当发现缓存未命中时,不是立即查数据库,而是先尝试获取一个分布式锁(如 Redis 的 SETNX),只有获取到锁的线程才去查数据库并重建缓存,其他线程等待或返回旧数据/默认值。

    适用于高并发且对数据实时性要求不是极端严格的场景。

  3. 逻辑过期
    不设置真正的 key 过期时间,而是在缓存 value 中维护一个逻辑过期时间,当发现逻辑过期时,使用后台线程异步更新缓存,当前请求仍可返回旧数据。


二、缓存穿透(Cache Penetration)

原因:

用户请求了一个 根本不存在的数据(比如不存在的商品 ID、非法参数等),导致每次请求都 穿透缓存,直接打到数据库。如果恶意用户大量发起这样的请求,数据库就会承受巨大压力。

影响:

  • 大量无效查询直接打到数据库,浪费资源。
  • 可能被恶意利用进行攻击(比如大量查询不存在的用户 ID)。

解决方案:

  1. 缓存空对象(Null Caching)
    当查询数据库也不存在该数据时,仍然将一个表示“空”的值(如 null、特殊标记)存入缓存,并设置较短的过期时间(如 30 秒 ~ 5 分钟),避免频繁查询数据库。

    注意:要防止缓存大量无意义空值占用空间。

  2. 布隆过滤器(Bloom Filter)
    在缓存层之前加一个布隆过滤器,用于快速判断某个 key 是否 可能存在。如果布隆过滤器判断该 key 一定不存在,则直接返回,不再查缓存和数据库。

    适合用于 ID 类查询,提前拦截非法或不存在的请求。

  3. 接口层校验
    加强参数校验,比如对 ID 范围、格式进行基础过滤,防止明显非法的请求进入系统。


三、缓存雪崩(Cache Avalanche)

原因:

大量缓存 key 在同一时间失效(比如设置了相同的过期时间),或者缓存服务宕机,导致大量请求直接打到数据库,造成数据库压力过大甚至崩溃,就像“雪崩”一样。

影响:

  • 数据库瞬间流量暴增,可能引发服务不可用。
  • 整个系统性能急剧下降。

解决方案:

  1. 设置不同的过期时间
    避免给大量 key 设置相同的过期时间,可以在基础的过期时间上加上随机值(如基础过期时间 30 分钟 + 随机 0~10 分钟),让缓存错峰失效。

  2. 使用高可用缓存架构
    比如 Redis 集群、主从 + 哨兵、Redis Cluster,避免单点故障导致整个缓存服务不可用。

  3. 熔断降级机制
    当数据库压力过大时,可以使用熔断器(如 Hystrix、Sentinel)暂时拦截部分请求,返回默认值或错误页,保护数据库。

  4. 多级缓存策略
    使用本地缓存(如 Caffeine、Guava Cache) + 分布式缓存(如 Redis)的多级架构,即使分布式缓存出现问题,本地缓存还能起到一定的缓冲作用。

  5. 缓存预热
    系统启动时或低峰期提前将热点数据加载到缓存中,避免刚上线或重启后大量请求直接访问数据库。


总结对比表

问题类型原因解决方案概要
缓存击穿热点 key 突然失效,大量请求直接访问数据库互斥锁、永不过期+后台更新、逻辑过期
缓存穿透请求了不存在的数据,绕过缓存直接查库缓存空对象、布隆过滤器、参数校验
缓存雪崩大量 key 同时失效 / 缓存服务宕机,导致请求全部压到数据库设置随机过期时间、高可用缓存、熔断降级、多级缓存、缓存预热

实际使用中的经验分享(补充)

在实际项目中,我们通常会 组合使用多种策略来防护以上问题,例如:

  • 对热门商品使用 永不过期 + 异步刷新 策略防止击穿;
  • 所有查询先经过 布隆过滤器缓存空对象 来防止穿透;
  • 给所有缓存 key 设置 随机过期时间,并采用 多级缓存 + 熔断降级 来防止雪崩;
  • 使用 Redis 哨兵或集群 提升缓存可用性;
  • 结合 监控系统(如 Prometheus + Grafana)实时观察缓存命中率、响应时间、数据库负载,及时发现异常。
http://www.dtcms.com/a/568530.html

相关文章:

  • 关于数据包分片总长度字段的计算和MF标志位的判断
  • 手机网站建站流程网站建设卩金手指科杰
  • BuildingAI 用户信息弹出页面PRD
  • ​Oracle RAC灾备环境UNDO表空间管理终极指南:解决备库修改难题与性能优化实战​
  • 《uni-app跨平台开发完全指南》- 02 - 项目结构与配置文件详解
  • 【数据分析】基于R语言的废水微生物抗性分析与负二项回归模型建模
  • 深圳专业网站公司注册查询网站
  • k8s --- resource 资源
  • 神经网络之反射变换
  • k8s——pod详解2
  • 四层神经网络案例(含反向传播)
  • MySQL初阶学习日记(1)--- 数据库的基本操作
  • 【k8s】k8s的网络底层原理
  • 一种创新的集成学习模型:结合双通路神经网络与逻辑回归的糖尿病患病概率预测
  • 神经网络之线性变换
  • Fastlane 结合 开心上架(Appuploader)命令行版本实现跨平台上传发布 iOS App 免 Mac 自动化上架实战全解析
  • 大连网站建设平台宁夏考试教育网站
  • 微信网站对接室内设计师报考官网
  • Ceph常用的三种存储操作
  • 【前端】从零开始搭建现代前端框架:React 19、Vite、Tailwind CSS、ShadCN UI 完整实战教程-第1章:项目概述与技术栈介绍
  • react使用ag-grid及常用api笔记
  • MiniEngine学习笔记 : CommandListManager
  • 人工智能讲师数据治理讲师叶梓《数字化转型与大模型技术应用培训提纲》
  • 1.7.课设实验-数据结构-二叉树-文件夹创建系统
  • 互联网大学生创新创业项目计划书seo网址查询
  • 同时打开两个浏览器页面,关闭 A 页面的时候,要求 B 页面同时关闭,怎么实现?
  • 什么是react?
  • Arbess零基础学习 - 使用Arbess+GitLab实现 React.js 项目自动化构建/主机部署
  • 从事网站开发需要的证书网页设计免费网站推荐
  • 任何数据结构的构造或初始化,都应指定大小,避免数据结构无限增长吃光内存【示例】