ホームページ >バックエンド開発 >PHPチュートリアル >プリペアドステートメントはどのようにして PHP での SQL インジェクションを防ぐことができますか?

プリペアドステートメントはどのようにして PHP での SQL インジェクションを防ぐことができますか?

Susan Sarandon
Susan Sarandonオリジナル
2025-01-01 09:08:11421ブラウズ

How Can Prepared Statements Prevent SQL Injection in PHP?

PHP での SQL インジェクションに対する保護

適切な予防措置を講じずにユーザー入力を SQL クエリに統合すると、SQL インジェクションに対するコードの脆弱性が発生します。次の脆弱なコード スニペットを考えてみましょう。

$unsafe_variable = $_POST['user_input']; 

mysql_query("INSERT INTO `table` (`column`) VALUES ('$unsafe_variable')");

このシナリオは、値') などのユーザー入力文字列を介して悪用される可能性があります。 DROP TABLE テーブル;--、悪意のあるクエリにつながります:

INSERT INTO `table` (`column`) VALUES('value'); DROP TABLE table;--')

防止戦略

このような攻撃を回避するには、データを SQL から分離し、データがデータとして扱われるようにすることが不可欠です。 SQL パーサーによってコマンドとして解釈されません。パラメータ化されたクエリを含むプリペアド ステートメントは、SQL ステートメントとパラメータ値を分離する堅牢なソリューションを提供します。データベース サーバーは SQL ステートメントを解析してコンパイルし、パラメータを文字列として扱い、悪意のある SQL インジェクションの試みを効果的にブロックします。

プリペアド ステートメントの実装

PDO

$stmt = $pdo->prepare('SELECT * FROM employees WHERE name = :name');
$stmt->execute([ 'name' => $name ]);

foreach ($stmt as $row) {
    // Do something with $row
}

MySQLi for MySQL (PHP 8.2 )

$result = $db->execute_query('SELECT * FROM employees WHERE name = ?', [$name]);
while ($row = $result->fetch_assoc()) {
    // Do something with $row
}

MySQLi 用MySQL (PHP 8.1 まで)

$stmt = $db->prepare('SELECT * FROM employees WHERE name = ?');
$stmt->bind_param('s', $name); // 's' specifies the variable type => 'string'
$stmt->execute();
$result = $stmt->get_result();
while ($row = $result->fetch_assoc()) {
    // Do something with $row
}

PDO および MySQLi に関する追加の注意事項

PDO

デフォルトでは、PDO はエミュレートされたプリペアド ステートメントを使用します。エミュレーションを無効にして、MySQL に対して真のプリペアド ステートメントを強制するには、次のように設定します。

$dbConnection->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);

MySQLi

同様に、次のように設定します。

mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT); // error reporting
$dbConnection = new mysqli('127.0.0.1', 'username', 'password', 'test');
$dbConnection->set_charset('utf8mb4'); // charset

プリペアド ステートメントについて

準備されたステートメントは、実行時にデータベース サーバーによって解析およびコンパイルされます。パラメーターは、フィルターを適用する場所をデータベース エンジンに通知します。値を指定して準備されたステートメントを実行すると、コンパイルされたステートメントは SQL 文字列ではなく、それらの値と結合されます。これにより、意図しない SQL 実行につながる可能性のある悪意のある文字列の挿入が防止されます。

警告

準備されたステートメントは、クエリ構造が変更される動的クエリには適していません。このような場合、可能な値を制限するホワイトリスト フィルターを使用する必要があります。

以上がプリペアドステートメントはどのようにして PHP での SQL インジェクションを防ぐことができますか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

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