news 2026/3/20 5:30:52

PHP的缓存击穿 = 缓存穿透?

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
PHP的缓存击穿 = 缓存穿透?

缓存击穿和缓存穿透是两个截然不同的概念,它们发生的场景、原因和解决方案都有本质区别。

核心结论

  • 缓存穿透:访问一个根本不存在的数据。相当于你要找一个不存在的人,查了通讯录(缓存)没找到,又去翻了全市户口本(数据库)还是没找到。这是“数据存在性”问题。
  • 缓存击穿:访问一个存在但刚好过期的热点数据。相当于你要找市长,但市长刚好在开会(缓存过期),导致所有电话都打到会议室(数据库)。这是“热点数据并发”问题。

第一层:缓存穿透的“庖丁解牛”

攻击原理

攻击者故意频繁请求一个数据库中根本不存在的数据

攻击流程
  1. 请求缓存:cache.get('user_9999999')->缓存未命中
  2. 请求数据库:SELECT * FROM users WHERE id = 9999999->数据库查询为空
  3. 由于数据不存在,无法写入缓存(或者只能缓存一个短暂的空值)
  4. 下一个相同请求到来,重复步骤1-3
造成危害
  • 数据库压力:恶意请求会绕过缓存,直接冲击数据库,可能导致数据库宕机。
  • 资源浪费:大量无效查询消耗系统资源。
