Nginx set_real_ip_from, real_ip_recursive & Cloudflare IP Restoration in Pakistan

Restore genuine Pakistani visitor IP addresses behind Cloudflare and reverse proxies using Nginx ngx_http_realip_module and real_ip_recursive anti-spoofing.

Nginx set_real_ip_from, real_ip_recursive & Cloudflare IP Restoration in Pakistan

Web applications, media portals, and e-commerce platforms in Pakistan widely utilize reverse proxy CDNs (such as Cloudflare, Fastly, or local caching edge nodes) for DDoS mitigation and global edge caching. However, routing all web traffic through an edge proxy introduces a critical architectural issue on origin servers: IP Address Masking.

Because the reverse proxy establishes a new TCP connection to your origin server, Nginx sees the proxy’s IP address (e.g. 172.68.x.x or 108.162.x.x) as the client IP ($remote_addr). This creates severe operational and security breakdowns:

  1. Broken Access Logs & Auditing: Access logs show millions of requests originating from only 10 or 15 Cloudflare edge IPs.
  2. Paralyzed Rate Limiting: A rate limiting rule (limit_req_zone $binary_remote_addr ...) accidentally groups hundreds of genuine Pakistani visitors into the same IP bucket, blocking legitimate customers!
  3. Flawed Fraud Detection & Geolocation: Payment gateways and banking modules cannot determine whether a customer is located in Karachi, Lahore, or an untrusted offshore VPN.
  4. Header Spoofing Vulnerabilities: Naively trusting client-supplied headers like X-Forwarded-For without validating proxy hops allows malicious actors to forge arbitrary IP addresses simply by injecting custom HTTP headers!

By deploying bare-metal Dedicated Servers and configuring Nginx’s ngx_http_realip_module with real_ip_recursive on; and automated trusted proxy CIDR whitelisting, engineers can safely restore genuine visitor IPs while preventing header forgery.


The Anatomy of IP Spoofing vs. real_ip_recursive Traversal

When an HTTP request passes through multiple proxy layers, each proxy appends the connecting client’s IP to the comma-separated X-Forwarded-For header:

X-Forwarded-For: Client_IP, Proxy_1, Proxy_2

An attacker can deliberately spoof this header by sending:

X-Forwarded-For: 127.0.0.1, 8.8.8.8
Attacker Sends Request with Injected Header:
  curl -H "X-Forwarded-For: 10.0.0.1" https://yourdomain.pk/

Path Traversal:
  [Attacker: 39.40.12.18] ──> [Cloudflare Edge: 172.70.142.10] ──> [Origin Nginx]

Without real_ip_recursive (Vulnerable):
  Nginx reads the first IP in the list:
  Nginx believes the client is 10.0.0.1! (SPOOF SUCCESSFUL!)

With real_ip_recursive on (Secure):
  1. Origin Nginx inspects the chain from RIGHT to LEFT:
     - 172.70.142.10 (Matches set_real_ip_from trusted CIDR -> SKIPPED)
     - 39.40.12.18   (NOT in trusted proxy list! -> ELECTED AS REAL CLIENT IP!)
     - 10.0.0.1      (Ignored as unverified spoofed payload!)
  2. Nginx sets $remote_addr = 39.40.12.18 (True Pakistani Visitor IP!)

Step 1: Verifying the Nginx Real-IP Module

Ensure your Nginx binary includes the http_realip_module:

nginx -V 2>&1 | grep -o "with-http_realip_module"

If compiled with the module, Nginx is equipped to dynamically rewrite $remote_addr in memory before requests are evaluated by security or logging directives.


Step 2: Automated Cloudflare IP CIDR Synchronization Script

Cloudflare publishes an authoritative list of IPv4 and IPv6 IP ranges. Because Cloudflare periodically adds or modifies transit subnets, administrators must automate the creation of the trusted proxy configuration file.

Create an automated synchronization script /usr/local/bin/update_cloudflare_ips.sh:

#!/bin/bash
# /usr/local/bin/update_cloudflare_ips.sh
# NextGen Pakistan - Automated Cloudflare Real-IP Synchronization

TARGET_CONF="/etc/nginx/conf.d/cloudflare_real_ip.conf"
TMP_CONF="/tmp/cloudflare_real_ip.conf.tmp"

echo "# Cloudflare Trusted Proxy CIDR Blocks - Generated on $(date)" > $TMP_CONF

