ホームページ >バックエンド開発 >PHPチュートリアル >PHP がクライアント IP を取得するいくつかの状況を分析する

PHP がクライアント IP を取得するいくつかの状況を分析する

WBOY
WBOYオリジナル
2016-06-13 13:04:25819ブラウズ

PHP がクライアント IP
を取得するいくつかの状況を分析します。 PHP がクライアント IP を取得する状況は、プロキシ サーバーが使用されない状況、透過的プロキシ サーバーが使用される状況、一般的な匿名プロキシ サーバーが使用される状況、欺瞞的なプロキシ サーバーが使用される状況、および匿名性の高いプロキシ サーバーが使用される状況。

この記事では、PHP がクライアント IP を取得するいくつかの状況の分析を詳しく紹介します。 PHP を使用して取得する IP は、クライアントの実際の IP である場合もあれば、プロキシ サーバーの IP である場合もあります。また、IP 値をまったく取得できない場合もあります。

$_SERVER["REMOTE_ADDR"] は、クライアント IP を取得するために PHP でよく使用されます。ただし、クライアントがプロキシ サーバーを使用してアクセスする場合、取得されるのはプロキシ サーバーの IP アドレスであり、実際のクライアントの IP アドレスではありません。プロキシ サーバー経由でクライアントの実際の IP アドレスを取得するには、$_SERVER["HTTP_X_FORWARDED_FOR"] を使用して読み取ります。

ただし、クライアントが「透過プロキシ」を使用する場合に限り、$_SERVER["HTTP_X_FORWARDED_FOR"] の値はクライアントの実際の IP になります (マルチレイヤ プロキシの場合、この値はクライアントの実際の IP)IP と複数のプロキシ サーバーの IP をカンマ「,」で区切って)、「匿名プロキシ」および「偽プロキシ」の場合はプロキシ サーバーの IP 値(マルチレイヤ プロキシの場合、この値は複数のプロキシ サーバーの IP をカンマ「,」で区切って構成することができます。「高匿名性プロキシ」の場合は null 値になります。

HTTP ヘッダー情報の REMOTE_ADDR と HTTP_FORWARDED_FOR の値については、クライアントの実際の IP が 221.5.252.160 であると仮定して、以下に詳しく説明します。

1. PHP の取得。プロキシ サーバーを使用しない場合 クライアント IP の状況:

REMOTE_ADDR = クライアント IP

HTTP_X_FORWARDED_FOR = 値がない、または表示されません

2. 透過的プロキシ サーバーを使用する場合: 透過的プロキシ

REMOTE_ADDR = 最後のプロキシ サーバー IP

HTTP_X_FORWARDED_FOR = クライアントの実際の IP (複数のプロキシ サーバーを経由する場合、この値は同様です: 221.5.252.160、203.98.182.163、203.129.72.215)

このタイプのプロキシ サーバーは依然としてクライアントの実際の IP をアクセス オブジェクトに送信するため、本当の身元を隠すという目的を達成できません。

3. 通常の匿名プロキシ サーバー PHP を使用してクライアント IP を取得します。 匿名プロキシ

REMOTE_ADDR = 最後のプロキシ サーバー IP

HTTP_X_FORWARDED_FOR = プロキシ サーバー IP (複数使用時以降)プロキシ サーバーの場合、この値は同様です: 203.98.182.163、203.98.182.163、203.129.72.215)

この場合、クライアントの実際の IP は隠されていますが、クライアントはアクセス オブジェクトに対して明らかにされます。クライアントはプロキシ サーバーを使用してアクセスしています。

IV. プロキシの歪み

REMOTE_ADDR = プロキシ サーバー IP

HTTP_X_FORWARDED_FOR = ランダム IP (複数のプロキシ サーバーを通過する場合、この値は類似: 220.4.251.159、203.98.182.163) 、203.129.72.215)

この場合、クライアントはプロキシ サーバーを使用していますが、偽のランダム IP (220.4.251.159) を捏造してクライアントの実際の IP を置き換えてスプーフィングしていることも明らかになります。それ。

5. PHP と高匿名性プロキシ サーバーを使用してクライアント IP を取得します: 高匿名性プロキシ (エリート プロキシ)

REMOTE_ADDR = プロキシ サーバー IP

HTTP_X_FORWARDED_FOR = 値なし、または Do

を表示しません REMOTE_ADDR であっても HTTP_FORWARDED_FOR であっても、ブラウザーやネットワーク デバイスが異なれば送信される IP ヘッダー メッセージも異なる可能性があるため、これらのヘッダー メッセージは利用できない場合があります。したがって、$_SERVER["REMOTE_ADDR"] および $_SERVER["HTTP_X_FORWARDED_FOR"] を使用して PHP によって取得される値は、null 値または「不明な」値である可能性があります。

したがって、PHP を使用してクライアント IP を取得するコードは次のようになります。

function getip() { 
    $unknown = 'unknown'; 

  if ( isset($_SERVER['HTTP_X_FORWARDED_FOR']) && $_SERVER['HTTP_X_FORWARDED_FOR'] && strcasecmp($_SERVER['HTTP_X_FORWARDED_FOR'], $unknown) ) { 
      $ip = $_SERVER['HTTP_X_FORWARDED_FOR']; 
  } elseif ( isset($_SERVER['REMOTE_ADDR']) && $_SERVER['REMOTE_ADDR'] && strcasecmp($_SERVER['REMOTE_ADDR'], $unknown)){ 

      $ip = $_SERVER['REMOTE_ADDR']; 
  } 
  /* 
  处理多层代理的情况 
  或者使用正则方式:$ip = preg_match("/[\d\.]{7,15}/", $ip, $matches) ? $matches[0] : $unknown; 
  */ 
  if (false !== strpos($ip, ',')) 
     $ip = reset(explode(',', $ip)); 
     return $ip; 
} 
  
function getip() { 
  $unknown = 'unknown'; 
  if ( isset($_SERVER['HTTP_X_FORWARDED_FOR']) && $_SERVER['HTTP_X_FORWARDED_FOR'] && strcasecmp($_SERVER['HTTP_X_FORWARDED_FOR'], $unknown) ) { 
  $ip = $_SERVER['HTTP_X_FORWARDED_FOR']; 
  } elseif ( isset($_SERVER['REMOTE_ADDR']) && $_SERVER['REMOTE_ADDR'] && strcasecmp($_SERVER['REMOTE_ADDR'], $unknown) ) { 
  $ip = $_SERVER['REMOTE_ADDR']; 
  } 
  /* 
  处理多层代理的情况 
  或者使用正则方式:$ip = preg_match("/[\d\.]{7,15}/", $ip, $matches) ? $matches[0] : $unknown; 
  */ 
  if (false !== strpos($ip, ',')) 
  $ip = reset(explode(',', $ip)); 
  return $ip; 
}



PHP がクライアント IP を取得するときに注意すべき点がもう 1 つあります。関数 getenv(' HTTP_X_FORWARDED_FOR') または getenv('REMOTE_ADDR') を使用しても、上記のコードと同じ効果を実現できます。 しかし、getenv() は、IIS isapi モードで実行される PHP をサポートしていません。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。