解决方案
  1. 缓存空对象:即使数据库查询为空,也在缓存中存储一个空值(如NULL)并设置一个较短的过期时间(如1-5分钟)。
    $user=$cache->get('user_'.$id);if($user===null){$user=$db->query("SELECT * FROM users WHERE id =$id");if(!$user){// 数据库也没有,缓存一个空对象,避免频繁查询数据库$cache->set('user_'.$id,false,300);// 缓存5分钟}else{$cache->set('user_'.$id,$user,3600);}}return$user!==false?$user:null;
  2. 布隆过滤器:在缓存前加一层布隆过滤器,快速判断数据是否可能存在。如果布隆过滤器说数据不存在,则直接返回,不查询缓存和数据库。

第二层:缓存击穿的“庖丁解牛”

发生场景

某个热点数据(如热门商品信息、明星微博)在缓存中过期瞬间,有大量并发请求同时到来。

击穿流程
  1. 热点Key缓存过期:cache.get('hot_product_123')->缓存过期
  2. 瞬间有数万个并发请求同时发现缓存失效
  3. 数万个请求同时去查询数据库:SELECT * FROM products WHERE id = 123
  4. 数据库瞬间承受巨大压力,可能被打挂
造成危害
  • 数据库雪崩:热点数据的并发查询可能导致数据库连接池耗尽、CPU飙高。
  • 系统瘫痪:整个服务因一个热点Key的失效而不可用。
解决方案
  1. 互斥锁:第一个发现缓存过期的请求获取分布式锁,然后查询数据库并重建缓存,其他请求等待。
    publicfunctiongetProduct($id){$key='product_'.$id;$product=$cache->get($key);if($product===null){// 缓存失效$lockKey='lock:'.$key;if($cache->add($lockKey,1,10)){// 尝试获取锁// 获取锁成功,查询数据库$product=$db->query("SELECT * FROM products WHERE id =$id");$cache->set($key,$product,3600);$cache->delete($lockKey);// 释放锁}else{// 没获取到锁,等待重试或返回默认值usleep(100000);// 等待100msreturn$this->getProduct($id);// 重试}}return$product;}
  2. 永不过期+逻辑过期:缓存不设置过期时间,但值中包含逻辑过期时间。后台任务定期更新缓存。
  3. 热点数据预加载:在缓存过期前,提前异步刷新缓存。

第三层:对比总结表

特征缓存穿透缓存击穿
攻击目标不存在的数据存在但过期的高并发数据
请求性质恶意攻击或错误请求正常的用户请求
并发量可能不高,但持续不断瞬间高并发
根本问题数据不存在性判断热点数据并发重建
解决方案1. 缓存空值
2. 布隆过滤器
1. 互斥锁
2. 逻辑过期

第四层:实战场景示例

缓存穿透场景

场景:攻击者用脚本遍历用户ID:/api/user/1,/api/user/2, …,/api/user/1000000
结果:大部分ID都不存在,每次请求都穿透到数据库。

缓存击穿场景

场景:双十一零点,数万用户同时点击"秒杀iPhone"商品页面,该商品缓存刚好在11:59:59过期。
结果:零点瞬间数万请求同时打向数据库查询同一商品信息。


第五层:还有一个"缓存雪崩"

为了完整起见,我们提一下相关的第三个概念:

缓存雪崩大量的缓存Key在同一时间点或时间段内集中过期,导致所有请求都落到数据库上。

  • 与击穿的区别:击穿是单个热点Key,雪崩是大量Key同时失效
  • 解决方案:给缓存过期时间加上随机值,避免同时过期。

终极总结

  • 穿透:查无此数据→ 用布隆过滤器缓存空值解决
  • 击穿:查热点数据但缓存刚好失效 → 用互斥锁解决
  • 雪崩大量数据缓存同时失效 → 用随机过期时间解决

理解这三者的区别,是设计高可用缓存架构的基础。它们虽然都导致数据库压力,但病因不同,治疗方案也完全不同。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/3/15 20:57:35

5分钟上手WebTopo:零基础打造专业级拓扑图的终极指南

还在为复杂的网络架构图发愁吗?想要快速绘制专业的工业监控界面却无从下手?今天我要向大家推荐一款真正让拓扑设计变得简单高效的神器——WebTopo!🚀 【免费下载链接】WebTopo 基于VUE的web组态(组态,拓扑图…

作者头像 李华
网站建设 2026/3/19 21:45:41

Sollumz插件实战指南:在Blender中高效制作GTA V游戏资产的完整流程

想要为GTA V创作独特的游戏资产却苦于复杂的文件格式转换?Sollumz插件为你提供了在Blender中一站式完成GTA V资产制作的便捷解决方案。这款开源工具深度整合了GTA V的专有文件格式,让普通玩家也能轻松制作专业的游戏内容。 【免费下载链接】Sollumz Blen…

作者头像 李华
网站建设 2026/3/17 6:23:40

LunaTranslator:让Galgame玩家轻松跨越语言障碍的智能翻译方案

LunaTranslator:让Galgame玩家轻松跨越语言障碍的智能翻译方案 【免费下载链接】LunaTranslator Galgame翻译器,支持HOOK、OCR、剪贴板等。Visual Novel Translator , support HOOK / OCR / clipboard 项目地址: https://gitcode.com/GitHub_Trending/…

作者头像 李华
网站建设 2026/3/15 19:45:26

Java外功核心7深入源码拆解Spring Bean作用域生命周期与自动装配

💝💝💝欢迎莅临我的博客,很高兴能够在这里和您见面!希望您在这里可以感受到一份轻松愉快的氛围,不仅可以获得有趣的内容和知识,也可以畅所欲言、分享您的想法和见解。 持续学习,不断…

作者头像 李华
网站建设 2026/3/15 19:45:23

揭秘智谱Open-AutoGLM搭建难题:3个关键坑点与实战避坑指南

第一章:智谱Open-AutoGLM搭建教程Open-AutoGLM 是智谱AI推出的一款面向自动化机器学习任务的开源工具,支持自然语言处理中的自动模型构建、训练与部署。通过该框架,开发者能够快速实现从数据预处理到模型推理的完整流程。环境准备 在开始搭建…

作者头像 李华
网站建设 2026/3/16 0:28:09

宏智树AI:重塑学术写作体验,开启智能化论文创作新时代

在学术研究的浩瀚星空中,每一项突破都始于思想的火花,而成于严谨的表达。然而,从灵感到成文这条路上,无数研究者曾面临过共同挑战:文献梳理的繁杂、数据处理的艰深、格式规范的琐碎、查重降重的煎熬……如今&#xff0…

作者头像 李华