How to get user IP on Nginx, the second layer of the two-tier server
1. I encountered a problem when configuring nginx server before. Previously, the server used a function to limit the maximum concurrent connections of the client, and the implementation of this function relied on
$remote-addr
such configuration in the server. achieved. But after adding a front-end layer (load, CDN, firewall, security service) server, the client IP obtained becomes the IP of the front-end server, not the real user IP address.
2. Faced with such a problem, I re-read the introduction of nginx official website several times and found another particularly important variable
$proxy_add_x_forwarded_for
This variable is the value of the X-forwarded-for field in the client access request. If the request does not contain this field, the automatic use of this variable will be equivalent to the remote-addr variable. This allows us to obtain the field of the client's real IP address that is usually saved by the front-end server in the HTTP request, usually what we call the X_FORWARDED_FOR field, and then through this method, we can implement a variety of functions.
Three. Let me give you a simple demonstration below. There are many deficiencies, please correct me.
First we set up the Nginx environment. Here we use the latest version 1.7.9 of the 1.7 series as an example. (For version issues, please see FAQ 1)
Download and WGET required address http://nginx.org/ download/nginx-1.7.9.tar.gz
1. Download Nginx
[lugt@localhostmysql]$ wget http://nginx.org/download/nginx-1.7.9.tar.gz
2. Unzip
[lugt@localhostmysql]$ tar zxvf nginx-1.7.9.tar.gz
3. Compile directly (you need to consider whether you need the support of plug-ins such as openssl)
[lugt@localhost mysql]$cd nginx-1.7. 9
[lugt@localhost nginx-1.7.9]$ ./configure
[lugt@localhost nginx-1.7.9]$ make
[lugt@localhost nginx-1.7.9]$ su
[lugt@ localhostnginx-1.7.9]$ make install
4. Then modify the nginx.conf configuration file
[lugt@localhost nginx-1.7.9]$ su
[lugt@localhost nginx-1.7.9]$cd /usr/local/nginx
[lugt@localhostnginx]$ vi conf/nginx.conf
Then find this in nginx.conf, add it to set up load balancing, imitate CDN
upstream dnsnginx1 { server[*.*.*.*/yourhostname]:8080 weight=10000; #填IP、域名 } server { listen 80; server_name #access_log logs/host.access.log main location /{ proxy_pass http://dnsnginx1; 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_set_header HTTP_X_FORWARDED_FOR $remote_addr; proxy_redirect default; } }
and set up a virtual server at 8080 Port,
limit_conn_zone $proxy_add_x_forwarded_for zone=addr:10m; # 并发设置 空间10M server { listen 8080; server_name [*.*.*.*/yourhostname]:8080 weight=10000; #填IP、域名 limit_conn addr 1; #限制客户端最大并发连接数为 1 location / { root html; index index.html index.htm; } }
saved. Then test the configuration file syntax
[lugt@localhostnginx]$ ./sbin/nginx –t
Start the server
[lugt@localhostnginx]$ ./sbin/nginx
IV. Use the ab tool to see the effect.
[lugt@localhost nginx]$ ab –c 10 –n 100 –v 4 http://127.0.0.1/ | grep HTTP/1.1
The meaning of this line: access the address through the AB testing tool, the number of concurrent connections is 30, total test 300 times, display HTTP return header information
Using the ab tool, it can be measured that no matter how many connections are sent at the same time, the only one that successfully returns 200 in the end is the maximum number of concurrent connections that previously limited nginx, so it can be proved that the IP restriction function has been Ready to use. For reference data, see FAQ2
FAQ 1 Version issue
If the Nginx version currently in use has not reached version 1.7.1, it is likely that nginx does not support this function.
At this time, you need to use a piece of code to sandwich the limit_conn_handler function. Get the value of x_forwarded_for from request.
Taking version 1.6.1 as an example, the code is added as follows. src/http/modules/ngx_http_limit_conn.c Line 184
hash =ngx_crc32_short(key.data, key.len); If(“” == &ctx->key){ <span style="white-space:pre"> </span>If(NULL!= r->main->headers_in->x_forwarded_for->elts){ key.data= *(char*)r->main->headers_in->x_forwarded_for->elts; key.len = 4; hash =ngx_crc32_short(key.data, key.len); <span style="white-space:pre"> </span>} }
100-v 4 http://127.0.0.1/ | grep HTTP/1.1
HTTP/1.1503 Service Temporarily UnavailableHTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1 503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1 200 OK
HTTP/ 1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1 200 OK
English Version
How to retrievethe true ip of the client user if there are two layers of servers
Days before, wehave been faced such a difficulty which is we can’t use the variable $remote_addr for gathering the clients’ip address. This problem surfaces when we used a proxy server between the trueserver and client, which is actually a cdn. And that makes our functions oflimiting the maximum connections a client can make to a server at a time. Thissituation can also found if the load balance or any anti-spam service are inuse. So that’s why we can’t use remote_addr variable further.
After I did someresearch on the documentation and the code , I found out that this problem canbe solved by replacing the
$remote_addr
variable with the
$proxy_add_x_forwarded_forvariable. As this variable allows to retrievethe data from the column X_forwarded_for from the request, we can use thisvariable functioning in many ways.
And now I shall makean easy example to practically use this method.
First of all,build up a Nginx server.
Here, I will usethe 1.7.9 version (latest to the written time) for instance, therefore, thereexist some differences between older versions than 1.7.1 (see FAQ 1)
1. Download A Nginx Copy:
[lugt@localhostmysql]$ wget http://nginx.org/download/nginx-1.7.9.tar.gz
2. Decompress the file
[lugt@localhostmysql]$ tar zxvf nginx-1.7.9.tar.gz
3. Compile The Code
[lugt@localhostmysql]$ cd nginx-1.7.9
[lugt@localhostnginx-1.7.9]$ ./configure
[lugt@localhostnginx-1.7.9]$ make
[lugt@localhostnginx-1.7.9]$ su
[lugt@localhostnginx-1.7.9]$ make install
4. And edit the config file nginx.conf
[lugt@localhost nginx-1.7.9]$ su
[lugt@localhostnginx-1.7.9]$ cd /usr/local/nginx
[lugt@localhostnginx]$ vi conf/nginx.conf
There add suchdirectives to the server1 for emulate for an CDN server
upstream dnsnginx1 { server[*.*.*.*/yourhostname]:8080 weight=1000; #fill in your ip/hostname } server { listen 80; server_name [hostname] #fill your ip/ hostname here #access_log logs/host.access.log main location /{ proxy_pass http://dnsnginx1; 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_set_header HTTP_X_FORWARDED_FOR $remote_addr; proxy_redirect default; } }
After the end ofone server directive, and in the http directive, add so to function the sever2
limit_conn_zone $proxy_add_x_forwarded_for zone=addr:10m; # sample setting server { listen 8080; server_name [*.*.*.*/hostname]:8080 weight=10000; #fill in ip/hostname here limit_conn addr 1; # Enablethe limitation of connection per ip at a time to 1. location / { root html; index index.html index.htm; } }
And then you cansave , test the config file and run nginx
Test your configfile:
[lugt@localhostnginx]$ ./sbin/nginx –t
Start the nginx server
[lugt@localhostnginx]$ ./sbin/nginx
Now, the serverhas been set and you can run a test at instance.
/* This CommandMeans to run a tool to connect to server as 10conn/once and 10 conns in total*/
[lugt@localhost~]$ ab -c 10 -n 100 -v 4 http://127.0.0.1/ | grep HTTP/1.1
FAQ 1
There is actuallysome little malfunctions when using elder versions than 1.7.1 (Probably the newversion has it for a new feature).So to use this directive in earlier versions,some code need to be added.
As a Example inthe version 1.6.1
In filesrc/http/modules/ngx_http_limit_conn.c Line around 184
hash =ngx_crc32_short(key.data, key.len); If("" == &ctx->key){ If(NULL!= r->main->headers_in->x_forwarded_for->elts){ key.data= *(char*)r->main->headers_in->x_forwarded_for->elts; key.len = 4; hash =ngx_crc32_short(key.data, key.len); }
}<span style="font-family: Arial, Helvetica, sans-serif;"> </span>
FAQ 2 TestingResults
[lugt@localhost~]$ ab -c 10 -n 100 -v 4 http://127.0.0.1/ | grep HTTP/1.1
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1 200 OK
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP /1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1503 Service Temporarily Unavailable
HTTP/1.1 200 OK
The above introduces how to obtain the user IP on the second layer Nginx of the two-layer server, including the relevant content. I hope it will be helpful to friends who are interested in PHP tutorials.

APHPDependencyInjectionContainerisatoolthatmanagesclassdependencies,enhancingcodemodularity,testability,andmaintainability.Itactsasacentralhubforcreatingandinjectingdependencies,thusreducingtightcouplingandeasingunittesting.

Select DependencyInjection (DI) for large applications, ServiceLocator is suitable for small projects or prototypes. 1) DI improves the testability and modularity of the code through constructor injection. 2) ServiceLocator obtains services through center registration, which is convenient but may lead to an increase in code coupling.

