用Nginx作为反向代理服务器进行前端缓存

之前写过用Varnish作为前端承载服务器的文章,不可否认的是,Varnish纯内存缓存的效率绝对超过任何其他缓存服务器,但是Varnish的作者有点洁癖,不肯增加HTTPS支持,在现今看来,确实有点跟不上时代了。

首先需要明确的是,其实最佳方案是Varnish和Nginx各自负责http和https的流量,这样是效率最大化的。我之前一直比较反感Nginx,是因为这货被人称道的优点我全都用不上,而他的缺点却会让我很麻烦。今天折腾他是因为有几个节点需要单独作为文件下载用,所以用他,比较简单一点,也节约内存。

 

安装就不多说了,各个平台的流程大同小异,我用Debian 8,几行命令即可:

echo "deb http://nginx.org/packages/debian/ jessie nginx" >> /etc/apt/sources.list
echo "deb-src http://nginx.org/packages/debian/ jessie nginx" >> /etc/apt/sources.list
wget http://nginx.org/keys/nginx_signing.key
apt-key add nginx_signing.key
apt-get update
apt-get install nginx

 

我这是把官方给的源加入系统列表,那么直接可以安装官方提供的最新稳定版。个人比较反感源代码编译。

首先创建缓存目录:

mkdir /usr/share/nginx/cache_dir

因为这个目录是我指定在这里,所以需要手工创建。

然后先把默认配置给关掉:

mv /etc/nginx/conf.d/default.conf /etc/nginx/conf.d/default.conf.bak

接着编辑一下全局配置文件:

nano /etc/nginx/nginx.conf

我记不清改过那些了,直接贴内容吧,我的配置文件内容:

#运行用户
user nginx;
#启动进程,通常设置成和cpu的数量相等
worker_processes  1;

#全局错误日志及PID文件
error_log  /var/log/nginx/error.log warn;
pid        /var/run/nginx.pid;


#工作模式及连接数上限
events {
    #epoll是多路复用IO(I/O Multiplexing)中的一种方式,
    #仅用于linux2.6以上内核,可以大大提高nginx的性能
    use   epoll; 

    #单个后台worker process进程的最大并发连接数    
    worker_connections  1024;

    # 并发总数是 worker_processes 和 worker_connections 的乘积
    # 即 max_clients = worker_processes * worker_connections
    # 在设置了反向代理的情况下,max_clients = worker_processes * worker_connections / 4  为什么
    # 为什么上面反向代理要除以4,应该说是一个经验值
    # 根据以上条件,正常情况下的Nginx Server可以应付的最大连接数为:4 * 8000 = 32000
    # worker_connections 值的设置跟物理内存大小有关
    # 因为并发受IO约束,max_clients的值须小于系统可以打开的最大文件数
    # 而系统可以打开的最大文件数和内存大小成正比,一般1GB内存的机器上可以打开的文件数大约是10万左右
    # 我们来看看360M内存的VPS可以打开的文件句柄数是多少:
    # $ cat /proc/sys/fs/file-max
    # 输出 34336
    # 32000 < 34336,即并发连接总数小于系统可以打开的文件句柄总数,这样就在操作系统可以承受的范围之内
    # 所以,worker_connections 的值需根据 worker_processes 进程数目和系统可以打开的最大文件总数进行适当地进行设置
    # 使得并发总数小于操作系统可以打开的最大文件数目
    # 其实质也就是根据主机的物理CPU和内存进行配置
    # 当然,理论上的并发总数可能会和实际有所偏差,因为主机还有其他的工作进程需要消耗系统资源。
    # ulimit -SHn 65535

}


