---

title: ETag强弱校验与缓存一致性治理(W/前缀/条件请求)最佳实践

keywords:

  • ETag
  • 条件请求
  • If-None-Match
  • 强/弱ETag
  • 一致性

description: 通过强/弱ETag策略与条件请求校验、统一生成规则与变更策略,保障缓存一致性与减少不必要传输。

categories:

  • 文章资讯
  • 编程技术

---

背景与价值

ETag允许客户端进行条件请求与缓存验证。合理生成与校验可减少传输并保持一致性。

统一规范

  • 弱ETag:使用 W/"..." 对内容近似变化使用弱校验。
  • 强ETag:对内容完全一致使用强校验。
  • 条件请求:支持 If-None-Match 与304响应。

核心实现

ETag生成与校验

function b64url(buf: ArrayBuffer): string { const u = new Uint8Array(buf); let s=''; for (let i=0;i<u.length;i++) s+=String.fromCharCode(u[i]); return btoa(s).replace(/\+/g,'-').replace(/\//g,'_').replace(/=+$/,'') }

async function etagWeak(body: ArrayBuffer): Promise<string> { const d = await crypto.subtle.digest('SHA-256', body); return 'W/"' + b64url(d) + '"' }
async function etagStrong(body: ArrayBuffer): Promise<string> { const d = await crypto.subtle.digest('SHA-256', body); return '"' + b64url(d) + '"' }

function matchAny(inm: string | undefined, tag: string): boolean { const s = (inm || '').split(',').map(t => t.trim()); return s.includes(tag) }

条件请求响应

type Req = { headers: Record<string, string | undefined> }
type Res = { setHeader: (k: string, v: string) => void; status: (n: number) => Res; end: (b?: any) => void }

async function serve(body: ArrayBuffer, req: Req, res: Res, weak = true) {
  const tag = weak ? await etagWeak(body) : await etagStrong(body)
  res.setHeader('ETag', tag)
  const inm = req.headers['if-none-match']
  if (matchAny(inm, tag)) return res.status(304).end()
  res.end(body)
}

落地建议

  • 为静态与动态资源分别选择强/弱ETag并支持条件请求,减少带宽并保持一致性。
  • 与缓存策略协同(Cache-Control/immutable)实现高效验证与长效缓存。

验证清单

  • 是否生成并下发强/弱ETag;条件请求命中是否返回304。

点赞(0) 打赏

评论列表 共有 0 条评论

暂无评论
立即
投稿

微信公众账号

微信扫一扫加关注

发表
评论
返回
顶部