管理员
论坛积分
分
威望 点
贡献值 个
金币 枚
|
情景 由于公司内网有多台服务器的http服务要映射到公司外网静态IP,如果用路由的端口映射来做,就只能一台内网服务器的80端口映射到外网80端口,其他服务器的80端口只能映射到外网的非80端口。非80端口的映射在访问的时候要域名加上端口,比较麻烦。并且公司入口路由最多只能做20个端口映射。肯定以后不够用。 然后k兄就提议可以在内网搭建个nginx反向代理服务器,将nginx反向代理服务器的80映射到外网IP的80,这样指向到公司外网IP的域名的HTTP请求就会发送到nginx反向代理服务器,利用nginx反向代理将不同域名的请求转发给内网不同机器的端口,就起到了“根据域名自动转发到相应服务器的特定端口”的效果,而路由器的端口映射做到的只是“根据不同端口自动转发到相应服务器的特定端口”,真是喜大普奔啊。 涉及的知识:nginx编译安装,nginx反向代理基本配置,路由端口映射知识,还有网络域名等常识。 本次实验目标是做到:在浏览器中输入xxx123.tk能访问到内网机器192.168.10.38的3000端口,输入xxx456.tk能访问到内网机器192.168.10.40的80端口。 配置步骤 服务器ubuntu 12.04
" a2 L5 f, Z8 S; b0 ], n- j/ m3 Z
- ###更新仓库, u% C' b& @. u3 a+ ~( S
- % }/ G _3 P1 o5 ?( u
- apt-get update -y
0 C& ?0 p) |" q8 i% e. z+ p - apt-get install wget -y( M( a% `! c. R5 h
- #下载nginx和相关软件包
复制代码
% L6 y+ E& f7 R% n
9 H6 k1 T) L1 S8 [# [pcre是为了编译rewrite模块,zlib是为了支持gzip功能。额,这里nginx版本有点旧,因为我还要做升级nginx的实验用。大家可以装新版本。
0 r3 [' J- h3 S, _% J
+ z. y# H' s" C% _- cd /usr/local/src
4 q* j7 J0 C" q+ }/ o5 f - wget <a href="ftp://ftp.csx.cam.ac.uk/pub/software/programming/pcre/pcre-8.33.tar.gz">ftp://ftp.csx.cam.ac.uk/pub/software/programming/pcre/pcre-8.33.tar.gz</a>
E) z4 J e0 y' r: Q% P - wget <a href="http://zlib.net/zlib-1.2.8.tar.gz">http://zlib.net/zlib-1.2.8.tar.gz</a>" V8 J' F/ v5 J- o9 o- L5 F
- wget <a href="http://nginx.org/download/nginx-1.4.2.tar.gz">http://nginx.org/download/nginx-1.4.2.tar.gz</a>
' C9 b6 Q+ G2 t# K2 E* }5 _ - tar xf pcre-8.33.tar.gz K7 C$ X) }! M. V: O r- I
- tar xf zlib-1.2.8.tar.gz9 D( h1 j" E8 M9 w
- #安装编译环境
# z! g! {. u* f2 j
复制代码 0 @7 m1 a Z# O5 c4 T% A
* P$ \" U! R# E9 J
apt-get install build-essential libtool -y) j1 e& C- [1 J
#创建nginx用户/ e% C5 S p: T/ W
) O( C; t8 ?1 O: h/ f- h6 Q& k. c
所谓的unprivileged user
' C! r+ s* F( r% T# k* f7 I8 h5 }
- useradd -s /bin/false -r -M -d /nonexistent www# U3 l' h" T0 X# Y! X& O
- #开始编译安装$ j. k& {2 ^& C8 X N$ K
- , f: y" \8 }! r: a6 V$ \ L
- /configure --with-pcre=/usr/local/src/pcre-8.33 --with-zlib=/usr/local/src/zlib-1.2.8 --user=www --group=www \% h( o3 o) m* V3 B' U
- --with-http_stub_status_module --with-http_ssl_module --with-http_realip_module
, R; @% d4 P8 F5 J3 \ - make; v3 M" p* [4 L: j# Y" |6 y
- make install
" o1 r* @& H# c' x. T$ Z3 Y" I - #给文件夹授权
复制代码
+ X- K0 g! K! c* s) k8 r" @
/ b8 ]! \7 Y- B' [% B2 D- B* |chown -R www:www /usr/local/nginx
3 D) ^8 W B' O#修改配置文件' n+ C7 f% U; i! }! J: @
vim nginx.conf
8 l8 U3 C, G: f$ _1 h
8 k8 e# I- X, V) Quser www www;
0 f3 r6 ~* t) a0 X7 m1 t5 Qworker_processes 1;
. p2 ?5 b6 ~6 E* m3 u" X# V: berror_log logs/error.log;
! L: L8 U& u, Q& ?" Apid logs/nginx.pid;" j. g, Q* o9 S4 V0 c9 L9 n
worker_rlimit_nofile 65535;
' W% T5 s! r; [events {
) u( ~8 _7 m' l6 c use epoll;
- V, X, w: F9 l) M; h7 J, e worker_connections 65535;/ G7 ~, m$ |7 Y |
}/ M1 W4 J# q' X, B4 G( X
http {! e% X$ A o! g( E& f; Y7 \
include mime.types;
M( s ]- t6 a* b! G" q! d% L default_type application/octet-stream;/ _5 g$ u( }2 J' `( R
include /usr/local/nginx/conf/reverse-proxy.conf;# K8 y. y2 \4 R0 q, g
sendfile on;1 X g" j2 D* K2 e3 l
keepalive_timeout 65;2 \2 t! ?$ L$ W) N. {
gzip on;
6 g* y2 e( I9 Z8 w' P client_max_body_size 50m; #缓冲区代理缓冲用户端请求的最大字节数,可以理解为保存到本地再传给用户$ ?: x9 k, t: Z
client_body_buffer_size 256k;& o0 F6 K; {# I% l2 o5 t& Q
client_header_timeout 3m;. B, n0 Z9 O0 }/ d2 q
client_body_timeout 3m;; m: @+ V" l( v. s$ f
send_timeout 3m;
9 J4 F. E, W M! J s7 l3 K proxy_connect_timeout 300s; #nginx跟后端服务器连接超时时间(代理连接超时)# u0 I* ~ o& D, c" d/ C
proxy_read_timeout 300s; #连接成功后,后端服务器响应时间(代理接收超时)
5 O8 ?1 G: Q7 V* O! Y proxy_send_timeout 300s;7 q6 i% ^# y# U3 I% I
proxy_buffer_size 64k; #设置代理服务器(nginx)保存用户头信息的缓冲区大小
( I& w( |& `3 h( m# B: [+ w8 i proxy_buffers 4 32k; #proxy_buffers缓冲区,网页平均在32k以下的话,这样设置" ?9 h5 L8 B) q% b
proxy_busy_buffers_size 64k; #高负荷下缓冲大小(proxy_buffers*2)
! Y) @( i; o" ~7 c* h1 ` proxy_temp_file_write_size 64k; #设定缓存文件夹大小,大于这个值,将从upstream服务器传递请求,而不缓冲到磁盘
2 ~/ `: I" q% f! y proxy_ignore_client_abort on; #不允许代理端主动关闭连接
( V( y7 l W. ]0 d" | server {
3 u; d8 K0 l( y6 l- ?2 g0 R listen 80;
1 ?/ q" D/ K# d, R' [- f server_name localhost;
% D" m5 _1 F9 w) ?, f2 ?, p location / {
8 h* K, c5 I# d8 V root html;' U6 k w# t2 R+ v4 ?
index index.html index.htm;( T _; T9 E6 H$ G) B: z
}
9 p8 l- u7 f# C9 j: Y+ E$ B error_page 500 502 503 504 /50x.html;( [2 z. \; n5 }2 z+ s. m. }9 p9 v
location = /50x.html {$ N# K' k/ I7 p: s. N5 a
root html;
2 t0 W) q5 _7 V- k }
+ b0 h- w2 a4 u4 U+ j. X6 Q9 M }; ~- D- d: T( R" K
}, e6 I1 O, G& D
0 a c8 {2 e0 U) i4 z
编辑反向代理服务器配置文件:
! h6 U* B* d2 r6 v/ @
5 ^/ C q; b* A3 A5 ]& Ivim /usr/local/nginx/conf/reverse-proxy.conf1 O& m& |: W9 \' x- a
8 A. y2 L V( H
server2 P0 S9 Z/ L1 B: K/ W1 e
{
/ J6 V9 D, @" {( B7 M' H; \5 } listen 80;- f0 O: u5 A) _) x3 _1 F
server_name xxx123.tk;& ~ {2 Q& R; s# u( C# X. z; J
location / {
' |8 M" d+ D$ J ~! Z proxy_redirect off;2 ^# _& {. s4 C7 ~
proxy_set_header Host $host;- o' x- K5 F" Q/ n
proxy_set_header X-Real-IP $remote_addr;: {2 g, a' q6 G
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
+ B+ c; N& p* Q proxy_pass http://192.168.10.38:3000;' |4 g- C: G* V9 e/ W& X9 X
}
: M5 T5 u+ S+ ?/ n9 ~' z4 P access_log logs/xxx123.tk_access.log;
: s4 H L; G( {7 ^# B}
2 V7 V( n% h. D$ l
/ O8 \: V# Z2 f" O2 d$ Bserver% b- Y) ]6 l, k9 a4 X- M
{8 t$ ]% N% V# Y S A
listen 80;. q3 j% ^. k& C. m& ]
server_name xxx456.tk;
+ ~2 l0 d# P8 X& H location / {
& H5 q) A0 e8 w4 I- m8 R6 }$ f; z- V proxy_redirect off;
, F6 @& @$ X" R- v- } proxy_set_header Host $host;
& e# A" C5 n4 K2 t) s proxy_set_header X-Real-IP $remote_addr;5 s- t8 X1 z1 s1 ^$ D
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;: q' L6 d# R+ j5 g/ C, F1 I0 E
proxy_pass http://192.168.10.40:80;" N! Q# l+ p# ^9 |* g
}7 V! W, |9 ^9 X' O* ]0 a
access_log logs/xxx456.tk_access.log;
3 _ e2 J# w* @7 ?9 F# c3 M5 M}* O* g+ o: \: @8 _
$ C- r# L3 E' `6 z- G* c
然后重新加载nginx配置文件,使之修改生效,再把xxx123.tk域名指向公司静态IP,这样就成功的做到了在浏览器中输入xxx123.tk的时候访问的内网服务器192.168.10.38的3000端口,输入xxx456.tk访问192.168.10.40的80端口的作用。 如果想对后端机器做负载均衡,像下面这配置就可以把对nagios.xxx123.tk的请求分发给内网的131和132这两台机器做负载均衡了。, F! j, w3 i: |6 p
' P. X8 p* t7 Q. `% L" T; `% H) G
upstream monitor_server {% i0 H2 A% x6 n" t8 @
server 192.168.0.131:80;5 R/ a5 x( X4 K6 s X
server 192.168.0.132:80; B q) `" f+ w, |1 i
}
: w8 G0 ]5 Z6 w9 {; f* u( ]2 y
$ Z+ P/ @, l8 G! Tserver
5 ?5 c1 H& H3 h% ?- }$ N/ S{& k! s* D. K- D! j* r2 L1 Y6 z
listen 80;
. ]: E0 @' x9 g$ { server_name nagios.xxx123.tk;2 Z+ c* |4 ~% T! J" Y
location / {
' q* C2 [, o4 x& d1 |, w proxy_redirect off;
# H. C+ ?% u! ]0 t- A8 k proxy_set_header Host $host;% Y& i7 x+ m% m; [, s
proxy_set_header X-Real-IP $remote_addr;
& w _8 K7 k5 C3 U# Z" W1 T proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 6 {/ j4 _ n. _
proxy_pass http://monitor_server;
( Q) ^" Z j. r1 ~7 ` }( M+ h) L- t, Z
access_log logs/nagios.xxx123.tk_access.log;
7 k1 i/ {4 J- ~4 p}# r! L# N$ E9 r6 B
# }6 V, u% f4 t" B, C8 V- }# }" j
额,关于负载均衡和缓存就不多说了,这里只是要起到一个简单的“域名转发”功能。 另外,由于http请求最后都是由反向代理服务器传递给后段的机器,所以后端的机器原来的访问日志记录的访问IP都是反向代理服务器的IP。 要想能记录真实IP,需要修改后端机器的日志格式,这里假设后端也是一台nginx: 在后端配置文件里面加入这一段即可:
# {) i. z0 ?8 e2 Q5 J' w6 y
- Y, f* X, ], v, @- S: y" Alog_format access '$HTTP_X_REAL_IP - $remote_user [$time_local] "$request" ' @" X4 g( |, w, v
'$status $body_bytes_sent "$http_referer" '
. o2 `' c& g! u8 t2 v7 \'"$http_user_agent" $HTTP_X_Forwarded_For';
# B1 }% X1 z7 p( H/ _ h
0 I0 o: c! U( x8 L$ ?access_log logs/access.log access;, R6 A; Y) s. w& U
) L4 U+ k3 T! N; s再看看原来日志的格式长什么样:" q! b- D6 O u% r: ~0 V4 z0 `
2 Q/ G" J0 A, x0 P8 T( L$ _6 p' ^
1% \* l6 o) x4 Q
2" @* M$ Q9 ^, H. V
3) E' v. R7 f k( k) q) j! ^
4
q; L) A6 I! d' V8 s+ W+ n55 {: E, A; l5 Z" t
#log_format main '$remote_addr - $remote_user [$time_local] "$request" '
9 K8 f& Y' P" Q# y' _# '$status $body_bytes_sent "$http_referer" '( U$ L8 ^- a2 v8 G( F! A5 Y
# '"$http_user_agent" "$http_x_forwarded_for"';
; V/ b* K( N2 [& G1 i ' W4 I! q" P) w% b. a' z/ p
#access_log logs/access.log main;) Z2 r1 N; o V+ ]
看出区别了吧 遇到的问题 之前没配置下面这段,访问时候偶尔会出现504 gateway timeout,由于偶尔出现,所以不太好排查
. P, S$ K2 R4 ?, A0 c
" d) u0 i G6 c a1
" u1 v# \4 I @1 o22 R! \( k# K% A
3
0 p. L* N1 r8 P* L4
# ]0 d9 y$ J) E& Q( ^58 q0 ?$ K. Z' }8 j/ [
6
) v4 j& _* v" [5 _71 k, G0 P8 K$ k# k
8
1 T* x p9 _# qproxy_connect_timeout 300s;/ \ f( v& Y" e
proxy_read_timeout 300s;
/ R1 [) ^( O/ w6 xproxy_send_timeout 300s;
4 h9 D, N/ R$ v+ Gproxy_buffer_size 64k;
, j0 d; J" o# e# P: j: Uproxy_buffers 4 32k;
/ b; P+ h5 M) ^! R- bproxy_busy_buffers_size 64k;
8 n* f$ {2 `. F$ Kproxy_temp_file_write_size 64k;
% ?9 E9 ^& a( E" c9 f' J* fproxy_ignore_client_abort on;
3 j) ^+ g# o9 c G报错日志:
/ k0 Q" K3 z& _: O: o3 D* M) Y- s
0 j6 x$ i/ s" M...upstream timed out (110: Connection timed out) while reading response header from upstream, client: ...(后面的省略) 从日志看来是连接超时了,网上一通乱查之后估计可能是后端服务器响应超时了,本着大胆假设,小心求证的原则,既然假设了错误原因就要做实验重现错误:那就调整代理超时参数,反过来把代理超时阀值设小(比如1ms)看会不会次次出现504。后来发现把proxy_read_timeout 这个参数设置成1ms的时候,每次访问都出现504。于是把这个参数调大,加入上面那段配置,解决问题了。; H' u5 g5 e3 o1 o6 ^. N
+ o% \' o9 Y YPS:关于域名转发
3 |( g2 ~, o0 A! @& {7 P0 Z- y. w5 Z9 J V, x
所谓域名URL转发,是通过服务器的特殊设置,将访问您当前域名的用户引导到您指定的另一个网络地址。 地址转向(也可称“URL转发”)即将一个域名指向到另外一个已存在的站点,英文称为“ URL FORWARDING ”。域名指向可能这个站点原有的域名或网址是比较复杂难记的。 已经注册成功的域名,若初设或取消 URL 转发设置,一般均在 24-48 小时之内生效。对于原有已经设置成功的 URL 转发域名,如果修改 URL 转发的目标地址,则只需 1-2 个小时即可生效。 不隐藏路径 URL 转发:例如: http://b.com/ 指向 http://a.com/xxx/ (任意目录);当在浏览器地址栏中敲入 http://b.com/ 后回车, IE 浏览器的地址栏里显示的地址会由原来您敲入的 http://b.com/ 自动变为显示真正的目标地址 http://a.com/xxx/ ; 隐藏路径的 URL 转发:例如:先同上, IE 浏览器的地址栏里显示的地址保持不变,仍是 http://b.com/ ,但实际访问到的是 http://a.com/xxx/ 的内容。7 q4 z: W( f* G0 l2 T) F
|
|