求生之路2选地图:基于HTTP协议WEB系统优化

来源:百度文库 编辑:中财网 时间:2024/05/03 13:05:19

        

 

    HTTP1.0 和 HTTP1.1 协议最主要的区别是HTTP1.1协议增加了会话保留时间(Keep-Alive),也就是会话完系统并不会立即关闭连接,他会保留一段时间,也就是apache nginx 或者 squid ….. 设置的Keep-Alive时间,这样如果在这个时间内客户端再次向服务器发出请求时,服务器和客户端就不需要再次进行TCP3次握手和重新连接.这样就加快了打开速度,但是如果话保留时间(Keep-Alive)设置太长就会使得服务器内存大量消耗系统压力也加大,太短也就没发挥HTTP1.1 协议的优点,这个是个取舍的问题,需要根据自己的需求设置,如果服务器访问量小设置大点没关系,如果访问量大就设置小点.

        因为以前没有很好的理解这点,我的nginx服务器和squid服务器就出现了效率很差的经历.nginx 10G内存 squid 6G内存,这两台服务器每天承受大概20万IP左右的访问量,PV多时接近400万,nginx服务器流量大概是50M每秒,squid流量大概是20M每秒,开始我设置nginx会话保留时间(Keep-Alive)为60秒, keepalive_timeout 60; 运行了一段时间发现8个nginx子进程越来越大,基本每个子进程都有70多M,活动连接也基本都是维持在1W以上,Cacti查看服务器压力也是很不理想,想起以前apache优化经验,把 keepalive_timeout 15; 后.立竿见影,服务器活动连接直接少了一半,nginx子进程也一下子降到30多M,nginx是好了,但squid还是不理想,当时我也没想到squid 有会话保留时间(Keep-Alive)的设置,因为squid服务器响应都是以HTTP1.0 响应,就以为没得HTTP1.1协议的会话保留时间(Keep-Alive)设置,squid服务器速度一直不理想,squidclient -h localhost -p 80 mgr:info查看了下squid运行情况,命中率还是理想,但下面的值就非常大,我查看过CCTV YOUKU 人民网,他们的这个值基本都维持在1000左右,我的squid肯定有问题,当时我也不知道怎么处理.就一直搁在那.

Maximum number of file descriptors:   51200
Largest file desc currently in use:     13776
Number of file desc currently in use:   10682

 

一天在看网上一篇博客的时候发现博客里面说squid也可以是设置会话保留时间(Keep-Alive),具体如下:

client_persistent_connections on
server_persistent_connections on
persistent_request_timeout 30 seconds

 

persistent_request_timeout这个值也就相当于keepalive_timeout时间,查看了squid默认配置文档,发现默认是2分钟,看到这我想我的squid问题在哪了,我赶紧把这段加上时间设置15秒,活动连接也立即减半,Number of file desc currently in use这个也减到2000千左右,squid也快了起来.终于解决了squid问题.

 

觉得这还不够,开始重视根据HTTP协议优化WEB服务器,后来经过发现还有要优化的,最典型的就是网站文件过期时间(expires)和gzip.分析过国内外很多大网站,他们对这两项都有明显的设置,最难理解的就是squid是否缓存gzip文件.头疼了我3天,睡觉都一直再想这个问题.折腾了4天终于理清了思路,发表下我的看法.

 

 

 

这图是我用IE6打开http://www.163.com/然后用 ieHTTPHeaders 工具抓到的http会话头.这个过程很简单,开始IE6浏览器发送了个GET请求,告诉服务器我要得到index.html里面的内容,用的 HTTP/1.1 协议,并且  支持gzip(Accept-Encoding: gzip, deflate); 然后服务器回应IE6的请求,从这图可以看明显的看出,服务器是以HTTP1.0回应的,squid服务器用的是HTTP1.0协议,内容是gzip格式(Content-Encoding:gzip),从expires可以看出text/html文件过期时间是120秒,X-Cache: HIT from cache.163.com 这就可以说明index.html文件是从squid服务器获取的,并不是MISS,如果MISS说明是从源端nginx服务器获取的文件.

 

先说设置expires的好处,如果第一次打开网站,IE会把网站文件下载保存到 C:\Documents and Settings\Administrator\Local Settings\Temporary Internet Files 这个文件夹,第二次打开网站的时候,
如果这个文件夹的文件没过期就不要去服务器下载,而是直接调用本地文件,速度就非常快,从这个过程也就可以理解设置这个参数的好处,如果没过期就不去服务器下载了,这样既节约了带宽也减小了系统压力,也加快了速度,图片 JS CSS HTML 文件他们具体过期时间设置有区别,具体的可以去分析下大网站,最后说下商城网站不要缓存HTML文件,要不然购物车会显示不了商品,要刷新才能看到.具体我也解释不了.

expires和squid里面的refresh_pattern参数也有一定的关系,下面这句是我从squid权威手册复制过来的,很明显的说明,如果源端服务器设置了expires,refresh_pattern就不起作用,以前好像也听别人说过.

refresh_pattern规则仅仅应用到没有明确过时期限的响应,原始服务器能使用Expires头部,或者Cache-Control:max-age指令来指定过时期限.

 


最后说下gzip, nginx apache 开启gzip我就不详细说明,google下就知道了

nginx 开启gzip

      gzip on;