PHPapplicationscanbeoptimizedforspeedandefficiencyby:1)enablingopcacheinphp.ini,2)usingpreparedstatementswithPDOfordatabasequeries,3)replacingloopswitharray_filterandarray_mapfordataprocessing,4)configuringNginxasareverseproxy,5)implementingcachingwi

PHPemailvalidationinvolvesthreesteps:1)Formatvalidationusingregularexpressionstochecktheemailformat;2)DNSvalidationtoensurethedomainhasavalidMXrecord;3)SMTPvalidation,themostthoroughmethod,whichchecksifthemailboxexistsbyconnectingtotheSMTPserver.Impl

TomakePHPapplicationsfaster,followthesesteps:1)UseOpcodeCachinglikeOPcachetostoreprecompiledscriptbytecode.2)MinimizeDatabaseQueriesbyusingquerycachingandefficientindexing.3)LeveragePHP7 Featuresforbettercodeefficiency.4)ImplementCachingStrategiessuc

ToimprovePHPapplicationspeed,followthesesteps:1)EnableopcodecachingwithAPCutoreducescriptexecutiontime.2)ImplementdatabasequerycachingusingPDOtominimizedatabasehits.3)UseHTTP/2tomultiplexrequestsandreduceconnectionoverhead.4)Limitsessionusagebyclosin