http {
    #设定mime类型,类型由mime.type文件定义
    include    /etc/nginx/mime.types;
    default_type  application/octet-stream;
    #设定日志格式
    log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                      '$status $body_bytes_sent "$http_referer" '
                      '"$http_user_agent" "$http_x_forwarded_for"';


    access_log  /var/log/nginx/access.log main;

    #sendfile 指令指定 nginx 是否调用 sendfile 函数(zero copy 方式)来输出文件,
    #对于普通应用,必须设为 on,
    #如果用来进行下载等应用磁盘IO重负载应用,可设置为 off,
    #以平衡磁盘与网络I/O处理速度,降低系统的uptime.
    sendfile     on;
    #tcp_nopush     on;

    #连接超时时间
    #keepalive_timeout  0;
    keepalive_timeout  120;
    tcp_nodelay     on;

# 开启gzip
gzip on;
# 启用gzip压缩的最小文件,小于设置值的文件将不会压缩
gzip_min_length 1k;
# gzip 压缩级别,1-10,数字越大压缩的越好,也越占用CPU时间,后面会有详细说明
gzip_comp_level 2;
# 进行压缩的文件类型。javascript有多种形式。其中的值可以在 mime.types 文件中找到。
gzip_types text/plain application/javascript application/x-javascript text/css application/xml text/javascript application/x-httpd-php image/jpeg image/gif image/png;
# 是否在http header中添加Vary: Accept-Encoding,建议开启
gzip_vary on;
# 禁用IE 6 gzip
gzip_disable "MSIE [1-6]\.";

    #设定请求缓冲
#    client_header_buffer_size    128k;
#    large_client_header_buffers  4 128k;


#server_names_hash_bucket_size 128; #服务器名字的hash表大小
#proxy_headers_hash_max_size 51200; #设置头部哈希表的最大值,不能小于你后端服务器设置的头部总数
#proxy_headers_hash_bucket_size 6400;#设置头部哈希表大小


include /etc/nginx/conf.d/*.conf;

}

有些调试用的我注释掉了,还有性能方面我这暂时没发现瓶颈,你可以根据情况调整。

具体include的路径么,各个系统不太相同,各位要根据自己系统调整,我的文件只确保在Debian 8上面正常运行。

最后就是站点配置文件了,路径为/etc/nginx/conf.d/default.conf,不一定非要用default.conf,只要在这个目录里面的conf文件就可以。

我这的配置:

#levels设置目录层次 
#keys_zone设置缓存名字和共享内存大小 
#inactive在指定时间内没人访问则被删除在这里是1天 
#max_size最大缓存空间

proxy_cache_path  /usr/share/nginx/cache_dir/tingtao  levels=2:2 keys_zone=tingtao:100m inactive=1d max_size=2g;
proxy_cache_path  /usr/share/nginx/cache_dir/tingtaoit  levels=2:2 keys_zone=tingtaoit:10m inactive=1d max_size=500m;

proxy_cache_key $scheme$host$request_uri;

proxy_connect_timeout       600;
proxy_send_timeout          600;
proxy_read_timeout          600;
send_timeout                600;
proxy_buffers 256 16k;
proxy_buffer_size 32k;

add_header Cache-Control public;
add_header X-Cache-Status $upstream_cache_status;


upstream web_http {
        server 1.1.1.1:80;
    }

upstream web_http_ssl {
        server 1.1.1.1:443;
    }


################################################
#              old.tingtao.org

server {
        listen          80;
        server_name     old.tingtao.org;
        keepalive_timeout    120;
        
        ##############################################
        
    		access_log off;
                proxy_set_header   Host $host;
    		proxy_set_header   X-Real-IP $remote_addr;
    		proxy_set_header   X-Forwarded-For  $proxy_add_x_forwarded_for;
        

       #   不缓存的文件和路径
        location ~ (wp-admin|\.php)$ {
        		proxy_pass http://web_http;
    	    proxy_no_cache 1;
            proxy_cache_bypass 1;
   		 }

       #     默认的缓存策略
        location / {
    						proxy_cache             tingtao;
                proxy_pass  http://web_http;
                proxy_redirect off;
                
                proxy_cache_valid 200 302 301 1d;                              #对不同的HTTP状态码设置不同的缓存时间,h小时,d天数  
                proxy_cache_valid any 1m;
    						proxy_cache_use_stale   error timeout invalid_header;
     }
}


server {
        listen          443 ssl;
        server_name     old.tingtao.org;
 
        ssl_certificate      /var/www/ca/old.tingtao.org/Nginx/1_old.tingtao.org_bundle.crt;
        ssl_certificate_key  /var/www/ca/old.tingtao.org/Nginx/2_old.tingtao.org.key;
        keepalive_timeout    120;
        
    						access_log off;
                proxy_set_header   Host $host;
    						proxy_set_header   X-Real-IP        $remote_addr;
    						proxy_set_header   X-Forwarded-For  $proxy_add_x_forwarded_for;

        

       #   不缓存的文件
        location ~ (wp-admin|\.php)$ {
        		proxy_pass https://web_http_ssl;
    	      proxy_no_cache 1;
            proxy_cache_bypass 1;
   		 }

       #     默认的
        location / {
    						proxy_cache             tingtao;
                proxy_pass  https://web_http_ssl;
                proxy_redirect off;
                
                proxy_cache_valid 200 302 301 1d;                              #对不同的HTTP状态码设置不同的缓存时间,h小时,d天数  
                proxy_cache_valid any 1m;
    						proxy_cache_use_stale   error timeout invalid_header;
     }
}

        #默认站点
    server {
        listen    80  default;
        server_name  www.tingtao.org;

        #定义服务器的默认网站根目录位置
        root /var/www/re.haote.net;

        #默认请求
        location / {
            #定义首页索引文件的名称
            index index.html index.php index.htm;
        }

        # 定义错误提示页面
        error_page 404 = http://re.haote.net/index.html;

        #禁止访问 .htaxxx 文件
            location ~ /.hta {
            deny all;
        }

}

 

简单说明一下:

1,文件中有3个站点,分别是old.tingtao.org的http和https,以及一个默认站点。默认站点不是必须的。默认站点的listen里需要有“default”关键字。

2,location ~ (wp-admin|\.php)$ 这个条件对于wordpress站点来说其实意义不大,这里只是为了举个例子。怎样可以只用一行就定义多个文件名+路径的形式,我看了很多人写的文章,都没这种写法,明明一段搞定的事情,非要折腾一屏幕……

我个人觉得,对于缓存服务器来说,无非就是缓存和不缓存两种情况,当然有些网站可能需要更细致的根据文件类型设置不同的缓存周期,或者根据不同路径丢到不同的后端服务器,这类需求照着修改就是了,比葫芦画瓢的事情不再多说。

3,实际上不论一个站点是http还是https,都可以从https/http两种后端请求内容,也就是说,http站点也可以从https的后端请求内容,反过来亦可。因为严格界定的话,其实缓存服务器可以理解为“中间人攻击”的一种,哈哈。

那么,也就是说,如果你灵活运用的话,只需要在我的配置文件里面增加一点点rewrite内容就可以实现一个http后端,衍生出http+https的前端。

4,proxy_cache tingtao;这行里面的tingtao对应着顶部的存储区配置,我复制了一点说明,对照修改即可。

5,add_header X-Cache-Status $upstream_cache_status;这一行是增加一个http响应头,方便调试缓存状态。

6,Nginx应该算是内存+硬盘缓存的,更深入的缓存调整细节还是仔细看看文档比较靠谱。Nginx和Varnish都不能取代对方,他们的适用场景不同:

如果配置牛B,内存大,并且是纯http,那用Varnish绝对飞起来;

如果配置差一些,内存小,硬盘大而且是SSD盘,那么Nginx会经济一些;

如果配置差,内存小,还硬盘差,那你最好别用缓存服务器了,这玩意不适合你,硬上的话只会让你的网站更慢 :mrgreen:

 

其他的想起来再补充吧。

Share

您可以选择一种方式赞助本站

微信钱包扫描赞助

发表评论

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

图片 表情