#  gzip_static on;

  gzip_min_length  1k;

  gzip_proxied   any;

  gzip_buffers     4 8k;

  gzip_http_version 1.0;

  gzip_vary on;

  add_header Vary Accept-Encoding;

  gzip_types       text/plain application/x-javascript text/css application/xml;

,gzip主要是压缩网站文件节约带宽和加快访问速度,小网站不要这个也可以. nginx后端 squid是否会缓存gzip文件这个问题折腾了我4天,不知道是我笨还是没找到理解的方法.apache后端是可以缓存的,最终还是被我理解了.总结了下:

 

如果要gzip ,nginx后端 要 gzip_http_version 1.0; 如果后端NGINX 设置了 gzip_vary on 或者add_header Vary Accept-Encoding ,squid要设置 cache_vary on ,否则不缓存gzip文件.squid默认配置文档是这么说的,如果cache_vary off 则不缓存.

squid3 已经没有了cache_vary 这个参数,如果要支持gzip压缩要加上以下配置.如果少了部分可能会导致gzip文件不缓存.

 

request_header_access Allow allow all
request_header_access Authorization allow all
request_header_access WWW-Authenticate allow all
request_header_access Proxy-Authorization allow all
request_header_access Proxy-Authenticate allow all
request_header_access Cache-Control allow all
request_header_access Content-Encoding allow all
request_header_access Content-Length allow all
request_header_access Content-Type allow all
request_header_access Date allow all
request_header_access Expires allow all
request_header_access Host allow all
request_header_access If-Modified-Since allow all
request_header_access Last-Modified allow all
request_header_access Location allow all
request_header_access Pragma allow all
request_header_access Accept allow all
request_header_access Accept-Charset allow all
request_header_access Accept-Encoding allow all
request_header_access Accept-Language allow all
request_header_access Content-Language allow all
request_header_access Mime-Version allow all
request_header_access Retry-After allow all
request_header_access Title allow all
request_header_access Connection allow all
request_header_access Proxy-Connection allow all
request_header_access All deny all

 

这段的发现过程: 在2.7以下是可以支持gzip,网易squid3也支持gzip,而我自己的改成了 gzip_http_version 1.0,还是不支持gzip,仔细想想,很明显是发给squid服务器的get头,部分信息被squid过滤掉了,所以我去squid默认配置文档找这段允许所有请求头.测试下结果还真支持gzip了.

 

至于nginx为什么要设置 gzip_vary on 或者 add_header Vary Accept-Encoding.网上是这么说:

 

squid只支持gzip的静态压缩,不支持动态压缩。具体一点说,就是response header里必须有content-length, 不可以用chunked方式。nginx默认的NginxHttpGzipModule, 采用的是chunked方式的动态压缩,而squid是不支持的。需要使用http_gzip_static_module这个模块,进行pre-compress,编译的时候要加上–with-http_gzip_static_module.这个问题大家可以参考下:

 

http://sudone.com/nginx/nginx_gzip_squid.html

http://bbs.chinaunix.net/archiver/?tid-1453195.html

 

我的测试过程:

curl.exe  --header "Accept-Encoding: gzip, deflate"  -D 1.txt -0 1.txt -0 http://www.t

curl.exe  --header "Accept-Encoding: gzip, deflate"  -D 1.txt -0 http://abc.com/index.html

curl.exe  --header "Accept-Encoding: gzip, deflate"  -D 2.txt http://abc.com/index.html

 

 http://www.360doc.com/mailto:root@Nginx:~# cat 1.txt
HTTP/1.0 200 OK
Content-Type: text/html
Content-Encoding: gzip
Server: nginx/0.8.14
Date: Sun, 18 Oct 2009 06:06:43 GMT
Last-Modified: Sat, 28 Nov 2009 02:02:10 GMT
Vary: Accept-Encoding
Age: 3414022
Content-Length: 4471
X-Cache: HIT from cache.abc.cn
X-Cache-Lookup: HIT from cache.abc.cn:80
Connection: close

 

上面那条命令是给服务器发了个 HTTP1.0 支持gzip 的GET方法,这时服务器就会回应个gzip压缩内容,然后把HTTP头保存到 1.txt .如果服务器返回的内容是乱码就说明,index.html gzip了,不是乱码就说明没gzip,测试是否能缓存gzip文件,主要看http头,cat 下1.txt .第一次肯定是 X-Cache: MISS from cache.abc.com ,因为第一次squid服务器没有缓存index.html,如果你再次运行下这条命令,再查看下1.txt,他就会是 X-Cache: HIT from cache.abc.com ,如果是hit就说明了是从squid获取的文件,说明squid已经缓存了index.html.

 

下面这条命令就是以 HTTP1.1 方式向服务器发送GET请求,效果和第一条差不多.(其实不管你是用HTTP1.0还是1.1协议发GET请求,squid服务器都是以HTTP1.0响应)

 

测试结果:(环境是squid2.7 nginx0.8.14)

Nginx 没设置 gzip_http_version 1.0;

 

上面两条命令运行的结果都相同,得到的内容都不是乱码,说明index.html没被gzip;这我的理解是因为squid是以HTTP1.0响应的,不支持nginx默认的gzip_http_version 1.1.所以gzip不了.

 

Nginx 设置了 gzip_http_version 1.0;

 

 上面两条命令运行的结果也相同,得到的内容是乱码,说明index.html gzip了, 第2次运行命令的时候发现 X-Cache 都是HIT,说明squid缓存了gzip文件.