この記事では、php を通じてクライアント IP を取得する方法を説明します
IP を取得する関数は次のとおりです:
function getIP() { $realip = ''; //设置默认值 if (isset($_SERVER['HTTP_X_FORWARDED_FOR'])) { $realip = $_SERVER['HTTP_X_FORWARDED_FOR']; } elseif (isset($_SERVER['HTTP_CLIENT_IP'])) { $realip = $_SERVER['HTTP_CLIENT_IP']; } else { $realip = $_SERVER['REMOTE_ADDR']; } preg_match('/^((?:\d{1,3}\.){3}\d{1,3})/',$realip,$match); if($match && ipType($match[0]) == 'InterNet网地址'){ return $match[0]; }else{ return false; } }
//インターネットでは IP アドレスの使用が許可されています
function ipType($ip) { $iplist = explode(".", $ip); if ($iplist[0] >= 224 && $iplist[0] <= 239) return '多播'; if ($iplist[0] >= 240 && $iplist[0] <= 255) return '保留'; if (preg_match('/^198\.51\.100/', $ip)) return 'TEST-NET-2,文档和示例'; if (preg_match('/^203\.0\.113/', $ip)) return 'TEST-NET-3,文档和示例'; if (preg_match('/^192\.(18|19)\./', $ip)) return '网络基准测试'; if (preg_match('/^192\.168/', $ip)) return '专用网络[内部网]'; if (preg_match('/^192\.88\.99/', $ip)) return 'ipv6to4中继'; if (preg_match('/^192\.0\.2\./', $ip)) return 'TEST-NET-1,文档和示例'; if (preg_match('/^192\.0\.0\./', $ip)) return '保留(IANA)'; if (preg_match('/^192\.0\.0\./', $ip)) return '保留(IANA)'; if ($iplist[0] == 172 && $iplist[1] <= 31 && $iplist[1] >= 16) return '专用网络[内部网]'; if ($iplist[0] == 169 && $iplist[1] == 254) return '链路本地'; if ($iplist[0] == 127) return '环回地址'; if ($iplist[0] == 10) return '专用网络[内部网]'; if ($iplist[0] == 0) return '本网络(仅作为源地址时合法)'; return 'InterNet网地址'; }
インターネット上の IP を取得するための一般的な関数は次のとおりです:
public function get_real_ip() { static $realip; if (isset($_SERVER)) { if (isset($_SERVER['HTTP_X_FORWARDED_FOR'])) { $realip = $_SERVER['HTTP_X_FORWARDED_FOR']; } else if (isset($_SERVER['HTTP_CLIENT_IP'])) { $realip = $_SERVER['HTTP_CLIENT_IP']; } else { $realip = $_SERVER['REMOTE_ADDR']; } } else { if (getenv('HTTP_X_FORWARDED_FOR')) { $realip = getenv('HTTP_X_FORWARDED_FOR'); } else if (getenv('HTTP_CLIENT_IP')) { $realip = getenv('HTTP_CLIENT_IP'); } else { $realip = getenv('REMOTE_ADDR'); } } return $realip; }
'REMOTE_ADDR'、'HTTP_X_FORWARDED_FOR'、'HTTP_CLIENT_IP' の違いは何ですか?
1.「REMOTE_ADDR」はリモートIPで、デフォルトはTCP接続からのクライアントのIPです。サーバーに直接接続されているクライアント IP のみを取得することが最も正確かつ確実であると言えます。相手がプロキシサーバーを経由してインターネットにアクセスすると発見されてしまいます。取得されるのはプロキシ サーバーの IP です。
例: a->b(proxy)->c、c が 'REMOTE_ADDR' を渡す場合、b の IP のみを取得できますが、a の IP は取得できません。
2. 大規模ネットワークで元のユーザー IP またはプロキシ IP アドレスを取得するための「HTTP_X_FORWARDED_FOR」、「HTTP_CLIENT_IP」。 HTTPプロトコルを拡張します。エンティティヘッダーが定義されています。
HTTP_X_FORWARDED_FOR = clientip,proxy1,proxy2 すべての IP は「,」で区切られます。 HTTP_CLIENT_IP 高度な匿名プロキシでは、これはプロキシ サーバーの IP を表します。 http プロトコルはエンティティ ヘッダーを拡張し、この値は受信側によって信頼されるため、受信側がルール形式に従って入力することが信頼されます。以下では、x_forword_for の例を使用して、通常の状況では、この値によってプロセスが変更されます。
リスクポイント:
これらの変数は http リクエスト、x-forword-for フィールド、および client-ip フィールドから取得されます。 通常のプロキシ サーバーは、当然ながら、rfc 仕様に従ってこれらの値を渡します。ただし、ユーザーが x-forword-for 値を直接構築してユーザーに送信すると、任意の値を書き込むことができるフィールドがあるのと同じになります。そして、サーバーはデータベースを直接読み取り、書き込み、または表示します。これは、入力に対するフィルタリングやテストを行わずにデータ ソースを操作するのと同様に、危険をもたらします。
上記の getip 関数の場合:
ただし、クライアントは自由に IP を偽造でき、任意の形式で IP を渡すことができます。 これにより、2 つの大きな問題が発生します。1 つは、特定のページを設定して IP 制限を課した場合です。 相手は簡単にIPを変更して継続的にページをリクエストすることができます。 次に、この種のデータを直接使用すると、SQL 登録やクロスサイト攻撃などの脆弱性が生じます。 1 つ目に関しては、ビジネスに制限を設定できますが、IP 制限は使用しないことをお勧めします。 2 つ目については、このタイプは巨大なサイバー リスクをもたらす可能性があります。それを正さなければなりません。
この記事では、php を通じてクライアント IP を取得する方法について説明します。その他の関連コンテンツについては、php 中国語 Web サイトに注目してください。
関連する推奨事項:
以上がPHPでクライアントIPを取得する方法を理解するの詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。