1.Use a Content Delivery Network
使用内容分发网络
http://developer.yahoo.com/performance/rules.html#cdn
按地域布置网站内容的第一步并不是要尝试重新架构你的网站让他们在分发服务器上正常运行。根据应用的需求来改变网站结构,这可能会包括一些比较复杂的任务,如在服务器间同步Session状态和合并数据库更新等。要想缩短用户和内容服务器的距离,这些架构步骤可能是不可避免的。
要记住,在终端用户的响应时间中有80%到90%的响应时间用于下载图像、样式表、脚本、Flash等页面内容。这就是网站性能黄金守则。和重新设计你的应用程序架构这样比较困难的任务相比,首先来分布静态内容会更好一点。这不仅会缩短响应时间,而且对于内容分发网络来说它更容易实现。
2.Add an Expires or a Cache-Control Header
为文件头指定Expires或Cache-Control
http://developer.yahoo.com/performance/rules.html#expires
3.Gzip Components
Gzip压缩文件内容
http://developer.yahoo.com/performance/rules.html#gzip
Gzip是目前最流行也是最有效的压缩方式。这是由GNU项目开发并通过RFC 1952来标准化的。另外仅有的一个压缩格式是deflate,但是它的使用范围有限效果也稍稍逊色。
Gzip大概可以减少70%的响应规模。目前大约有90%通过浏览器传输的互联网交换支持gzip格式。如果你使用的是Apache,gzip模块配置和你的版本有关:Apache 1.3使用mod_zip,而Apache 2.x使用moflate。
浏览器和代理都会存在这样的问题:浏览器期望收到的和实际接收到的内容会存在不匹配的现象。幸好,这种特殊情况随着旧式浏览器使用量的减少在减少。 Apache模块会通过自动添加适当的Vary响应文件头来避免这种状况的出现。
服务器根据文件类型来选择需要进行gzip压缩的文件,但是这过于限制了可压缩的文件。大多数web服务器会压缩HTML文档。对脚本和样式表进行压缩同样也是值得做的事情,但是很多web服务器都没有这个功能。实际上,压缩任何一个文本类型的响应,包括XML和JSON,都值得的。图像和PDF文件由于已经压缩过了所以不能再进行gzip压缩。如果试图gizp压缩这些文件的话不但会浪费CPU资源还会增加文件的大小。
Gzip压缩所有可能的文件类型是减少文件体积增加用户体验的简单方法。
4.Configure ETags
配置ETag
http://developer.yahoo.com/performance/rules.html#etags
Entity tags(ETags)(实体标签)是web服务器和浏览器用于判断浏览器缓存中的内容和服务器中的原始内容是否匹配的一种机制(“实体”就是所说的“内容”,包括图片、脚本、样式表等)。增加ETag为实体的验证提供了一个比使用“last-modified date(上次编辑时间)”更加灵活的机制。Etag是一个识别内容版本号的唯一字符串。唯一的格式限制就是它必须包含在双引号内。原始服务器通过含有 ETag文件头的响应指定页面内容的ETag。
ETag的问题在于,它是根据可以辨别网站所在的服务器的具有唯一性的属性来生成的。当浏览器从一台服务器上获得页面内容后到另外一台服务器上进行验证时ETag就会不匹配,这种情况对于使用服务器组和处理请求的网站来说是非常常见的。默认情况下,Apache和IIS都会把数据嵌入ETag中,这会显著减少多服务器间的文件验证冲突。
Apache 1.3和2.x中的ETag格式为inode-size-timestamp。即使某个文件在不同的服务器上会处于相同的目录下,文件大小、权限、时间戳等都完全相同,但是在不同服务器上他们的内码也是不同的。
IIS 5.0和IIS 6.0处理ETag的机制相似。IIS中的ETag格式为Filetimestamp:ChangeNumber。用ChangeNumber来跟踪 IIS配置的改变。网站所用的不同IIS服务器间ChangeNumber也不相同。 不同的服务器上的Apache和IIS即使对于完全相同的内容产生的ETag在也不相同,用户并不会接收到一个小而快的304响应;相反他们会接收一个正常的200响应并下载全部内容。如果你的网站只放在一台服务器上,就不会存在这个问题。但是如果你的网站是架设在多个服务器上,并且使用Apache和 IIS产生默认的ETag配置,你的用户获得页面就会相对慢一点,服务器会传输更多的内容,占用更多的带宽,代理也不会有效地缓存你的网站内容。即使你的内容拥有Expires文件头,无论用户什么时候点击“刷新”或者“重载”按钮都会发送相应的GET请求。
如果你没有使用ETag提供的灵活的验证模式,那么干脆把所有的ETag都去掉会更好。Last-Modified文件头验证是基于内容的时间戳的。去掉ETag文件头会减少响应和下次请求中文件的大小。微软的这篇支持文稿讲述了如何去掉ETag。在Apache中,只需要在配置文件中简单添加下面一行代码就可以了:
FileETag none
5.Flush the Buffer Early
尽早刷新输出缓冲
http://developer.yahoo.com/performance/rules.html#flush
当用户请求一个页面时,无论如何都会花费200到500毫秒用于后台组织HTML文件。在这期间,浏览器会一直空闲等待数据返回。在PHP中,你可以使用flush()方法,它允许你把已经编译的好的部分HTML响应文件先发送给浏览器,这时浏览器就会可以下载文件中的内容(脚本等)而后台同时处理剩余的HTML页面。这样做的效果会在后台繁忙或者前台较空闲时更加明显。
输出缓冲应用最好的一个地方就是紧跟在<head />之后,因为HTML的头部分容易生成而且头部往往包含CSS和JavaScript文件,这样浏览器就可以在后台编译剩余HTML的同时并行下载它们。 例子:
... <!-- css, js -->
</head>
<?php flush(); ?>
<body>
... <!-- content -->
为了证明使用这项技术的好处,Yahoo!搜索率先研究并完成了用户测试。
Yahoo! search
http://search.yahoo.com/
6.Use GET for AJAX Requests
使用GET来完成AJAX请求
http://developer.yahoo.com/performance/rules.html#ajax_get
Yahoo! Mail团队发现,当使用XMLHttpRequest时,浏览器中的POST方法是一个“两步走”的过程:首先发送文件头,然后才发送数据。因此使用GET最为恰当,因为它只需发送一个TCP包(除非你有很多cookie)。IE中URL的最大长度为2K,因此如果你要发送一个超过2K的数据时就不能使用GET了。
一个有趣的不同就是POST并不像GET那样实际发送数据。根据HTTP规范,GET意味着“获取”数据,因此当你仅仅获取数据时使用GET更加有意义(从语意上讲也是如此),相反,发送并在服务端保存数据时使用POST。
HTTP specs
http://www.w3.org/Protocols/rfc2616/rfc2616-sec9.html
7.Avoid Empty Image src
避免空的图片地址
http://developer.yahoo.com/performance/rules.html#emptysrc
Image with empty string src attribute occurs more than one will expect. It appears in two form:
1.straight HTML
<img src="">
2.JavaScript
var img = new Image();
img.src = "";
Both forms cause the same effect: browser makes another request to your server.
?Internet Explorer makes a request to the directory in which the page is located.
?Safari and Chrome make a request to the actual page itself.
?Firefox 3 and earlier versions behave the same as Safari and Chrome, but version 3.5 addressed this issue[bug 444931] and no longer sends a request.
?Opera does not do anything when an empty image src is encountered.