陈旧响应可以在源站故障时维持公开手册的可读性,也可能保留过时价格、已撤销权限或误导性的状态。可用性并不天然高于正确性。启用这种行为之前,应先确定哪些信息允许继续使用、什么条件下可以复用,以及最多能旧多久,而不是看到一次错误响应就无条件拿旧成功结果代替。
历史 Node/http-cache-semantics 实验用虚构响应核对有界策略与调用方所选正文。年龄 35、89 可覆盖符合条件的错误,91 不行;失败不会重新开启窗口。离线通过不等于真实网络或故障测试,本图没有新增执行。 用可用性换新鲜度 过期和淘汰是两件事。过期响应仍可留在缓存里,用于条件验证或受到许可的陈旧响应;但冷缓存或已经淘汰条目的缓存,没有旧正文可返回。陈旧指令无法凭空创造副本,保存着字节也不会自动授予复用权限。选中的响应还必须匹配当前请求,包括相关 Vary 维度和访问边界,不能拿另一个请求留下的成功内容填补故障。
如何表示 stale-while-revalidate 允许在有界窗口内返回旧响应,同时尝试不阻塞该响应的验证。stale-if-error 则允许在尝试访问源站遭遇符合条件的错误时使用旧响应。两者触发条件不同,都不强制缓存保存内容,也不能保证每种缓存实现都支持。请求到达时若已越过允许窗口,不能因为之前有过一次许可,就继续无限期使用旧内容。
对于 max-age=30, stale-if-error=60,额外六十秒从新鲜期结束后开始计算,不是从每一次失败尝试重新开始。候选响应的总年龄窗口约为九十秒。RFC 5861 指定了会形成 500、502、503、504 的错误场景。认证失败或资源不存在,不能随手重新包装成可用性故障,再用旧的成功响应掩盖真正需要客户端看到的结果。
成功的条件验证不一定重新下载正文。三零四响应可以依据验证元数据更新存储响应,同时保留原来的表示字节。应把这种结果与替换正文的二百响应、故障期间的陈旧命中分别记录;三种情况可能显示相同页面,却对应不同的新鲜度依据,不能仅靠正文是否改变判断验证是否发生。
坏掉的样子 每次重验证失败后都把 Age 清零,会把有界例外变成无限陈旧。保留旧正文却刷新存储时间戳,也会造成同类错误。失败时应保留年龄;只有真正的新响应或成功验证,才提供更新新鲜度的依据。后台验证通常由流量触发,所以一个长期无人访问的缓存,不一定会在下一次用户访问之前主动把内容更新好。
只读或幂等并不代表可以安全返回旧内容。一个 GET 也可能涉及对时效敏感的权限或价格。RFC 9111 禁止在适用的 no-cache、must-revalidate 等指令不允许时复用陈旧响应。应避免互相矛盾的策略,并测试实际部署的缓存如何处理这些限制。另外,RFC 5861 中关于旧 Warning 字段的建议,已被废弃该字段的 RFC 9111 更新,不能把它当作当前验收必需项。
...