CloudFlare并通过PHPlogging访问者的IP地址
我试图使用PHP的$_SERVER['REMOTE_ADDR']
来跟踪和logging正在访问我的网站的用户/访问者。 在PHP中用于IP地址跟踪的典型方法。
但是,我正在使用CloudFlare进行caching等,并接收CloudFlare的IP地址:
108.162.212。* – 108.162.239。*
在仍使用CloudFlare的情况下,检索实际用户/访问者IP地址的正确方法是什么?
云耀斑可用的额外的服务器variables是:
$_SERVER["HTTP_CF_CONNECTING_IP"]
真正的访客IP地址,这是你想要的
访问者的$_SERVER["HTTP_CF_IPCOUNTRY"]
国家
$_SERVER["HTTP_CF_RAY"]
见这里的描述
$_SERVER["HTTP_CF_VISITOR"]
这可以帮助你知道它的http或https
你可以像这样使用它:
if (isset($_SERVER["HTTP_CF_CONNECTING_IP"])) { $_SERVER['REMOTE_ADDR'] = $_SERVER["HTTP_CF_CONNECTING_IP"]; }
如果您这样做,并且访问IP地址的有效性很重要,则可能需要validation$_SERVER["REMOTE_ADDR"]
包含实际有效的cloudflare IP地址,因为任何人都可以伪造标头,前提是他能够连接直接到服务器IP。
由于这个问题被问及和回答,CloudFlare已经发布了Apache的mod_cloudflare
,它logging并显示了实际的访问者IP地址而不是CloudFlare的地址:
https://www.cloudflare.com/resources-downloads#mod_cloudflare
Cloudflare发送一些额外的请求头到您的服务器,包括CF-Connecting-IP
,我们可以使用这个简单的单行程序将其存储到$user_ip
(如果定义的话):
$user_ip = (isset($_SERVER["HTTP_CF_CONNECTING_IP"])?$_SERVER["HTTP_CF_CONNECTING_IP"]:$_SERVER['REMOTE_ADDR']);
我正在重写我的答案我用于另一个问题“ CloudFlare DNS /直接IP标识符 ”
Cloudflare的ips被公开存储,所以你可以在这里查看它们,然后检查ip是否来自cloudflare(这将允许我们从http头HTTP_CF_CONNECTING_IP
获得真实的ip)。
如果你正在使用这个来禁用所有的非cf连接,反之亦然,我build议你有一个php脚本文件,在每一个其他脚本之前被调用,比如common.php或者pagestart.php等等。
function ip_in_range($ip, $range) { if (strpos($range, '/') == false) $range .= '/32'; // $range is in IP/CIDR format eg 127.0.0.1/24 list($range, $netmask) = explode('/', $range, 2); $range_decimal = ip2long($range); $ip_decimal = ip2long($ip); $wildcard_decimal = pow(2, (32 - $netmask)) - 1; $netmask_decimal = ~ $wildcard_decimal; return (($ip_decimal & $netmask_decimal) == ($range_decimal & $netmask_decimal)); } function _cloudflare_CheckIP($ip) { $cf_ips = array( '199.27.128.0/21', '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/12', ); $is_cf_ip = false; foreach ($cf_ips as $cf_ip) { if (ip_in_range($ip, $cf_ip)) { $is_cf_ip = true; break; } } return $is_cf_ip; } function _cloudflare_Requests_Check() { $flag = true; if(!isset($_SERVER['HTTP_CF_CONNECTING_IP'])) $flag = false; if(!isset($_SERVER['HTTP_CF_IPCOUNTRY'])) $flag = false; if(!isset($_SERVER['HTTP_CF_RAY'])) $flag = false; if(!isset($_SERVER['HTTP_CF_VISITOR'])) $flag = false; return $flag; } function isCloudflare() { $ipCheck = _cloudflare_CheckIP($_SERVER['REMOTE_ADDR']); $requestCheck = _cloudflare_Requests_Check(); return ($ipCheck && $requestCheck); } // Use when handling ip's function getRequestIP() { $check = isCloudflare(); if($check) { return $_SERVER['HTTP_CF_CONNECTING_IP']; } else { return $_SERVER['REMOTE_ADDR']; } }
要使用这个脚本很简单:
$ip = getRequestIP(); $cf = isCloudflare(); if($cf) echo "Cloudflare :D<br>"; else echo "Not cloudflare o_0"; echo "Your actual ip address is: ". $ip;
这个脚本会告诉你真实的IP地址,如果请求是CF还是不是!
对于magento 1.x用户(我还没有尝试magento 2.0),请检查https://tall-paul.co.uk/2012/03/13/magento-show-remote-ip-in-cloudflare-the-右键/需要更改app / etc / local.xml并添加:HTTP_CF_CONNECTING_IP
HTTP_CF_CONNECTING_IP只在你使用cloudflare的时候工作,也许你转移你的网站或者删除cloudflare,你会忘记这个值,所以使用这个代码。
$ip=$_SERVER["HTTP_CF_CONNECTING_IP"]; if (!isset($ip)) { $ip = $_SERVER['REMOTE_ADDR']; }
当您使用CloudFlare时,您的服务器和用户之间的所有请求都通过CloudFlare服务器进行路由。
在这种情况下,有两种方法可以获取用户的真实IP地址:
- 通过CloudFlare服务器添加的额外服务器头
- 在您的服务器上添加一个CloudFlare Apache / NGINX模块。
方法1:通过额外的服务器头获取IP
您可以使用下面的代码来获取用户的IP地址:
$user_ip = (isset($_SERVER["HTTP_CF_CONNECTING_IP"]) $_SERVER["HTTP_CF_CONNECTING_IP"]:$_SERVER['REMOTE_ADDR']);
它是如何工作的?
CloudFlare在请求中添加一些额外的服务器variables,如下所示:
$_SERVER["HTTP_CF_CONNECTING_IP"]
– 用户的真实IP地址
$_SERVER["HTTP_CF_IPCOUNTRY"]
– ISO2国家的用户
$_SERVER["HTTP_CF_RAY"]
用于login目的的特殊string
在上面的代码中,我们正在检查$_SERVER["HTTP_CF_CONNECTING_IP"]
是否被设置。 如果它在那里,我们会认为作为用户的IP地址,否则我们将使用默认代码$_SERVER['REMOTE_ADDR']
方法2:在您的服务器上安装Cloudflare模块
- 在Apache服务器上安装CloudFlare模块
- 在NGINX服务器上安装CloudFlare模块
- 在EasyApache + CPanel上安装CloudFlare模块