2012-07-31 45 views
3

我们有几个文件通过HTTP提供服务,并且会随时更改。哪些是可以更改内容的最佳缓存相关HTTP标头?

哪些是与缓存相关的HTTP标头,我们应该在HTTP响应中返回以优化浏览器加载速度,同时强制浏览器验证它是否具有文件的最新版本?

我们已经设置了过期日期的“过期”标题(似乎此时已达成共识)。

但后来有人建议设置这个头:

Cache-Control: no-cache, no-store, must-revalidate 

但与此头的问题是,它可以防止浏览器保持文件的本地副本,因此文件被下载每次,甚至如果它没有改变,用200响应代码。

如果我只是用:

Cache-Control: no-cache 

然后,浏览器(至少火狐14和Chrome 20)保留一个本地副本,发送If-Modified-SinceIf-None-Match头,服务器返回一个304码和文件内容没有下载。 这是可随时更改这些文件的最佳行为。

问题是,我不知道设置“no-cache”是否足以强制所有浏览器(包括旧的,但仍然使用的版本)和代理服务器重新验证其本地缓存副本与服务器。

最后,Pragma: no-cache头怎么样?它是否也应该包含在HTTP响应中呢?

+0

如果您有答案,您应该自己写答案并将其标记为答案,而不是在问题中以粗体添加陈述。 – 2016-03-27 01:50:51

+0

@AlexisWilke大胆的陈述不是我的问题的答案,这只是我想强调的一点。 – 2016-03-29 08:56:52

回答

1

的最好办法,也许不是100%适合您的需求是:

Cache-Control:max-age=315360000, public 
Expires:Tue, 23 Aug 2022 10:53:13 GMT 

,并为文件“内容有关的文件名”,如stylesheet_v32.css。 只要内容发生变化,请将文件名+引用更改为,然后浏览器获取最新版本。如果文件名保持不变,浏览器不需要请求它。

这是安全的,贯穿整个浏览器。

依靠Cache-Control: no-cache和无论如何保存它的浏览器是我不想做的事情。

3

Google开发人员文档有一个nice documentation on caching,并提供了一些很好的使用模式。

例如,它具有用于定义最佳缓存控制策略的流程图。

enter image description here

此外,它一个很好的模式,以指纹添加到文件,并设置较长时间到期定义如一年。

  • 本地缓存响应使用,直到资源“到期”
  • 嵌入URL中的文件内容指纹使我们强制客户端更新到响应
  • 每个应用程序的新版本需要定义自己的缓存层次结构以获得最佳性能

enter image description here

定义每个资源的缓存策略的能力,使我们能够 定义“缓存层次结构”,使我们能够控制每个不仅多久 缓存,又是如何迅速的新版本由 访问者所看到。例如,我们来分析一下上面的例子:

  • 的HTML标记为“无缓存”,这意味着浏览器将始终重新验证每个请求的文件,并获取 最新版本,如果内容的变更。此外,在HTML标记 中,我们在CSS和JavaScript资源的URL中嵌入了指纹:如果 这些文件的内容发生更改,那么页面的HTML将更改为 ,并且HTML响应的新副本将为 已下载。
  • CSS允许被浏览器和中间缓存(例如CDN)缓存,并且设置为在1年内到期。请注意,我们可以安全地使用
    1年的“远期到期”,因为我们将文件
    指纹文件的文件名嵌入:如果CSS已更新,则URL也将更改为
  • JavaScript也设置为在1年内到期,但被标记为私有,可能是因为它包含一些私人用户数据,CDN不应该缓存。
  • 图像缓存时没有版本或唯一的指纹,并且设置为在1天内过期。

ETag的,缓存控制,以及独特的URL的结合使我们能够 提供世界上最好的:长寿命到期时间,控制 其中响应可以缓存,并按需更新

+0

还有[另一个来自Google的文档](https://developers.google.com/web-toolkit/doc/latest/DevGuideCompilingAndDebugging#perfect_caching),这是反向的。在这篇文档中,他们推荐'Cache-Control:public,max-age = 0,must-revalidate'而不是'Cache-Control:no-cache'用于可随时改变的内容。 – 2016-03-29 08:58:10

+0

请注意,'ETag'可能会导致Firefox出现“问题”,因为它似乎总是重新检查数据,即使您的缓存持续时间大于零。因此,版本化的文件(如CSS和JS文件)不应使用“ETag”。 – 2016-03-29 22:03:07

0

我发现了两种方式由客户端强制缓存重新检查:

Cache-Control: max-age=0, must-revalidate 
Expires: Thu, 01 Jan 1970 00:00:00 GMT 

这适用于至少Firefox浏览器。我会想象IE和Chrome也会做出正确的反应。它应该使用HTTP/1.0的旧版浏览器。

使用HTTP 1.1,您可以使用ETag。在这种情况下,must-revalidate选项是没有必要的,因为具有ETag是足以让客户反应,就像must-revalidate在那里:

Cache-Control: max-age=0 
ETag: 123 
Expires: Thu, 01 Jan 1970 00:00:00 GMT 

这将告诉客户端来创建数据的高速缓存版本ETag 123每次需要该数据的副本时重新检查服务器。然后您可以回复304 Not Modified

确切无法使用的两个选项是:no-cacheno-store

如果要防止中间缓存缓存数据,请确保将private添加到Cache-Control选项。

作为一个有趣的功能,您还可以使用一个小的最大年龄,例如几分钟,让客户端缓存该数据的时间,然后发送一个GET,您可以用304

Cache-Control: max-age=300 
ETag: 123 
Expires: Tue, 29 Mar 2015 15:05:00 GMT 

在这种情况下,浏览器有望不检查新数据5分钟。之后,它发送给您If-None-Match: 123

相关问题