管理员
   
论坛积分
分
威望 点
贡献值 个
金币 枚
|
情景 由于公司内网有多台服务器的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
2 X2 g3 H5 m6 L0 n2 s- p3 x1 Z) _1 F; D Q* D
- ###更新仓库% Q; ?# ?5 G/ d6 M; s3 i& j9 }2 |
* s+ ^5 D4 R6 G) m) \$ M b- apt-get update -y
8 i+ x$ `. X% ^) ?. t7 _" ~ - apt-get install wget -y
4 a6 ^; g8 ?& F - #下载nginx和相关软件包
复制代码
* l9 \% d5 t3 e- |; ^: ], K$ K3 O5 H- Z7 K* s
pcre是为了编译rewrite模块,zlib是为了支持gzip功能。额,这里nginx版本有点旧,因为我还要做升级nginx的实验用。大家可以装新版本。
" x6 P1 t. Q& a- o
; E5 @/ C8 `8 o" L- cd /usr/local/src
/ F% ? K7 ~9 l- O/ p6 {; i - 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>5 Z7 ?) K, i9 S: C5 j. J
- wget <a href="http://zlib.net/zlib-1.2.8.tar.gz">http://zlib.net/zlib-1.2.8.tar.gz</a>7 k' r- V7 C8 }( c5 p
- wget <a href="http://nginx.org/download/nginx-1.4.2.tar.gz">http://nginx.org/download/nginx-1.4.2.tar.gz</a>
8 a% y1 x4 j2 ? - tar xf pcre-8.33.tar.gz3 A- I6 J& L% D) i9 M: {
- tar xf zlib-1.2.8.tar.gz
- p5 s7 y$ H( [2 u; z/ k$ L8 u- ] - #安装编译环境
% Q+ L8 w( p5 k: ^- x
复制代码
' l" X1 R1 @( Y3 Q' z " q- K! E, H. x$ M4 ]* b
apt-get install build-essential libtool -y0 p, n$ \7 A4 C, c4 u3 K2 N' r
#创建nginx用户, Q! r8 g% s* L+ V
! ~+ M. i/ |+ E' l1 ]( C
所谓的unprivileged user2 \' O$ [) d G
' C1 G U# y: l
- useradd -s /bin/false -r -M -d /nonexistent www4 d q3 N# _5 u2 Y4 V
- #开始编译安装4 r, t) E8 m3 P. V5 H
- * w5 x& T9 X" _0 v( Y
- /configure --with-pcre=/usr/local/src/pcre-8.33 --with-zlib=/usr/local/src/zlib-1.2.8 --user=www --group=www \
* L$ t, N' n/ Q; F% L" i' N - --with-http_stub_status_module --with-http_ssl_module --with-http_realip_module
/ ?! ^1 X0 O4 F v9 M+ e - make
, v1 y$ N4 {! e. u( M - make install
F, C4 p, l. ^6 S: c; e, |& A - #给文件夹授权
复制代码
1 ~- s& `* t, e& B3 I5 [! O5 I
/ x5 f* h K; a. i9 M6 U2 Z( Cchown -R www:www /usr/local/nginx% v1 A% d# k8 k) q2 n% }$ j
#修改配置文件
8 ]/ ]7 O: k3 h+ n! V7 Q) `! }vim nginx.conf# N: X- p1 k/ \
$ O5 p9 |8 f4 y$ F; Juser www www;; e5 t/ @ Z5 y' H" K" r u h
worker_processes 1;2 i4 q. G3 V; q( C' H7 p
error_log logs/error.log;( V6 n( ?- f( G4 o/ V
pid logs/nginx.pid;
- ^8 U7 S& z* \. R7 C, V) C8 S$ @/ zworker_rlimit_nofile 65535;, k) t. y9 ^/ |5 p
events {0 I' r+ {! g L" e$ Z
use epoll;" U2 t {( s- y$ w4 s- I# w
worker_connections 65535;% ?2 C' \: n2 f3 Z0 L8 i9 l" [
}
5 I0 e, n4 I0 l; T `; q2 Rhttp {* I" u5 ~3 ]. ]
include mime.types;
4 n% x4 N1 x* v* V2 i5 s: f) z- X# V& q default_type application/octet-stream;
& a& J0 F/ j) @ include /usr/local/nginx/conf/reverse-proxy.conf;
0 n* u7 v+ P3 g! H* B O; n sendfile on;
, Q+ V3 {; i1 |" z& X. | keepalive_timeout 65;
, E$ K# M* e: R! z- M! V# Y) y gzip on;
; ]3 N: `+ m% ^3 ?7 Z0 K client_max_body_size 50m; #缓冲区代理缓冲用户端请求的最大字节数,可以理解为保存到本地再传给用户
/ O; @0 [: x+ r1 i: } client_body_buffer_size 256k;3 \! ^' {% S: U1 S
client_header_timeout 3m;
- e: R2 q7 e# K! ? client_body_timeout 3m;7 z! O) W3 T4 M. C3 K# N4 ^) e0 O
send_timeout 3m;
& c" v* W0 D5 }: ?7 Z- [4 \ proxy_connect_timeout 300s; #nginx跟后端服务器连接超时时间(代理连接超时)- v7 W. p4 l( x; t6 v
proxy_read_timeout 300s; #连接成功后,后端服务器响应时间(代理接收超时)' Q" R J3 }0 q
proxy_send_timeout 300s;
9 n: y% i @7 |3 b proxy_buffer_size 64k; #设置代理服务器(nginx)保存用户头信息的缓冲区大小
0 y+ D5 V$ Y2 U" p proxy_buffers 4 32k; #proxy_buffers缓冲区,网页平均在32k以下的话,这样设置, P3 c" d: r# @. J
proxy_busy_buffers_size 64k; #高负荷下缓冲大小(proxy_buffers*2)
2 P! ^2 e& y4 G# V proxy_temp_file_write_size 64k; #设定缓存文件夹大小,大于这个值,将从upstream服务器传递请求,而不缓冲到磁盘! s9 g" _: g b! K* E4 ]
proxy_ignore_client_abort on; #不允许代理端主动关闭连接$ z6 Y" n/ N! d5 e
server {
; v2 Q& {! \2 N listen 80;) `% g3 ~6 u, f
server_name localhost;
0 v; o9 z2 F3 g1 C2 T4 d location / {9 M6 S" f0 B: E4 a3 t$ h, i3 z
root html;! B$ J2 X/ y0 V Y6 A+ K& ]) `
index index.html index.htm;
3 S: O! @2 @8 H! d. z }: z; P0 l1 V4 A+ x( Q5 u/ t8 e( a
error_page 500 502 503 504 /50x.html;. T( H/ {1 C- S5 v' a: Z
location = /50x.html {
. J- I5 J+ o5 y# b root html;4 Q5 |" ]: m! F" V# y
}
3 m0 m) s1 M; k }$ x3 \3 |8 b1 U
}
7 y- y' P3 J) u9 c3 P k3 r" [3 I: W/ _% I2 G' h2 i
编辑反向代理服务器配置文件:+ f5 o% D8 l1 l) ]" V* l% ]* R
+ _) Q3 \. B2 f1 H, Y6 p* Vvim /usr/local/nginx/conf/reverse-proxy.conf
}* i0 Y( k9 I: ~2 f6 T6 e# f
, I# R9 g+ S( V" ]server
5 D! K q+ }/ y; H: u* z{
0 g; G" {( M/ V2 U5 {- Y4 [* L x listen 80;
" o/ ?/ ?5 h' }! k% w4 T5 h O" \( o server_name xxx123.tk;
5 I& c D- N/ Y% G' g4 t6 P location / {
0 V8 l$ g+ S7 ^7 V* |! t proxy_redirect off;
" |) ^( k( I" E, c: q" } proxy_set_header Host $host;
9 I& ~# }* S, Q) Z3 b- X proxy_set_header X-Real-IP $remote_addr;
/ z+ @8 G2 s' ~* [" I proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
' I( l3 o6 s; Q8 j$ s3 U proxy_pass http://192.168.10.38:3000;, I& M9 G$ F$ B6 [
}
) |0 F |, f$ F access_log logs/xxx123.tk_access.log;6 h* H m! \+ i. p
}
5 @* v8 P$ d1 b, Z d3 h* H1 ~
3 p2 |/ d7 e$ M0 hserver
* S& Q/ {* a* c7 a{0 ~7 B0 T; C2 c5 I4 W
listen 80;' E0 G2 S& M& Y# q# s
server_name xxx456.tk; Z9 ~, a# ?8 z
location / {+ l, ?1 K, e7 k
proxy_redirect off;& `4 V1 `' B% b5 h
proxy_set_header Host $host;6 q8 K6 _- ~9 j, `$ m1 V, _
proxy_set_header X-Real-IP $remote_addr;6 [" }, u6 b- r
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;6 R0 E0 T; w8 S( {
proxy_pass http://192.168.10.40:80;
8 c8 Z2 w6 ~' z6 m6 s8 i, E3 K& l. H }
i# Y2 f) S% }) c# F& T access_log logs/xxx456.tk_access.log;
" V: g5 Z5 j; i9 A6 n}
" \& l' y6 z0 P+ _+ |
7 `* Z9 i) P5 l: [5 ~( g然后重新加载nginx配置文件,使之修改生效,再把xxx123.tk域名指向公司静态IP,这样就成功的做到了在浏览器中输入xxx123.tk的时候访问的内网服务器192.168.10.38的3000端口,输入xxx456.tk访问192.168.10.40的80端口的作用。 如果想对后端机器做负载均衡,像下面这配置就可以把对nagios.xxx123.tk的请求分发给内网的131和132这两台机器做负载均衡了。
6 g# l6 u) u& l& t7 O$ a# O
! i: U/ h+ o0 R9 d' D$ H2 Supstream monitor_server {' g" u2 {1 `( y9 @+ N
server 192.168.0.131:80;
6 S/ {. y& F; o- Y+ h server 192.168.0.132:80;9 J3 T% f" r) X! x. c$ ?# [5 d
}4 l1 x# B7 Q3 \1 K& o/ n2 \, P
0 s% f; q6 _0 A+ Q# ^/ d" ?& H
server
, W6 Z' h& [2 J{
- o+ G* a! V8 a! L% k listen 80;
. {2 w5 \6 C. H9 ^( \7 D( L server_name nagios.xxx123.tk;
9 M! l7 o1 _/ {) q! c! K" r location / {
9 y) G' i4 K& y2 `6 |. n proxy_redirect off;
8 E- x" t! _% F2 r! n' a proxy_set_header Host $host;$ E8 s G( K+ o" t% M
proxy_set_header X-Real-IP $remote_addr;6 u1 A- w8 v4 f6 l* Z/ U& z; M
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; ( v) S" \7 b# w1 Q- V3 f6 x% T9 m2 b
proxy_pass http://monitor_server;0 a5 r- v# r* T4 w) P' M
}9 }, C' ]$ p4 j8 l
access_log logs/nagios.xxx123.tk_access.log;6 x% F: Y. P. D$ E% e
}
E/ j V! J$ O
2 _( ^. B; q5 u. z2 p0 v额,关于负载均衡和缓存就不多说了,这里只是要起到一个简单的“域名转发”功能。 另外,由于http请求最后都是由反向代理服务器传递给后段的机器,所以后端的机器原来的访问日志记录的访问IP都是反向代理服务器的IP。 要想能记录真实IP,需要修改后端机器的日志格式,这里假设后端也是一台nginx: 在后端配置文件里面加入这一段即可:
. j) b p* m5 k: K0 C( @0 @7 x
log_format access '$HTTP_X_REAL_IP - $remote_user [$time_local] "$request" '
4 c# W. y; _4 v- ]& N# W7 ]* k; }'$status $body_bytes_sent "$http_referer" '
) Q& U% c8 j L1 X8 x'"$http_user_agent" $HTTP_X_Forwarded_For';8 l9 {0 C: u. v a) {; _* T h* ^
7 y; O8 z4 v# [1 a) N+ E& zaccess_log logs/access.log access;
+ n: I5 C6 ?6 @3 [6 q4 s6 J# E; S# D( T
/ M- B$ G. R3 i- A8 A再看看原来日志的格式长什么样:
4 X5 k5 \ E( i5 K. f0 A' y* l5 ?5 P! b3 W2 K
19 k( p. v) ?2 ^
2
/ c' j' P/ ^0 ]" d5 V1 }+ S( ^3, v! N5 F1 w8 Q
4
# L6 }2 c6 x0 C5) ~3 w% a/ t+ i$ j, r J4 G9 |
#log_format main '$remote_addr - $remote_user [$time_local] "$request" ') R9 Y: [# j- e. T
# '$status $body_bytes_sent "$http_referer" '8 S/ q8 z( z3 J( b* Z3 {
# '"$http_user_agent" "$http_x_forwarded_for"';
. Y$ X. X. N7 V$ Z% T4 z
+ j2 Z! G+ B0 f6 D#access_log logs/access.log main;
6 D% J" P# D3 T. T/ N看出区别了吧 遇到的问题 之前没配置下面这段,访问时候偶尔会出现504 gateway timeout,由于偶尔出现,所以不太好排查
Q7 A' v! v& i' U5 W6 [( n
# r& K0 _! T! w4 g. ^; H1
( p, o- {" Z4 X3 Q+ a1 V9 f5 [/ r2
: {6 g. H' l: C. d. B: y a& E35 V: K% h; E% `) @: L H% f( g1 ~
4
( t/ Q) {" q) ^) |3 F; q) b5
% l. K" i8 o1 v) W% z6
' G# Y2 v" X" j! z! s8 u3 k3 |7+ U. S) |% r, {7 F$ Z! ^
8) m3 B o3 A6 I1 w2 K% c
proxy_connect_timeout 300s;" d# r# E1 J+ U3 f3 _1 B+ j' C
proxy_read_timeout 300s;
1 u6 \" c& ~' o5 L( [% E8 K: `, ?/ t% O4 zproxy_send_timeout 300s;
& c" a: ?6 R# w4 V1 O5 S) z; b, i$ i$ Y, Zproxy_buffer_size 64k;' o6 `9 l9 L( x( T
proxy_buffers 4 32k;
# M! W3 O4 z5 }3 G, _. X6 \9 [proxy_busy_buffers_size 64k;
$ m' g! c4 U8 Q6 U% z& X+ \# tproxy_temp_file_write_size 64k;- v: L" r+ n) H, c6 u. L; A
proxy_ignore_client_abort on;! Y K% I# M/ Z* H# i1 c
报错日志:0 A/ p2 n: r( Q6 E1 X
3 L6 {2 v; k4 e& d. `8 Y...upstream timed out (110: Connection timed out) while reading response header from upstream, client: ...(后面的省略) 从日志看来是连接超时了,网上一通乱查之后估计可能是后端服务器响应超时了,本着大胆假设,小心求证的原则,既然假设了错误原因就要做实验重现错误:那就调整代理超时参数,反过来把代理超时阀值设小(比如1ms)看会不会次次出现504。后来发现把proxy_read_timeout 这个参数设置成1ms的时候,每次访问都出现504。于是把这个参数调大,加入上面那段配置,解决问题了。 D2 n3 @; l5 a/ P/ F) H
/ [" z8 J' a# p7 _3 R) @
PS:关于域名转发
' G/ k& `- _' u1 p2 V9 A [6 T+ F
1 Y3 A. J9 E" l; E8 ^1 M1 b8 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/ 的内容。
6 `7 V/ \* ]( _, T/ ?/ ?' ] H* V |
|