# Fetch official IPv4 ranges
curl -sL https://www.cloudflare.com/ips-v4 | while read -r line; do
    if [[ ! -z "$line" ]]; then
        echo "set_real_ip_from $line;" >> $TMP_CONF
    fi
done

# Fetch official IPv6 ranges
curl -sL https://www.cloudflare.com/ips-v6 | while read -r line; do
    if [[ ! -z "$line" ]]; then
        echo "set_real_ip_from $line;" >> $TMP_CONF
    fi
done

# Include local proxies / load balancers if applicable
echo "set_real_ip_from 127.0.0.1;" >> $TMP_CONF
echo "set_real_ip_from 10.0.0.0/8;" >> $TMP_CONF

# Configure header and recursive traversal
echo "real_ip_header CF-Connecting-IP;" >> $TMP_CONF
echo "real_ip_recursive on;" >> $TMP_CONF

# Validate syntax before replacing production file
cp $TMP_CONF $TARGET_CONF
nginx -t > /dev/null 2>&1

if [ $? -eq 0 ]; then
    systemctl reload nginx
    echo "Cloudflare IPs updated and Nginx reloaded successfully!"
else
    echo "ERROR: Nginx syntax check failed! Configuration not applied."
    exit 1
fi

Make the script executable and run it:

chmod +x /usr/local/bin/update_cloudflare_ips.sh
/usr/local/bin/update_cloudflare_ips.sh

Add a monthly cron job in /etc/cron.monthly/update_cloudflare_ips to keep CIDRs current.


Step 3: Configuring Nginx Server Blocks & Logging Format

In /etc/nginx/nginx.conf, define a high-fidelity logging format that logs both the resolved client IP ($remote_addr) and the raw upstream connecting IP ($realip_remote_addr):

# /etc/nginx/nginx.conf
http {
    include       mime.types;
    default_type  application/octet-stream;

    # Include trusted proxy CIDRs
    include /etc/nginx/conf.d/cloudflare_real_ip.conf;

    # Log format showing both true client and proxy hop
    log_format enterprise_combined '$remote_addr - $remote_user [$time_local] '
                                   '"$request" $status $body_bytes_sent '
                                   '"$http_referer" "$http_user_agent" '
                                   'Proxy_IP="$realip_remote_addr" '
                                   'Country="$http_cf_ipcountry"';

    access_log /var/log/nginx/access.log enterprise_combined;

    # Rate limiting zone now tracks true client IPs!
    limit_req_zone $binary_remote_addr zone=api_zone:20m rate=15r/s;

    include /etc/nginx/conf.d/*.conf;
}

Step 4: Testing & Header Inspection

Test the resolution by sending a request through Cloudflare and checking your Nginx access log:

tail -f /var/log/nginx/access.log

Sample output:

39.40.12.18 - - [30/Sep/2026:16:30:15 +0500] "GET /api/v1/products HTTP/2.0" 200 4820 "-" "Mozilla/5.0" Proxy_IP="172.70.142.10" Country="PK"

Notice:

  • $remote_addr: Correctly resolved to 39.40.12.18 (Jazz / PTCL domestic IP in Pakistan).
  • Proxy_IP: Accurately records 172.70.142.10 (Cloudflare edge proxy).
  • Rate limits now track individual visitors rather than aggregating entire cities under one Cloudflare IP!

High-Performance Origin Server Infrastructure in Pakistan

Origin servers sitting behind reverse proxies handle high volumes of keepalive TCP sessions and continuous SSL termination. Shared hosting platforms frequently throttle CPU cycles, causing edge proxies like Cloudflare to return Error 521: Web server is down or Error 524: A timeout occurred.

Deploying your origin infrastructure on bare-metal Dedicated Servers in Pakistan guarantees dedicated physical AMD EPYC / Intel Xeon processors, local NVMe storage arrays, and direct 10Gbps connectivity peered at PKIX, ensuring that your origin servers respond to edge CDN requests in sub-millisecond times.

Protect Your Origin Infrastructure with NextGen Dedicated Servers

Deliver lightning-fast CDN origin response times, eliminate false IP blocking, and secure your platforms against header spoofing attacks. NextGen bare-metal infrastructure provides enterprise DDoS shielding, local data residency, and 24/7 technical operations.

Deploy Dedicated Servers in Pakistan