好吧,我有一个小的身份验证问题。我的web服务允许使用用户名和密码通过HTTP连接到我的API,但此连接也可以限制为特定的IP地址。
这意味着$_SERVER['REMOTE_ADDR']可能是不正确的。我已经知道,任何IP信息都不能真正依赖-我的限制只是为了增加另一层安全。
如果这是对我的web服务器的请求的一般概述:
clientSERVER => clientPROXY => myPROXY => mySERVER
这意味着mySERVER会显示myPROXY的REMOTE_ADDR,而不是客户端的and,并将客户端的实际IP作为HTTP_X_FORWARDED_FOR发送。
为了克服这个问题,我的web服务有一个“可信代理”IP地址列表,如果REMOTE_ADDR来自这些可信IP地址之一,它就会告诉我的web服务实际的IP地址是HTTP_X_FORWARDED_FOR的值。
现在问题出在clientPROXY上了。这意味着(通常) mySERVER会获得具有多个IP地址的HTTP_X_FORWARDED_FOR值。根据HTTP_X_FORWARDED_FOR文档,该值是以逗号分隔的IP地址列表,其中第一个IP是实际真实客户端的IP,其他每个IP地址都是代理的IP地址。
那么,如果HTTP_X_FORWARDED_FOR有多个值,并且我的服务是IP受限的,我是否必须根据我允许的IP列表检查HTTP_X_FORWARDED_FOR的“最后”值,而忽略实际的客户端IP?
我假设在一个系统中,我必须设置允许的IP地址列表,白名单上的IP地址应该是代理的地址,而不是代理后面的IP (因为它可能是某个本地主机IP,并且经常更改)。
HTTP_CLIENT_IP又是什么呢?
发布于 2014-05-13 13:56:59
您可以使用此函数获取正确的客户端IP:
public function getClientIP(){
if (array_key_exists('HTTP_X_FORWARDED_FOR', $_SERVER)){
return $_SERVER["HTTP_X_FORWARDED_FOR"];
}else if (array_key_exists('REMOTE_ADDR', $_SERVER)) {
return $_SERVER["REMOTE_ADDR"];
}else if (array_key_exists('HTTP_CLIENT_IP', $_SERVER)) {
return $_SERVER["HTTP_CLIENT_IP"];
}
return '';
}发布于 2014-06-18 07:45:43
我喜欢Hrishikesh的回答,对于这个问题,我只对add...because有这样的回答,当使用多个代理时,我们看到一个逗号分隔的字符串,我们发现有必要添加一个分解并获取最终的值,如下所示:
$IParray=array_values(array_filter(explode(',',$_SERVER['HTTP_X_FORWARDED_FOR'])));
return reset($IParray);array_filter是用来删除空条目的。
发布于 2016-08-03 17:13:50
鉴于最新的httpoxy漏洞,确实需要一个完整的示例,即如何正确使用HTTP_X_FORWARDED_FOR。
这里有一个用PHP编写的示例,如何检测客户端IP地址,如果您知道客户端可能位于代理服务器之后,并且知道此代理服务器是可信的。如果您不知道任何受信任的代理,只需使用REMOTE_ADDR
<?php
function get_client_ip ()
{
// Nothing to do without any reliable information
if (!isset ($_SERVER['REMOTE_ADDR'])) {
return NULL;
}
// Header that is used by the trusted proxy to refer to
// the original IP
$proxy_header = "HTTP_X_FORWARDED_FOR";
// List of all the proxies that are known to handle 'proxy_header'
// in known, safe manner
$trusted_proxies = array ("2001:db8::1", "192.168.50.1");
if (in_array ($_SERVER['REMOTE_ADDR'], $trusted_proxies)) {
// Get the IP address of the client behind trusted proxy
if (array_key_exists ($proxy_header, $_SERVER)) {
// Header can contain multiple IP-s of proxies that are passed through.
// Only the IP added by the last proxy (last IP in the list) can be trusted.
$proxy_list = explode (",", $_SERVER[$proxy_header]);
$client_ip = trim (end ($proxy_list));
// Validate just in case
if (filter_var ($client_ip, FILTER_VALIDATE_IP)) {
return $client_ip;
} else {
// Validation failed - beat the guy who configured the proxy or
// the guy who created the trusted proxy list?
// TODO: some error handling to notify about the need of punishment
}
}
}
// In all other cases, REMOTE_ADDR is the ONLY IP we can trust.
return $_SERVER['REMOTE_ADDR'];
}
print get_client_ip ();
?>https://stackoverflow.com/questions/11452938
复制相似问题