Dependency injection (DI) significantly improves the testability of PHP code by explicitly transitive dependencies. 1) DI decoupling classes and specific implementations make testing and maintenance more flexible. 2) Among the three types, the constructor injects explicit expression dependencies to keep the state consistent. 3) Use DI containers to manage complex dependencies to improve code quality and development efficiency.

DatabasequeryoptimizationinPHPinvolvesseveralstrategiestoenhanceperformance.1)Selectonlynecessarycolumnstoreducedatatransfer.2)Useindexingtospeedupdataretrieval.3)Implementquerycachingtostoreresultsoffrequentqueries.4)Utilizepreparedstatementsforeffi


Hot AI Tools

Undresser.AI Undress
AI-powered app for creating realistic nude photos

AI Clothes Remover
Online AI tool for removing clothes from photos.

Undress AI Tool
Undress images for free

Clothoff.io
AI clothes remover

Video Face Swap
Swap faces in any video effortlessly with our completely free AI face swap tool!

Hot Article

Hot Tools

Dreamweaver Mac version
Visual web development tools

SublimeText3 Mac version
God-level code editing software (SublimeText3)

EditPlus Chinese cracked version
Small size, syntax highlighting, does not support code prompt function

MinGW - Minimalist GNU for Windows
This project is in the process of being migrated to osdn.net/projects/mingw, you can continue to follow us there. MinGW: A native Windows port of the GNU Compiler Collection (GCC), freely distributable import libraries and header files for building native Windows applications; includes extensions to the MSVC runtime to support C99 functionality. All MinGW software can run on 64-bit Windows platforms.

SecLists
SecLists is the ultimate security tester's companion. It is a collection of various types of lists that are frequently used during security assessments, all in one place. SecLists helps make security testing more efficient and productive by conveniently providing all the lists a security tester might need. List types include usernames, passwords, URLs, fuzzing payloads, sensitive data patterns, web shells, and more. The tester can simply pull this repository onto a new test machine and he will have access to every type of list he needs.
