Scenario
Because the company's intranet has multiple servers whose http services need to be mapped to the company's Internet static IP address, if you use the routing Port ing, you can only map the port 80 of an intranet server to the Internet port 80, port 80 of other servers can only be mapped to non-Port 80 of the Internet. Non-Port 80 ing requires adding ports to the domain name during access, which is troublesome. In addition, the company's entry route can only perform 20 Port ing at most. It is definitely not enough in the future.
Then, brother k proposed to build an nginx Reverse proxy server on the intranet to map 80 of the nginx Reverse proxy server to 80 of the Internet IP address, in this way, the HTTP request directed to the domain name of the company's Internet IP address will be sent to the nginx Reverse proxy server, and the nginx Reverse proxy will be used to forward requests from different domain names to ports of different machines on the intranet, the "automatically forwarded to the specific port of the corresponding server based on the domain name" effect is achieved, while the port ING of the router only achieves "automatically forwarded to the specific port of the corresponding server based on different ports ", it's really great.
Knowledge: nginx compilation and installation, basic configuration of nginx Reverse proxy, knowledge of routing Port ing, and knowledge of network domain names.
The goal of this experiment is to: enter 111cn.net in the browser to access port 3000 of the intranet machine 192.168.10.38, and enter xxx456.tk to access port 80 of the intranet machine 192.168.10.40.
Procedure
Server ubuntu 12.04
### Update a repository
The code is as follows: |
Copy code |
Apt-get update-y
Apt-get install wget-y |
# Download nginx and related software packages
Pcre is used to compile the rewrite module, and zlib is used to support the gzip function. Yes, here the nginx version is a little old, because I want to upgrade the nginx experiment. You can install a new version.
The code is as follows: |
Copy code |
Cd/usr/local/src
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> Wget <a href = "http://zlib.net/zlib-1.2.8.tar.gz"> http://zlib.net/zlib-1.2.8.tar.gz </a> Wget <a href = "http://nginx.org/download/nginx-1.4.2.tar.gz"> http://nginx.org/download/nginx-1.4.2.tar.gz </a> Tar xf pcre-8.33.tar.gz Tar xf zlib-1.2.8.tar.gz # Install the compiling environment Apt-get install build-essential libtool-y # Create an nginx user
|
The so-called unprivileged user
The code is as follows: |
Copy code |
Useradd-s/bin/false-r-M-d/nonexistent www # Start compilation and installation
/Configure -- with-pcre =/usr/local/src/pcre-8.33 -- with-zlib =/usr/local/src/zlib-1.2.8 -- user = www -- group = www
-- With-http_stub_status_module -- with-http_ssl_module -- with-http_realip_module Make Make install # Authorize a folder Chown-R www: www/usr/local/nginx # Modifying the configuration file Vim nginx. conf
User www;
Worker_processes 1; Error_log logs/error. log; Pid logs/nginx. pid; Worker_rlimit_nofile 65535; Events { Use epoll; Worker_connections 65535; } Http { Include mime. types; Default_type application/octet-stream; Include/usr/local/nginx/conf/reverse-proxy.conf; Sendfile on; Keepalive_timeout 65; Gzip on; Client_max_body_size 50 m; # maximum number of bytes for the buffer proxy to buffer user-side requests. Client_body_buffer_size 256 k; Client_header_timeout 3 m; Client_body_timeout 3 m; Send_timeout 3 m; Proxy_connect_timeout 300 s; # timeout for nginx connection to backend servers (proxy connection timeout) Proxy_read_timeout 300 s; # response time of the backend server after successful connection (proxy receiving timeout) Proxy_send_timeout 300 s; Proxy_buffer_size 64 k; # set the buffer size for the proxy server (nginx) to save user header information Proxy_buffers 4 32 k; # proxy_buffers buffer, if the average web page is below 32 k, this setting Proxy_busy_buffers_size 64 k; # buffer size under high load (proxy_buffers * 2) Proxy_temp_file_write_size 64 k; # sets the cache folder size. If the size is greater than this value, requests will be transmitted from the upstream server without buffering to the disk. Proxy_ignore_client_abort on; # The proxy is not allowed to close the connection. Server { Listen 80; Server_name localhost; Location /{ Root html; Index index.html index.htm; } Error_page 500 502 503 x.html; Location =/50x.html { Root html; } } } |
Edit the configuration file of the reverse proxy server:
The code is as follows: |
Copy code |
Vim/usr/local/nginx/conf/reverse-proxy.conf Server
{ Listen 80; Server_name 111cn.net; Location /{ Proxy_redirect 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; Proxy_pass http: // 192.168.10.38: 3000; } Access_log logs/111cn.net _ access. log; } Server { Listen 80; Server_name www.111cn.net; Location /{ Proxy_redirect 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; Proxy_pass http: // 192.168.10.40: 80; } Access_log logs/xxx456.tk _ access. log; } |
Then, reload the nginx configuration file to make the modification take effect, and then direct the 111cn.net domain name to the company's static IP address, in this way, port 3000 of 192.168.10.38 of the intranet server accessed when 111cn.net is input in the browser, and Port 80 of 192.168.10.40 is accessed by xxx456.tk.
If you want to perform load balancing on the backend machines, you can use the following configuration to distribute requests to nagios.111cn.net to the intranet machines 131 and 132 for load balancing.
The code is as follows: |
Copy code |
Upstream monitor_server { Server 192.168.0.131: 80; Server 192.168.0.132: 80; } Server { Listen 80; Server_name nagios.111cn.net; Location /{ Proxy_redirect 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; Proxy_pass http: // monitor_server; } Access_log logs/nagios.111cn.net _ access. log; } |
Yes, I will not talk much about load balancing and caching. Here we just want to provide a simple "domain name forwarding" function.
In addition, because http requests are finally transmitted to the back-end machines by the reverse proxy server, the access IP addresses recorded in the original access logs of the back-end machines are the IP addresses of the reverse proxy server.
To record the real IP address, you need to modify the log format of the backend machine. Here we assume that the backend is also an nginx:
Add this section to the backend configuration file:
The code is as follows: |
Copy code |
Log_format access' $ HTTP_X_REAL_IP-$ remote_user [$ time_local] "$ request "'
'$ Status $ body_bytes_sent "$ http_referer "' '"$ Http_user_agent" $ HTTP_X_Forwarded_For '; Access_log logs/access. log access; |
Let's look at the format of the original log:
The code is as follows: |
Copy code |
# 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 logs/access. log main; |
See the difference.
Problems encountered
• The following section is not configured before, and 504 gateway timeout may occasionally occur during access. Due to the occasional appearance, troubleshooting is not good.
The code is as follows: |
Copy code |
Proxy_connect_timeout 300 seconds; Proxy_read_timeout 300 seconds; Proxy_send_timeout 300 s; Proxy_buffer_size 64 k; Proxy_buffers 4 32 k; Proxy_busy_buffers_size 64 k; Proxy_temp_file_write_size 64 k; Proxy_ignore_client_abort on; |
Error log:
... Upstream timed out (110: Connection timed out) while reading response header from upstream, client:... (omitted later)
From the log, it seems that the connection times out. It is estimated that the backend server response may have timed out after a disorderly query on the internet. Based on bold assumptions and the principle of careful proof, we have to experiment to reproduce the error since the cause of the error is assumed: then adjust the proxy timeout parameter, and set the proxy timeout threshold to a smaller value (for example, 1 ms) to see if 504 is returned for the next time. Later, we found that when we set the proxy_read_timeout parameter to 1 ms, 504 is displayed for each access. So we increased this parameter and added the above configuration to solve the problem.