ホームページ  >  記事  >  バックエンド開発  >  PHP でデータベースを操作するための前処理ステートメントの詳細な紹介 (コード付き)

PHP でデータベースを操作するための前処理ステートメントの詳細な紹介 (コード付き)

醉折花枝作酒筹
醉折花枝作酒筹転載
2021-06-17 17:19:232659ブラウズ

この記事では、PHP でデータベースを操作するための前処理ステートメントについて詳しく説明します (コード付き)。一定の参考値があるので、困っている友達が参考になれば幸いです。

PHP でデータベースを操作するための前処理ステートメントの詳細な紹介 (コード付き)

#PHP でデータベースを操作するためのステートメントの前処理

今日の記事の内容は実際には非常に基本的なものですが、最新の開発では、誰もがフレームワークを使用しており、基盤となるデータベース操作コードをカプセル化する人や、自分で記述する人はほとんどいません。そこで今回は、データベース内の関連する拡張機能のプリペアドステートメントの内容を確認していきます。

#準備されたステートメントとは何ですか?

#準備されたステートメントは、実行する SQL ステートメントのコンパイルされたテンプレートと考えることができ、変数パラメーターを使用して制御できます。プリペアド ステートメントには、次の 2 つの大きな利点があります。

クエリは 1 回解析 (または前処理) するだけで済みますが、同じパラメータまたは異なるパラメータを使用して複数回実行できます。クエリの準備が完了すると、データベースはクエリを実行するための計画を分析、コンパイル、最適化します。複雑なクエリの場合、このプロセスには時間がかかり、同じクエリを異なるパラメータで複数回繰り返す必要がある場合、アプリケーションの速度が大幅に低下する可能性があります。準備されたステートメントを使用すると、分析/コンパイル/最適化サイクルの繰り返しを回避できます。簡単に言えば、準備されたステートメントは使用するリソースが少ないため、より高速に実行されます。
  • 準備されたステートメントに指定されたパラメーターは引用符で囲む必要はありません。ドライバーが自動的に処理します。アプリケーションでプリペアド ステートメントのみを使用する場合、SQL インジェクションは確実に発生しません。 (ただし、クエリの他の部分がエスケープされていない入力から構築されている場合は、依然として SQL インジェクションのリスクが存在します)。
  • 上記の内容は公式ドキュメントからの抜粋ですが、実際、プリペアド ステートメントがもたらす最も直感的な利点は、SQL インジェクションを効果的に防止できることです。 SQLインジェクションの内容については、今後MySQLを学習する際に詳しく勉強するので、ここではあまり紹介しませんが、とにかくプリペアドステートメントだけでこの作業は完了します。

PDO はプリペアド ステートメントを操作します

PHP 拡張機能の中でも、PDO はすでに主流のコア データベース拡張ライブラリであり、当然プリペアド ステートメントに対する非常に包括的なサポートも備えています。
$pdo = new PDO('mysql:host=localhost;port=3306;dbname=blog_test', 'root', '');
$pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

// :xxx 占位符
$stmt = $pdo->prepare("insert into zyblog_test_user (username, password, salt) values (:username, :password, :salt)");
$stmt->bindParam(':username', $username);
$stmt->bindParam(':password', $password);
$stmt->bindParam(':salt', $salt);

$username = 'one';
$password = '123123';
$salt = 'aaa';
$stmt->execute();

$username = 'two';
$password = '123123';
$salt = 'bbb';
$stmt->execute();

コードでは、prepare() メソッドを使用して準備済みステートメントを定義し、PDOStatement オブジェクトを返します。プリペアド ステートメント内で :xxx などのプレースホルダー シンボルを使用し、PDOStatement オブジェクトの bindingParam() メソッドを使用して変数をこれらのプレースホルダーに外部的にバインドします。最後に、execute() を使用して実際に SQL ステートメントを実行します。

このコードから、準備されたステートメントの 2 つの主な利点がわかります。 1 つ目はプレースホルダーです。プレースホルダーを使用すると、SQL ステートメントに一重引用符を記述する必要がなくなります。一重引用符は、SQL インジェクションの脆弱性の主な原因となることがよくあります。 bindParam() メソッドは、バインドされたデータの型を自動的に変換します。もちろん、bindParam() メソッドではオプションのパラメーターでバインドされたデータ型を指定することもできるため、コードをより安全にすることができます。

もう 1 つの利点は、テンプレートの機能です。PDOStatement オブジェクトを 1 つだけ定義し、データの内容を変更することで、execute() メソッドを複数回使用してプリペアド ステートメントを実行できます。

プレースホルダーを記述する別の方法として、疑問符をプレースホルダー記号として使用する方法があります。この場合、bindParam() メソッドのキー名には数字の添字が使用されます。ここで、数字の下付き文字は 1 から始まることに注意してください。

// ? 占位符
$stmt = $pdo->prepare("insert into zyblog_test_user (username, password, salt) values (?, ?, ?)");
$stmt->bindParam(1, $username);
$stmt->bindParam(2, $password);
$stmt->bindParam(3, $salt);

$username = 'three';
$password = '123123';
$salt = 'ccc';
$stmt->execute();

このクエリでは、プリペアド ステートメントの機能を簡単に使用してデータをクエリすることもできます。ここでは、execute() を直接使用して、プレースホルダーのパラメーターを渡します。

// 查询获取数据
$stmt = $pdo->prepare("select * from zyblog_test_user where username = :username");

$stmt->execute(['username'=>'one']);

while($row = $stmt->fetch()){
    print_r($row);
}

mysqli 操作のプリペアド ステートメント

主流は PDO であり、ほとんどのフレームワークも PDO を使用しますが、スクリプトを作成したり、迅速にテストする必要がある場合は、一部の機能では、迅速な開発のために今でも mysqli を使用しています。もちろん、mysqli はプリペアド ステートメント関連の関数もサポートしています。
// mysqli 预处理
$conn = new mysqli('127.0.0.1', 'root', '', 'blog_test');
$username = 'one';
$stmt = $conn->prepare("select username from zyblog_test_user where username = ?");
$stmt->bind_param("s", $username);

$stmt->execute();

echo $stmt->bind_result($unames);

var_dump($unames);

while ($stmt->fetch()) {
    printf("%s\n", $unames);
}

mysqli のメソッド名が異なることに加えて、バインド パラメーターのキー名もまったく同じではないことがわかります。ここでは疑問符のプレースホルダーを使用します。bind_param() メソッドでは、シンボルの位置を示すには s を使用します。パラメーターが複数ある場合は、このように sss... と記述します。

概要

準備されたステートメントの機能は、現在のフレームワークにカプセル化されています。実際、あまり気にする必要はありません。 Laravel で DB::select() がデータベース操作を実行するとき、準備されたステートメントの適用がわかります。 vendor/laravel/framework/src/Illuminate/Database/Connection.php の select() メソッドを自分で確認できます。

テスト コード:

https://github.com/zhangyue0503/dev-blog/blob/master/php/202008/source/PHP%E4%B8%AD%E6%93%8D%E4%BD%9C%E6%95%B0%E6%8D%AE%E5%BA%93%E7%9A%84%E9%A2%84%E5%A4%84%E7%90%86%E8%AF%AD%E5%8F%A5.php

推奨学習:

php ビデオ チュートリアル

以上がPHP でデータベースを操作するための前処理ステートメントの詳細な紹介 (コード付き)の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事はsegmentfault.comで複製されています。侵害がある場合は、admin@php.cn までご連絡ください。