Skip to content

02. 浏览器缓存机制深度解析

1. 浏览器缓存的分类体系

浏览器缓存主要分为以下两种核心类型:

  1. 强缓存(Strong Cache)

    • 通过 Cache-ControlExpires 响应头实现
    • 典型特征:直接读取本地缓存,不发送请求到服务器
    • 示例场景:当 Cache-Control: max-age=3600 时,1小时内重复请求直接使用缓存
    text
    HTTP/1.1 200 OK
    Cache-Control: max-age=3600
    Content-Type: text/css
  2. 协商缓存(Conditional Cache)

    • 依赖 Last-Modified/If-Modified-SinceETag/If-None-Match 两组头部
    • 典型特征:需要向服务器发送验证请求,返回 304 状态码时使用缓存
    • 验证流程:

2. 触发浏览器缓存的典型场景

  1. 静态资源重复请求

    • CSS/JS 文件:style.css, app.js
    • 图片资源:logo.png, banner.jpg
    • 字体文件:font.woff2
  2. 页面导航行为

    • 浏览器后退/前进操作
    • 相同 URL 的重复访问
    • 新标签页打开已访问过的页面
  3. 现代 Web 应用特性

    • SPA 应用路由切换时的异步资源加载
    • CDN 边缘节点的缓存响应
    • Service Worker 控制的缓存策略

3. 缓存控制策略详解

1. 强缓存控制

text
Cache-Control: max-age=31536000, public, immutable
  • max-age:缓存有效期(秒)
  • public:允许代理服务器缓存
  • immutable:声明资源永久不变(适用于带 hash 的文件)

2. 协商缓存配置

text
ETag: "6273b-dqwe9-5f0dssa8g7d8"
Last-Modified: Wed, 21 Oct 2023 07:28:00 GMT

3. 混合策略示例

text
Cache-Control: max-age=600, must-revalidate

该配置表示:

  • 600 秒内使用强缓存
  • 超过有效期后必须向服务器验证

4. 现代缓存策略最佳实践

资源类型推荐策略示例配置
带 hash 文件长期强缓存max-age=31536000, immutable
HTML 文档协商缓存no-cache
API 响应短时效缓存max-age=60, private
敏感数据禁用缓存no-store, must-revalidate

4. 缓存验证的数学原理

当使用 ETag 验证时,服务器通过哈希算法生成资源标识:

ETag=Hash(Content+Metadata)\rm ETag = Hash(Content + Metadata)

客户端后续请求携带:

IfNoneMatch:"HashValue"\rm If-None-Match: "HashValue"

服务器比较哈希值:

{Hashserver=Hashclient304HashserverHashclient200+NewETag\begin{cases} \rm Hash_{server} = Hash_{client} & \Rightarrow 304 \\ \rm Hash_{server} \neq Hash_{client} & \rm \Rightarrow 200 + New-ETag \end{cases}

5. 特殊场景处理

  1. 强制刷新机制Ctrl+F5 强制刷新会添加 Cache-Control: no-cache 请求头,绕过所有缓存

  2. Vary 头的影响 当响应包含 Vary: User-Agent 时,不同 UA 的请求会创建独立缓存副本

  3. Service Worker 优先级 Service Worker 的缓存拦截优先级高于传统 HTTP 缓存机制

javascript
// Service Worker 缓存拦截示例
self.addEventListener('fetch', event => {
  event.respondWith(
    caches.match(event.request)
      .then(response => response || fetch(event.request))
  );
});

理解这些缓存机制可以帮助开发者:

  • 减少 40%-60% 的重复资源请求
  • 降低服务器带宽消耗约 30%
  • 提升页面加载速度 50% 以上(根据 Google 性能报告)