2

我工作的一位架构师最近阅读了Yahoo! 的 Exceptional Performance Best Practices指南,其中说要为页面使用的资源(如 JavaScript、CSS 和图像)使用一个遥远的 Expires 标头。这个想法是你为这些资源在未来几年设置一个 Expires 标头,这样它们总是被浏览器缓存,每当我们更改文件并因此需要浏览器再次请求资源而不是使用它的缓存时,更改文件名通过添加版本号。

不过,他没有将其纳入我们的构建过程,而是有另一个想法。我们不会为每个构建更改源文件和服务器磁盘上的文件名(当然,这会很乏味),我们将伪造它。他的计划是在所述资源上设置远期过期,然后实现两个 HttpModule。

一个模块将在我们的 ASPX 和 HTML 页面发出之前拦截所有响应流,查找资源链接并添加版本参数,即文件的最后修改日期。另一个 HttpModule 将处理所有对资源的请求,并简单地忽略地址的版本部分。这样,浏览器每次在磁盘上发生更改时总是会请求一个新的资源文件,而实际上不必更改磁盘上文件的名称。

说得通?

我的担忧与重写 ASPX/HTML 页面响应流的模块有关。<script>他只是要在标签的“src”属性和<img>标签的“href”属性上应用一堆Regex.Replace() <link>。对于内容类型为“text/html”的服务器上的每个请求,都会发生这种情况。可能每分钟数百或数千。

我知道 HttpModules 被挂接到 IIS 管道中,但这必须在 IIS 发送 HTTP 响应所需的时间上增加一个令人望而却步的延迟。不?你怎么看?

4

3 回答 3

1

需要注意的几点:

  1. 如果想法是在静态文件名中添加查询字符串以指示其版本,不幸的是,这也会阻止内核模式 HTTP 驱动程序 (http.sys) 进行缓存
  2. 基于一堆正则表达式扫描每个完整的响应会很慢,很慢,很慢。它也可能不可靠,有难以预测的极端情况。

几种选择:

  1. 使用控制适配器将某些 URL 或路径显式替换为当前版本。这使您可以专注于图像、CSS 等。
  2. 版本静态文件时更改文件夹名称而不是文件名
  3. 考虑使用 ASP.NET 外观来帮助集中文件名。这将有助于简化维护。

如果有帮助,我会在我的书 ( Ultra-Fast ASP.NET ) 中介绍这个主题,包括代码示例。

于 2009-11-18T02:35:24.483 回答
0

他担心没有缓存在客户端上的东西——显然这在一定程度上取决于用户群体如何配置他们的浏览器;如果它是默认配置,那么我怀疑您是否需要担心尝试第二次猜测客户端缓存,这太难了,并且无法保证结果,也不会帮助新用户。

就 HTTP 模块而言 - 原则上我会说它们很好,但如果你走这条路,你会希望它们变得非常快速和高效;这可能值得一试。不过,我不能谈论使用 RegEx 来做你想做的事情的适当性。

如果您正在寻找高性能,我建议您(或您的架构师)做一些阅读(我并不是以讨厌的方式)。我最近学到了一些我认为会有所帮助的东西——让我解释一下(也许你们已经知道了)。

浏览器在任何时候只能保持有限数量的同时打开到特定主机名的连接。例如,IE6 只会做 6 个连接到 www.foo.net。

如果您从 images.foo.net 中调用您的图像,您将立即获得 6 个新连接。这个想法是将不同的内容类型分离成不同的主机名(css.foo.net、scripts.foo.net、ajaxcalls.foo.net),这样您就可以确保浏览器真正代表您工作。

于 2009-11-18T02:18:11.650 回答
0

http://code.google.com/p/talifun-web

StaticFileHandler - 以可缓存、可恢复的方式提供静态文件。CrusherModule - 以可缓存的方式提供压缩版本的 JS 和 CSS。

您并没有完全获得内核模式缓存速度,但从 HttpRuntime.Cache 提供服务有其优势。内核模式缓存无法缓存部分响应,并且您没有对缓存的细粒度控制。要实现的最重要的事情是一致的 etag 标头和 expires 标头。这将比其他任何事情都更能提高您的网站性能。

减少提供的文件数量可能是提高网站速度的最佳方法之一。CrusherModule 将您网站上的所有 css 合并到一个文件中,并将所有 js 合并到另一个文件中。

内存便宜,硬盘慢,所以用吧!

于 2010-02-18T15:13:05.803 回答