浏览器只在强缓存失效后才触发协商缓存;HTML作为入口文件必须设no-cache或max-age=0,否则用户无法获取新版本,ETag等协商机制将完全失效。

HTML 缓存机制的核心逻辑,一句话就能说清:**浏览器只在强缓存失效后,才可能触发协商缓存;而协商缓存根本不会生效,如果强缓存还没过期。** 你发版后用户看不到新 HTML,90% 的原因就卡在这句话里。
Cache-Control: max-age=86400 是最常踩的坑
这个值意味着浏览器会把 HTML 文件缓存整整一天,期间所有请求都走 from disk cache,压根不发网络请求——ETag、If-None-Match 全部失效。你改了 HTML、重新部署、清了 CDN,用户刷新页面还是旧的,因为浏览器连服务器的门都没敲。
- HTML 作为入口文件,必须设极短的
max-age(比如max-age=0或max-age=1),甚至直接禁用强缓存(no-cache) -
no-cache不等于“不缓存”,而是强制每次走协商缓存;它比no-store更合理,兼顾更新及时性与网络开销 - 别依赖
Expires,它的绝对时间易受客户端时钟影响,且优先级低于Cache-Control
ETag 对 HTML 生效的前提是强缓存已过期
很多团队花力气加 ETag,但忘了配好 Cache-Control,结果 ETag 形同虚设。浏览器只有在强缓存判定“该资源可能过期了”之后,才会在请求头带上 If-None-Match 去和服务端比对。
- 服务端生成
ETag应基于 HTML 内容哈希(如md5(htmlBody)),而不是时间戳或随机值 - 若用 Node.js 手写中间件,注意不要在每次响应中都重算 ETag(比如读文件+哈希),应缓存计算结果,否则性能反被拖累
- CDN 节点若未透传
ETag和If-None-Match,协商缓存会在 CDN 层断掉——需确认 CDN 配置是否开启 “协商缓存透传”
刷新行为直接影响缓存路径选择
用户按什么键,浏览器走哪条缓存链路,完全不一样。这不是玄学,是规范定义的行为。
将调研报告、方案对比、数据分析、需求梳理、会议纪要、设计说明、代码评审、学习笔记等任务产物输出为可在浏览器直接打开的单文件 HTML,替代 Markdown 作为最终交付物。Markdown 在信息密度、视觉清晰度和可分享性上已跟不上 AI 产物的丰富度,HTML 能同时承载排版、表格、SVG 等。
立即学习“前端免费学习笔记(深入)”;
- 地址栏回车 / 页面跳转:完整走强缓存 → 协商缓存流程
- F5 刷新:跳过强缓存,但会发起带
If-None-Match或If-Modified-Since的协商请求 - Ctrl+F5(强制刷新):忽略所有缓存头,直接发完整请求,返回 200 + 全量内容
所以线上问题排查时,光看 Network 面板里有没有请求没用;得看状态码是 200 (from memory cache)、304 还是 200 OK,再结合用户操作方式判断真实路径。
真正难的不是配对几个响应头,而是理解「HTML 必须成为缓存策略的锚点」:JS/CSS 可以靠文件名哈希长期强缓存,但 HTML 本身必须可控地、高频地参与验证。漏掉这点,所有静态资源缓存再精细,发版也白搭。


















