What does the $http_x_real_ip variable mean in the Nginx log_format directive? I’m studying a working Nginx configuration and came across this variable in the logging format. I can’t find information about it in the official Nginx documentation. Is this a custom variable that I need to search for in the configuration, or is it a standard variable that is not documented?
The $http_x_real_ip Variable in Nginx
The $http_x_real_ip variable in Nginx is a standard system variable that contains the value of the HTTP header X-Real-IP. This variable is used to access the real client IP address passed through proxy servers or CDNs and is part of Nginx’s built-in variable system, where the $http_ prefix indicates access to HTTP header values.
Table of Contents
- What is $http_x_real_ip
- How the $http_x_real_ip variable works
- Examples of use in log_format
- Differences from other IP variables
- Configuration and setup
- Security and validation
- Conclusion
What is $http_x_real_ip
The $http_x_real_ip variable is part of Nginx’s standard set of variables that provides access to HTTP header values. In Nginx, there is a general variable system where any HTTP header can be accessed through a variable named $http_<header_name>, where the header name is converted to lowercase and hyphens are replaced with underscores.
Thus, the $http_x_real_ip variable directly corresponds to the HTTP header X-Real-IP, which is commonly used by proxy servers and CDNs to pass the real client IP address through a proxy chain.
Important: This variable is not a custom or user-defined variable — it is a standard part of Nginx and available in all Nginx builds since early versions.
How the $http_x_real_ip variable works
When a request passes through Nginx, the server automatically creates variables for all received HTTP headers. The process with $http_x_real_ip can be described as follows:
- The client sends a request through a proxy server
- The proxy server adds the
X-Real-IPheader with the real client IP address - Nginx receives this header and creates the corresponding
$http_x_real_ipvariable - In the Nginx configuration, this variable can be used in directives, including
log_format
Example of basic usage:
log_format main '$http_x_real_ip - $remote_user [$time_local] "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent"';
This log format will display the real client IP address passed through the X-Real-IP header.
Examples of use in log_format
Various examples of using $http_x_real_ip in the log_format directive were found in the researched configurations:
Basic format with real IP
log_format specialLog '$remote_addr forwarded for $http_x_real_ip - $remote_user [$time_local] "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent"';
Combined format with multiple IP headers
log_format combined_realip '$http_x_forwarded_for - $remote_user [$time_local] "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent"';
Cloudflare format
log_format combined_realip_cf '$http_cf_connecting_ip $http_x_forwarded_for - $remote_user [$time_local] "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent"';
Comparison table of logging formats
| Format | Description | Example usage |
|---|---|---|
| Main | Standard format with real IP | Basic logging |
| Special | Indicates proxy chaining | Request route analysis |
| Cloudflare | Optimized for CDN | Working with Cloudflare |
As noted in research, for Nginx, you can simply use the $http_x_real_ip variable instead of the IP address to get the real client IP passed through the header.
Differences from other IP variables
It’s important to understand the differences between various IP variables in Nginx:
IP Variables Comparison
| Variable | Description | When used |
|---|---|---|
$remote_addr |
IP address of the last proxy server | Direct connection to Nginx |
$http_x_forwarded_for |
Chain of IP addresses through proxies | Standard XFF header |
$http_x_real_ip |
Real client IP | X-Real-IP header |
$http_cf_connecting_ip |
IP from Cloudflare | Working with Cloudflare |
As explained in Stack Overflow discussions, the choice between headers depends on the type of proxy server used and whether the received data can be trusted.
Configuration and setup
Correct operation with $http_x_real_ip may require additional Nginx configuration:
Basic configuration
http {
log_format main '$http_x_real_ip - $remote_user [$time_local] "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent"';
server {
access_log /var/log/nginx/access.log main;
}
}
Configuration with realip module
If using the ngx_http_realip_module, you can trust certain proxy servers:
http {
set_real_ip_from 192.168.1.0/24;
set_real_ip_from 10.0.0.0/8;
real_ip_header X-Real-IP;
log_format main '$remote_addr - $remote_user [$time_local] "$request" $status $body_bytes_sent "$http_referer" "$http_user_agent"';
}
As specified in the Nginx documentation, with recursive search disabled, the original client address matching one of the trusted addresses is replaced with the last address sent in the request header.
Security and validation
When using $http_x_real_ip, it’s important to consider security aspects:
Checking trusted proxies
http {
# Trust only specific proxy servers
set_real_ip_from 192.168.1.0/24;
set_real_ip_from 10.0.0.0/8;
real_ip_header X-Real-IP;
}
Protection against IP spoofing
As noted in Server Fault answers, by default, real_ip_header uses X-Real-IP, which means a malicious user can send a request with a random X-Real-IP and it will be used as $remote_addr.
Security recommendations
- Always specify trusted proxy servers through
set_real_ip_from - Use secure network segments for trust
- Consider using PROXY Protocol for more reliable IP transmission
- Validate IP addresses in your application
Conclusion
-
$http_x_real_ip is a standard Nginx variable containing the value of the
X-Real-IPheader, not a user-defined variable. -
Main purpose — to access the real client IP address passed through proxy servers or CDNs as an HTTP header.
-
Use in log_format allows including the real IP address in logs instead of the last proxy server’s IP address, which is important for analysis and monitoring.
-
Security configuration requires specifying trusted proxy servers through
set_real_ip_fromto prevent IP address spoofing. -
Alternative headers — depending on the infrastructure, you can use
X-Forwarded-For,CF-Connecting-IP, or other headers through the corresponding Nginx variables.
For deeper study, I recommend reviewing the official ngx_http_realip_module documentation and examining configuration examples in real projects.
Sources
- NGINX access_log: log the real client IP from X-Forwarded-For/X-Real-IP/cf-connecting-ip instead of the proxy IP
- nginx with real_ip – log both client remote_addr and proxies address - Server Fault
- NGINX and X-Forwarded-For Header (XFF) | Loadbalancer
- Get user real ip in nginx behind nginx reverse proxy – Yannick Pereira-Reis
- Module ngx_http_realip_module - Nginx Documentation
- Forwarding Visitor’s Real-IP in Nginx Proxy/Fastcgi backend correctly
- Difference between X-Forwarded-For and X-Real-IP headers - Stack Overflow
- How to use multiple real IP headers with nginx | Medium