一篇文章搞懂,浏览器强缓存以及协商缓存

你有没有发现,有些网页第二次打开速度特别快?这就是利用了缓存。 下面介绍一下浏览器常见的两种缓存策略。

一:强缓存

强缓存的本质是 "时间有效性验证",浏览器无需向服务器发送请求,直接根据本地缓存的过期时间判断是否可用。

假设项目中有一张图片资源:test.png。 首次请求test.png时,服务器返回Cache-Control: max-age=86400(24 小时有效期)。​ 24 小时内再次请求该图片,浏览器直接从缓存读取,网络请求瀑布图显示200OK ,不会向服务器发送请求(200仅仅表示资源加载成功,并未与服务器交互)。

强缓存类型:

1.from memory cache (资源暂存于浏览器内存)

2.from disk cache ( 资源持久化存储于本地硬盘)

关键http头部字段

Expires (单位:GMT 时间字符串)

格式:Expires: Wed, 03 Jun 2025 12:00:00 GMT​

缺点:依赖服务器时间,若客户端与服务器时钟不同步,服务器返回的过期时间就不一定是准确的,可能导致缓存提前失效或过期资源被使用​。

Cache-Control(单位:秒)

max-age=604800:7 天有效期,优先级高于 Expires​。

Cache-Control其他值:

public:允许代理服务器缓存(如 CDN)​

private:仅客户端可缓存​

no-cache:非禁止缓存,而是要求使用前必须经服务器验证(实际触发协商缓存)​

no-store:严格禁止缓存,每次请求必须从服务器获取

Cache-Control与Expires的优先级对比

Cache-Control 的优先级高于 Expires

原因:

Expires 通过 "具体时间点" 定义过期(如 Wed, 31 Dec 2025 23:59:59 GMT),但它依赖浏览器本地时间

Cache-Controlmax-age 以 "时长" 定义过期(如 max-age=86400 表示 1 秒),计算起点是 "资源首次下载完成的时间",不依赖本地时间

Cache-Control 优先级高于 Expires,核心是它解决了 Expires 依赖本地时间的缺陷。

强缓存工作流程

浏览器发起资源请求 -> 服务器返回资源,并设置缓存 -> 再次发送资源请求 ->检查是否过期 →->未过期 (不存在缓存 或 已过期 → 发起网络请求) -> 返回200(不发送网络请求)

如果资源命中值强缓存,如何更新?

改变资源唯一标识,加版本号、改变资源hash值...

二 : 协商缓存

1、触发条件与核心逻辑

当强缓存失效(如 max-age 过期),浏览器会向服务器发送请求,携带缓存标识验证资源是否更新。

2、双重验证机制

第一重:Last-Modified / If-Modified-Since

服务器响应时添加Last-Modified: Thu, 01 Jun 2025 10:00:00 GMT​

浏览器再次请求时,在请求头中携带If-Modified-Since: Thu, 01 Jun 2025 10:00:00 GMT​

服务器对比资源实际修改时间,若未变更则返回304 Not Modified,浏览器使用本地缓存

第二重:ETag / If-None-Match(优先级更高)​

服务器根据资源内容生成唯一哈希值,如ETag: "5f8e1a2b3c4d5e6f"​

浏览器请求时携带If-None-Match: "5f8e1a2b3c4d5e6f"​

服务器对比哈希值,一致则返回 304,否则返回新资源(200 OK)

3、协商缓存两种方式优先级说明

为什么ETag 的精度高于 Last-Modified?

1.某些场景下资源修改时间变更但内容未变(如修改注释)Last-Modified 会误判为更新;

2.因为Last-Modified的最小单位是秒,加入文件在一秒内改变了多次,这个时候Last-Modified的值并没有变化。

ETag 基于内容哈希,只要内容不变,即使修改时间变化也能正确识别为未更新。

协商缓存的304/200,均为服务器返回。

三、协商缓存与强缓存优先级

强缓存优先级高于协商缓存

原因:本质是为了最大化减少网络请求,提升加载性能

参考文章:

blog.csdn.net/m0_74065758...

相关推荐
DianSan_ERP11 小时前
电商架构演进:如何在高并发场景下实现多平台API的标准化履约?
运维·前端·网络·安全·架构·自动化
碎_浪14 小时前
给键盘党的英语记忆工具:我做了一款「打字背单词」桌面应用
前端·程序员·ai编程
阿成学长_Cain15 小时前
Linux dirs命令详解|Bash目录堆栈管理快速切换目录实战教程
linux·运维·前端·数据库
多加点辣也没关系15 小时前
JavaScript|第4章:类型转换
开发语言·javascript
yqcoder15 小时前
httpOnly 是什么,又有什么用?
开发语言·前端·javascript
IT_陈寒15 小时前
Java的Stream.parallel()把我CPU跑爆了,这种优化要谨慎
前端·人工智能·后端
小皮虾16 小时前
小程序首页性能优化实战:从 4 秒到 1.8 秒
前端·微信小程序
烬羽16 小时前
还在手动拼路径、写回调地狱?一文吃透 Node.js 的 path 和 fs
javascript·程序员·node.js
山河木马16 小时前
GPU自动处理专题1-裁剪到底在裁什么(裁剪)
前端·webgl·计算机图形学