Nginx 负载均衡和反向代理

Upstream 模块是 Nginx负载均衡的主要模块,它提供了简单的办法来实现在轮询和客户端IP之间的后端服务器负载均衡,并可以对服务器进行健康检查。它的配置方式是:
在 nginx.conf 中加入:

1
2
3
4
upstream somename{
server domain1.abc.com weight=5;
server domain2.abc.com:8080
}

这样就声明了一个负载均衡的服务器集合.而我们的服务都是在 server模块中定义的,所以可以想象,如果我们要对服务进行负载均衡,肯定要在 server 模块中进行和 upstream的关联。如:

1
2
3
4
5
6
7
8
9
server{
listen 80;
server_name www.domain1.com
location /message/
{
proxy_pass http://somename/
proxy_set_header Host $host;
}
}

上面这段配置的意思就是,当访问 www.domain1.com/message/时,会反向代理到前面 upstream定义的 somename 这一个服务器集合中。默认的负载均衡方式是轮询.Upstream 中的 server指令用于指定服务器的名称和参数,服务器的名称可以是一个域名,一个IP地址,或 unix socket.
server 模块中可以通过如上所示的 proxy_pass 或 fastcgi_pass 进和向代理 upstream服务器集群.
proxy_set_header 用于在向反向代理的web服务器发起请求时添加指定的 Header头信息。比如服务器A上有多个虚拟主机,我们通过反向代理将请求转向服务器A,如何能确定是要转向哪个虚拟主机呢,就是通过proxy_set_header 来进行的。
使用反向代理后,后端WEB服务器(以PHP为例),就不能直接通过$_SERVER['REMOTE_ADDR']来获得用户的真实IP了,它获得的是Nginx负载均衡服务器的IP。这时候要通过在Nginx反向代理时添加Header头信息X-Forwarded-For让服务器通过$_SERVER['HTTP_X_FORWARDED_FOR']来获得真实的IP.

下面贴上一些完整的配置文件:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
user  www www;
worker_processes 4;
error_log /home/wwwlogs/nginx_error.log crit;
pid /usr/local/nginx/logs/nginx.pid;
#Specifies the value for maximum file descriptors that can beopened by this process.
worker_rlimit_nofile 51200;
events
{
use epoll;
worker_connections 51200;
}
http
{
include mime.types;
default_type application/octet-stream;

server_names_hash_bucket_size 128;
client_header_buffer_size 32k;
large_client_header_buffers 4 32k;
# 允许客户端请求的最大单个文件字节数
client_max_body_size 50m;
# 缓冲区代理缓冲用户端请求的最大字节数,可以先保存到本地再传给用户
client_body_buffer_size 128k
# 和服务器连接超时时间.单为是秒
proxy_connect_timeout 600;
# 连接成功后等候服务器响应时间.单位是秒
proxy_read_timeout 600;
# 服务器数据回传时间.即在规定时间内服务器必须传完所有的数据.单位是秒
proxy_send_timeout 600;
# 代理请求缓存区.这里会保存用户的头信息以供nginx进行处理
proxy_buffer_size 16k

sendfile on;
tcp_nopush on;

keepalive_timeout 60;

tcp_nodelay on;

fastcgi_connect_timeout 300;
fastcgi_send_timeout 300;
fastcgi_read_timeout 300;
fastcgi_buffer_size 64k;
fastcgi_buffers 4 64k;
fastcgi_busy_buffers_size 128k;
fastcgi_temp_file_write_size 256k;

gzip on;
gzip_min_length 1k;
gzip_buffers 416k;
gzip_http_version 1.0;
gzip_comp_level 2;
gzip_types text/plain application/x-javascript text/cssapplication/xml;
gzip_vary on;

#limit_zone crawler $binary_remote_addr 10m;
# 定义三组服务器
upstream php_server_pool{
server 192.168.1.10:80 weight=4 max_fails=2 fail_timeout=30s;
server 192.168.1.11:80 weight=4 max_fails=2 fail_timeout=30s;
server 192.168.1.12:80 weight=2 max_fails=2 fail_timeout=30s;
}
upstream message_server_pool{
server 192.168.1.13:3245;
server 192.168.1.14:3245 down;
}
upstream bbs_server_pool{
server 192.168.1.15:80 weight=1max_fails=2 fail_timeout=30s;
server 192.168.1.16:80 weight=1 max_fails=2fail_timeout=30s;
server 192.168.1.17:80 weight=1 max_fails=2fail_timeout=30s;
server 192.168.1.18:80 weight=1 max_fails=2fail_timeout=30s;
}
# 第一个虚拟主机,反向代理 php_server_pool这组服务器
server
{
listen 80;
server_name www.mydomain.jp;
index index.html index.htm index.php;
root /home/wwwroot/ywlxjp;

location /
{
# 如果后端服务器返回 502,504,超时等.将自动把请求转发到 upstream池中的另一台服务器中实现故障转移
proxy_next_upstream http_502 http_504 error timeoutinvalid_header
proxy_pass http://php_server_pool;
proxy_set_header Host www.mydomain.jp
proxy_set_header X-Forwarded-For $remote_addr;
}
log_format access '$remote_addr - $remote_user [$time_local]"$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" $http_x_forwarded_for';
access_log /home/wwwlogs/ywlxjp.log access;
}
# 第二个虚拟主机
server
{
listen 80;
server_name xmdm.mydomain.cn;
index index.html index.htm index.php;
root /home/wwwroot;
# 访问xmdm.mydomain.cn/message/将被转发到message_server_pool服务器集合中
location /message/
{
proxy_pass http://message_server_pool;
proxy_set_header Host $host;
}
# 访问xmdm.mydomain.cn/被转发到 php_server_pool服务器集合中
location /
{
proxy_pass http://php_server_pool;
proxy_set_header Host $host;
proxy_set_header X-Forwarded-For $remote_addr;
}
access_log /home/wwwlogs/xmdm.log access;
}
# 第三个虚拟主机
server
{
listen 80;
server_name yume.mydomain.jp;
index index.html index.htm index.php;
root /home/wwwroot/dreamjp;

location /
{
fastcgi_pass unix:/tmp/php-cgi.sock;
fastcgi_index index.php;
include fcgi.conf;
}
access_log /home/wwwlogs/yume.log access;
}

server
{
listen 80;
server_name soft.easymobi.cn;
index index.html index.htm index.php;
root /home/wwwroot/soft;

location /
{
proxy_pass http://bbs_server_pool;
proxy_set_header Host $host;
proxy_set_header X-Forwarded-For $remote_addr;
}
access_log /home/wwwlogs/soft.log access;
}
include vhost/*.conf;
}