Cloudflare Proxy is a great tool, it hides our server IP address, caches files, and protects from DDOS attacks.
When a visitor opens our site web server receives Cloudflares IP address as a visitor address. Everywhere in logs we'll see wrong address, but there is an easy fix.
Cloudflare Connecting IP Header
By default Cloudflare will return header value of CF-Connecting-IP
and it'll contain real IP address of the visitor.
Usual and expected header with visitor IP is REMOTE_ADDR
.
Now we need to insert CF-Connecting-IP
value into REMOTE_ADDR
.
Setting real IP address in Nginx
Majority of Laravel/PHP applications nowadays are on Nginx, so I'll focus on it.
Nginx posses ngx_http_realip_module which is used to change the client address.
Main directive set_real_ip_from
Most important directive in this Nginx module is set_real_ip_from
, it defines trusted addresses that are known to send correct replacement addresses. In our case this direcive will be used to specify Cloudflare IP addresses which will send traffic to our server.
Cloudflare IP Ranges
Cloudflare keeps up to date list of their ip address at IP Ranges. Only traffic originating from these IP addresses can be trusted.
IPs v4
List of trusted IP v4 address of Cloudflare:
173.245.48.0/20
103.21.244.0/22
103.22.200.0/22
103.31.4.0/22
141.101.64.0/18
108.162.192.0/18
190.93.240.0/20
188.114.96.0/20
197.234.240.0/22
198.41.128.0/17
162.158.0.0/15
104.16.0.0/13
104.24.0.0/14
172.64.0.0/13
131.0.72.0/22
IPs v6
List of trusted IP v6 addresses of Cloudflare:
2400:cb00::/32
2606:4700::/32
2803:f800::/32
2405:b500::/32
2405:8100::/32
2a06:98c0::/29
2c0f:f248::/32
Inserting trusted IPs into Nginx config
Inside Nginx configuration of our domain we need to specify these trusted IPs and what to do with them.
I like to separate this Cloudflare logic into new config file cloudflare.conf
:
#Cloudflare ip addresses
# - IPv4
set_real_ip_from 103.21.244.0/22;
set_real_ip_from 103.22.200.0/22;
set_real_ip_from 103.31.4.0/22;
set_real_ip_from 104.16.0.0/13;
set_real_ip_from 104.24.0.0/14;
set_real_ip_from 108.162.192.0/18;
set_real_ip_from 131.0.72.0/22;
set_real_ip_from 141.101.64.0/18;
set_real_ip_from 162.158.0.0/15;
set_real_ip_from 172.64.0.0/13;
set_real_ip_from 173.245.48.0/20;
set_real_ip_from 188.114.96.0/20;
set_real_ip_from 190.93.240.0/20;
set_real_ip_from 197.234.240.0/22;
set_real_ip_from 198.41.128.0/17;
# - IPv6
set_real_ip_from 2400:cb00::/32;
set_real_ip_from 2405:8100::/32;
set_real_ip_from 2405:b500::/32;
set_real_ip_from 2606:4700::/32;
set_real_ip_from 2803:f800::/32;
set_real_ip_from 2c0f:f248::/32;
set_real_ip_from 2a06:98c0::/29;
real_ip_header CF-Connecting-IP;
With this configuration we'are saying to Nginx if request is coming from some of these IP address take it's CF-Connecting-IP
header and put it inside REMOTE_ADDR
.
Now it's time to include this new Cloudflare configuration file inside site configuration in sites-available
folder inside server
section:
include /etc/nginx/cloudflare.conf;
After Nginx server restart, we'll start to notice real IP addresses of the visitors.