Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
2016-09-23 19:14
1011 查看
一、关于Nginx
nginx在启动后,在unix系统中会以daemon的方式在后台运行,后台进程包含一个master进程和多个worker进程。master进程主要用来管理worker进程,包含:接收来自外界的信号,向各worker进程发送信号,监控worker进程的运行状态,当worker进程退出后(异常情况下),会自动重新启动新的worker进程。
而基本的网络事件,则是放在worker进程中来处理了。
多个worker进程之间是对等的,他们同等竞争来自客户端的请求,各进程互相之间是独立的。
关于nginx,主要由3大模块,内核模块,事件模块,http核心模块。
nginx模块一般被分成三大类:handler、filter和upstream。
handler源码分析,可以去看 tengine的介绍 http://tengine.taobao.org/book/chapter_03.html
filter源码分析,可以去看 tengine的介绍 http://tengine.taobao.org/book/chapter_04.html
upstream源码分析,可以去看 tengine的介绍 http://tengine.taobao.org/book/chapter_05.html
Nginx开发从入门到精通
二、安装Nginx
1、安装yum源rpm -ivh http://download.fedoraproject.org/pub/epel/6/x86_64/epel-release-6[/code]
2、安装nginx
① gzip 模块需要 zlib 库 ( 下载: http://www.zlib.net/zlib-1.2.8.tar.gz )
② rewrite 模块需要 pcre 库 ( 下载: http://www.pcre.org/ 下载: ftp://ftp.csx.cam.ac.uk/pub/software/programming/pcre/pcre-8.37.tar.gz)
③ ssl 功能需要 openssl 库 ( 下载: http://www.openssl.org/source/openssl-fips-2.0.12.tar.gz )
④ Nginx包下载: http://nginx.org/download/nginx-1.9.13.tar.gz
依赖包安装顺序依次为:openssl、zlib、pcre, 然后安装Nginx包.[root@nginx ~]# yum install -y pcre-devel openssl-devel zlib-devel [root@nginx ~]# wget http://nginx.org/download/nginx-1.9.13.tar.gz [root@nginx ~]# tar -xvf nginx-1.9.13.tar.gz [root@nginx ~]#./configure --with-pcre=../pcre-8.21 --with-zlib=../zlib-1.2.7 --with-openssl=../openssl-fips-2.0.2 [root@nginx ~]#make && make install
3、为nginx提供SysV init脚本
cat /etc/init.d/nginx#!/bin/sh # # nginx - this script starts and stops the nginx daemon # # chkconfig: - 85 15 # description: Nginx is an HTTP(S) server, HTTP(S) reverse \ # proxy and IMAP/POP3 proxy server # processname: nginx # config: /etc/nginx/nginx.conf # config: /etc/sysconfig/nginx # pidfile: /var/run/nginx.pid # Source function library. . /etc/rc.d/init.d/functions # Source networking configuration. . /etc/sysconfig/network # Check that networking is up. [ "$NETWORKING" = "no" ] && exit 0 nginx="/usr/sbin/nginx" prog=$(basename $nginx) NGINX_CONF_FILE="/etc/nginx/nginx.conf" [ -f /etc/sysconfig/nginx ] && . /etc/sysconfig/nginx lockfile=/var/lock/subsys/nginx make_dirs() { # make required directories user=`nginx -V 2>&1 | grep "configure arguments:" | sed 's/[^*]*--user=\([^ ]*\).*/\1/g' -` options=`$nginx -V 2>&1 | grep 'configure arguments:'` for opt in $options; do if [ `echo $opt | grep '.*-temp-path'` ]; then value=`echo $opt | cut -d "=" -f 2` if [ ! -d "$value" ]; then # echo "creating" $value mkdir -p $value && chown -R $user $value fi fi done } start() { [ -x $nginx ] || exit 5 [ -f $NGINX_CONF_FILE ] || exit 6 make_dirs echo -n $"Starting $prog: " daemon $nginx -c $NGINX_CONF_FILE retval=$? echo [ $retval -eq 0 ] && touch $lockfile return $retval } stop() { echo -n $"Stopping $prog: " killproc $prog -QUIT retval=$? echo [ $retval -eq 0 ] && rm -f $lockfile return $retval } restart() { configtest || return $? stop sleep 1 start } reload() { configtest || return $? echo -n $"Reloading $prog: " killproc $nginx -HUP RETVAL=$? echo } force_reload() { restart } configtest() { $nginx -t -c $NGINX_CONF_FILE } rh_status() { status $prog } rh_status_q() { rh_status >/dev/null 2>&1 } case "$1" in start) rh_status_q && exit 0 $1 ;; stop) rh_status_q || exit 0 $1 ;; restart|configtest) $1 ;; reload) rh_status_q || exit 7 $1 ;; force-reload) force_reload ;; status) rh_status ;; condrestart|try-restart) rh_status_q || exit 0 ;; *) echo $"Usage: $0 {start|stop|status|restart|condrestart|try-restart|reload|force-reload|configtest}" exit 2 esac
4、为此脚本赋予执行权限,添加至服务管理列表,并让其开机自动启动[root@nginx ~]# chmod +x /etc/init.d/nginx [root@nginx ~]# chkconfig --add nginx [root@nginx ~]# chkconfig nginx on
5、启动nginx,并用浏览器访问 htpp://192.168.1.22, 即主机ip, 如果有欢迎进入nginx则说明nginx配置安装成功, 否则可能需要关闭防火墙。[root@nginx ~]# service nginx start
6、关闭防火墙[root@nginx ~]# service iptables stop [root@nginx ~]# chkconfig iptables off [root@nginx ~]# getenforce三、nginx.conf 配置文件
Nginx 配置文件主要分成四部分:main(全局设置)、http(HTTP 的通用设置)、server(虚拟主机设置)、location(匹配 URL 路径)。还有一些其他的配置段,如 event,upstream 等。
通用设置说明
user nginx #指定运行 nginx workre 进程的用户和组
worker_rlimit_nofile #指定所有 worker 进程能够打开的最大文件数
worker_cpu_affinity #设置 worker 进程的 CPU 粘性,以避免进程在 CPU 间切换带来的性能消耗.如 worker_cpu_affinity 0001 0010 0100 1000;(四核)
worker_processes 4 #worker 工作进程的个数,这个值可以设置为与 CPU 数量相同,如果开启了 SSL 和 Gzip,那么可以适当增加此数值
worker_connections 1000 #单个 worker 进程能接受的最大并发连接数,放在 event 段中
error_log logs/error.log info #错误日志的存放路径和记录级别
use epoll #使用 epoll 事件模型,放在 event 段中
server 配置示例# server {}: 定义一个虚拟主机 server { # 定义监听的地址和端口,默认监听在本机所有地址上 listen 80; # 定义虚拟主机名,可以使用多个名称,还可以使用正则表达式或通配符。 server_name www.example.com; # 开启 sendfile 调用来快速的响应客户端 sendfile on # 长连接超时时间,单位是秒。 keepalive_timeout 65 # 指定响应客户端的超时时间 send_timeout # 允许客户端请求的实体最大大小 client_max_body_size 10m # 设置请求 URL 所对应资源所在文件系统上的根目录 root /web/htdocs; # location [ = | ~ | ~* | ^~ ] URI { ... } # 设置一个 URI 匹配路径 # =:精确匹配 # ~:正则表达式匹配,区分字符大小写 # ~*:正则表达式匹配,不区分字符大小写 # ^~:URI 的前半部分匹配,且不实用正则表达式 # 优先级:= > location 完整路径 > ^~ > ~ > ~* > location 起始路径 > location / location / { index index.html index.htm; } location /status { stub_status on; # 基于 IP 访问控制: allow 和 deny, 允许10.0.0.0网段客户进行访问 allow 10.0.0.0/8; # 拒绝其他所有网段进行访问 deny all; # 访问日志是否开启 access_log off; # 重定向: rewrite <REGEX> <REPL> <FLAG> # 可用的 flag: # - last:重写完成后,继续匹配其他 rewrite 规则 # - break:重写完成后不再继续匹配 # - redirect:返回 302 重定向(临时重定向),客户端对重定向的 URL 发起新的请求 # - permanent:返回 301 重定向(永久重定向),客户端对重定向的 URL 发起新的请求 rewrite ^(/status/.*)/media/(.*)\..*$ $1/mp3/$2.mp3 last; }四、nginx配置ssl
server { listen 443; server_name example.com; root /apps/www; index index.html index.htm; ssl on; # ssl_certificate 表示 CA 文件 ssl_certificate /etc/nginx/ssl/nginx.crt; # 表示密钥文件 ssl_certificate_key /etc/nginx/ssl/nginx.key; # ssl_protocols SSLv3 TLSv1 TLSv1.1 TLSv1.2; # ssl_ciphers ALL:!ADH:!EXPORT56:RC4+RSA:+HIGH:+MEDIUM:+LOW:+SSLv2:+EXP; # ssl_prefer_server_ciphers on; }五、nginx防盗图配置
防盗图主要是针对定向的路径,当用户访问该路径,检测域名,如果域名不对,重定向。location ~ \/public\/(css|js|img)\/.*\.(js|css|gif|jpg|jpeg|png|bmp|swf) { valid_referers none blocked *.homeway.me; if ($invalid_referer) { rewrite ^/ http://xiaocao.u.qiniudn.com/blog%2Fpiratesp.png; } }六、Nginx之反向代理
关于反向代理和正向代理的说明请阅读:http://blog.csdn.net/xlxxcc/article/details/52640432
在配置nginx反向代理之间我们得先准备两台测试服务器,Web1与Web2。
注意:每次修改配置,需要重新加载配置或者重新启动。# 重启apache service httpd restart # 重新加载nginx配置 service nginx reload
1、安装httpd[root@web1 ~]# yum install -y httpd [root@web2 ~]# yum install -y httpd
2、提供测试页面[root@web1 ~]# echo "<h1>web1.test.com</h1>" > /var/www/html/index.html [root@web2 ~]# echo "<h1>web2.test.com</h1>" > /var/www/html/index.html
3、启动httpd服[root@web1 ~]# service httpd start [root@web2 ~]# service httpd start
4、浏览器访问 http://localhost/, 浏览器显示web1.test.com和web2.test.com说明正常。
5、nginx 代理模块 : proxy_pass ,
注意,当使用http proxy模块(甚至FastCGI),所有的连接请求在发送到后端服务器之前nginx将缓存它们,因此,在测量从后端传送的数据时,它的进度显示可能不正确。
配置http反向代理:location / { # 这个指令设置被代理服务器的地址和被映射的URI,地址可以使用主机名或IP加端口号的形式 proxy_pass http://192.168.1.12; proxy_set_header X-Real-IP $remote_addr; }
6、浏览器访问代理主机,会发现跳转达到192.168.1.12, 显示web1.test.com
7、查看web1的访问日志: tail /var/log/httpd/access_log可以看到我们这里的客户的IP全是,nginx代理服务器的IP,并不是真实客户端的IP。下面我们修改一下,让日志的IP显示真实的客户端的IP。location / { proxy_pass http://192.168.18.201; # 记录访问用户真实ip proxy_set_header X-Real-IP $remote_addr; #加上这一行 }
8、还需要配置被代理的apache配置: vim /etc/httpd/conf/httpd.conf, 才能在apache的访问日志中。
改成:
注,这是修改后的参数,将h%修改为%{X-Real-IP}i,好的下面我们再来测试一下。
好了,到这里Nginx代理后端一台服务器,看到日志里记录的IP地址就是真实的客户端地址了。七、Nginx之负载均衡
1.upstream 负载均衡模块说明,示例:upstream test.net{ ip_hash; server 192.168.10.13:80; server 192.168.10.14:80 down; server 192.168.10.15:8009 max_fails=3 fail_timeout=20s; server 192.168.10.16:8080; } server { location / { proxy_pass http://test.net; } }
2、upstream的几种调度方式和示例,请查阅:http://blog.csdn.net/xlxxcc/article/details/52641063
3、.配置nginx负载均衡, vim /etc/nginx/nginx.confupstream webservers { server 192.168.1.12 weight=1; server 192.168.1.13 weight=1; } server { listen 80; server_name localhost; #charset koi8-r; #access_log logs/host.access.log main; location / { # 此处不可少, 指向上面的均衡负载配置 proxy_pass http://webservers; proxy_set_header X-Real-IP $remote_addr; } }
4、重新加载nginx配置service nginx reload
5、浏览器访问代理主机,会发现浏览器偶尔显示web1.test.com, 偶尔显示web2.test.com。两者交替出现,说明达到了负载均衡的效果。
6、配置nginx进行健康状态检查upstream webservers { #max_fails,允许请求失败的次数,默认为1。当超过最大次数时,返回proxy_next_upstream 模块定义的错误。 server 192.168.18.201 weight=1 max_fails=2 fail_timeout=2; # fail_timeout,在经历了max_fails次失败后,暂停服务的时间。max_fails可以和fail_timeout一起使用,进行健康状态检查。 server 192.168.18.202 weight=1 max_fails=2 fail_timeout=2; }
7、配置backup服务器, 应对所有服务器都不能提供服务[root@nginx ~]# vim /etc/nginx/nginx.conf upstream webservers { server 192.168.18.201 weight=1 max_fails=2 fail_timeout=2; server 192.168.18.202 weight=1 max_fails=2 fail_timeout=2; server 127.0.0.1:8080 backup; } [root@nginx ~]# mkdir -pv /data/www/errorpage [root@nginx errorpage]# cat index.html <h1>Sorry......</h1>
8、关闭web1和web2,浏览器访问服务器,会发现浏览器显示 Sorry……八、Nginx之页面缓存
1、页面缓存指令说明,请查阅:http://blog.csdn.net/xlxxcc/article/details/52641496
2、定义一个简单nginx缓存服务器,[root@nginx ~]# vim /etc/nginx/nginx.conf proxy_cache_path /data/nginx/cache/webserver levels=1:2 keys_zone=webserver:20m max_size=1g; server { listen 80; server_name localhost; #charset koi8-r; #access_log logs/host.access.log main; location / { proxy_pass http://webservers; proxy_set_header X-Real-IP $remote_addr; proxy_cache webserver; proxy_cache_valid 200 10m; } }
3、新建缓存目录, 并重新加载配置文件[root@nginx ~]# mkdir -pv /data/nginx/cache/webserver
4、配置$server_addr和$upstream_cache_status缓存变量
$server_addr: 服务器地址,在完成一次系统调用后可以确定这个值,如果要绕开系统调用,则必须在listen中指定地址并且使用bind参数。
$upstream_cache_status: 其值可能为:
MISS 未命中
EXPIRED - expired。请求被传送到后端。
UPDATING - expired。由于proxy/fastcgi_cache_use_stale正在更新,将使用旧的应答。
STALE - expired。由于proxy/fastcgi_cache_use_stale,后端将得到过期的应答。
HIT 命中[root@nginx ~]# vim /etc/nginx/nginx.conf proxy_cache_path /data/nginx/cache/webserver levels=1:2 keys_zone=webserver:20m max_size=1g; server { listen 80; server_name localhost; #charset koi8-r; #access_log logs/host.access.log main; #增加两头部 add_header X-Via $server_addr; add_header X-Cache $upstream_cache_status; location / { proxy_pass http://webservers; proxy_set_header X-Real-IP $remote_addr; proxy_cache webserver; proxy_cache_valid 200 10m; } }
5、重新加载配置文件[root@nginx ~]# service nginx reload
6、谷歌浏览器访问服务,点击F12 -> Network, 查看Response Headers, 我们可以看到X-Cache: HIT, 说明访问的服务器是缓存命中。
7、查看缓存目录[root@nginx ~]# cd /data/nginx/cache/webserver/f/63/ [root@nginx 63]# ls 681ad4c77694b65d61c9985553a2763f
注,缓存目录里确实有缓存文件。好了,nginx缓存配置就到这边了,更多配置请根据需要看配置文档。九、Nginx之URL重写
1、Nginx Rewrite 指令说明,请查阅:http://blog.csdn.net/xlxxcc/article/details/52641293
2、简单案例
注,由于配置文件内容较多,为了让大家看着方便,我们备份一下配置文件,打开一个新的配置文件。[root@nginx ~]# cd /etc/nginx/ [root@nginx nginx]# mv nginx.conf nginx.conf.proxy [root@nginx nginx]# cp nginx.conf.bak nginx.conf [root@nginx nginx]# vim /etc/nginx/nginx.conf server { listen 80; server_name localhost; #charset koi8-r; #access_log logs/host.access.log main; location / { root html; index index.html index.htm; rewrite ^/bbs/(.*)$ http://192.168.1.12/forum/$1; } }
[root@nginx ]# service nginx reload
web1 准备forum目录与测试文件[root@web1 ~]# cd /var/www/html/ [root@web1 html]# ls index.html [root@web1 html]# mkdir forum [root@web1 html]# cd forum/ [root@web1 forum]# vim index.html <h1>forum page!</h1>
3、浏览测试一下, 显示 forum page! 谷歌浏览器打开F12 -> Network -> Headers,可以看到status code 302指的是临时重定向,那就说明我们rewrite重写配置成功。大家知道302是临时重定向而301是永久重定向,那么怎么实现永久重定向呢。一般服务器与服务器之间是临时重定向,服务器内部是永久重定向。下面我们来演示一下永久重定向。
4、配置永久重定向[root@nginx nginx]# vim /etc/nginx/nginx.conf server { listen 80; server_name localhost; #charset koi8-r; #access_log logs/host.access.log main; location / { root html; index index.html index.htm; rewrite ^/bbs/(.*)$ /forum/$1; } }
准备forum目录与测试文件[root@nginx ~]# cd /usr/html/ [root@nginx html]# ls 50x.html index.html [root@nginx html]# mkdir forum [root@nginx html]# cd forum/ [root@nginx forum]# vim index.html <h1>192.168.18.208 forum page</h1>
5.重新加载一下配置文件[root@nginx ~]# service nginx reload
6、测试一下,谷歌浏览器打开F12 -> Network -> Headers,我们访问bbs/是直接帮我们跳转到forum/下,这种本机的跳转就是永久重定向也叫隐式重定向。好了,rewrite重定向我们就说到这里了,想要查询更多关于重定向的指令请参考官方文档。十、Nginx之URL重写
1、实验拓扑
需求分析,前端一台nginx做负载均衡反向代理,后面两台httpd服务器。整个架构是提供BBS(论坛)服务,有一需求得实现读写分离,就是上传附件的功能,我们上传的附件只能上传到Web1,然后在Web1上利用rsync+inotify实现附件同步,大家都知道rsync+inotify只能是主向从同步,不能双向同步。所以Web1可进行写操作,而Web2只能进行读操作,这就带来读写分离的需求,下面我们就来说一下,读写分离怎么实现。
2、WebDAV功能说明
WebDAV (Web-based Distributed Authoring and Versioning) 一种基于 HTTP 1.1协议的通信协议。它扩展了HTTP 1.1,在GET、POST、HEAD等几个HTTP标准方法以外添加了一些新的方法,使应用程序可直接对Web Server直接读写,并支持写文件锁定(Locking)及解锁(Unlock),还可以支持文件的版本控制。这样我们就能配置读写分离功能了,下面我们来具体配置一下。
3、修改配置文件[root@nginx nginx]# vim /etc/nginx/nginx.conf server { listen 80; server_name localhost; #charset koi8-r; #access_log logs/host.access.log main; location / { proxy_pass http://192.168.18.202; if ($request_method = "PUT"){ proxy_pass http://192.168.18.201; } } }
4、重新加载一下配置文件[root@nginx ~]# service nginx reload
5、配置httpd的WebDAV功能[root@web1 ~]# vim /etc/httpd/conf/httpd.conf <Directory "/var/www/html"> Dav on .... </Directory>
6、重新启动一下httpd[root@web1 ~]# service httpd restart
7、测试一下[root@nginx ~]# curl http://192.168.18.201 <h1>web1.test.com</h1> [root@nginx ~]# curl http://192.168.18.202 <h1>web2.test.com</h1>
注,web1与web2访问都没问题。[root@nginx ~]# curl -T /etc/issue http://192.168.18.202 <!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN"> <html><head> <title>405 Method Not Allowed</title> </head><body> <h1>Method Not Allowed</h1> The requested method PUT is not allowed for the URL /issue. <hr> <address>Apache/2.2.15 (CentOS) Server at 192.168.18.202 Port 80</address> </body></html>
注,我们上传文件到,web2上时,因为web2只人读功能,所以没有开户WebDAV功能,所以显示是405 Method Not Allowed。[root@nginx ~]# curl -T /etc/issue http://192.168.18.201 <!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN"> <html><head> <title>403 Forbidden</title> </head><body> <h1>Forbidden</h1> You don't have permission to access /issue on this server. <hr> <address>Apache/2.2
注,我们在Web1开启了WebDAV功能,但我们目录是root目录是不允许apache用户上传的,所以显示的是403 Forbidden。下面我们给apache授权,允许上传。[root@web1 ~]# setfacl -m u:apache:rwx /var/www/html/
下面我们再来测试一下,[root@nginx ~]# curl -T /etc/issue http://192.168.18.201 <!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML 2.0//EN"> <html><head> <title>201 Created</title> </head><body> <h1>Created</h1> Resource /issue has been created. <hr /> <address>Apache/2.2.15 (CentOS) Server at 192.168.18.201 Port 80</address> </body></html>
注,大家可以看到我们成功的上传了文件,说明nginx读写分离功能配置完成。最后,我们来查看一下上传的文件。[root@web1 ~]# cd /var/www/html/ [root@web1 html]# ll 总用量 12 drwxr-xr-x 2 root root 4096 9月 4 13:16 forum -rw-r--r-- 1 root root 23 9月 3 23:37 index.html -rw-r--r-- 1 apache apache 47 9月 4 14:06 issue
好了,到这里nginx的反向代理、负载均衡、页面缓存、URL重写及读写分离就全部讲解完成。希望大家有所收获,^_^……
原文出自:陈明乾 的BLOG
原文出处:http://freeloda.blog.51cto.com/2033581/1288553
相关文章推荐
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解(二)
- (转)NGINX 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解 (三)
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解(1)
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解 (转载)
- [转载]Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解(2)
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解 (六)
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解 (五)
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解
- Nginx 反向代理、负载均衡、页面缓存、URL重写及读写分离详解