在PHP 中使用MySQLi 擴展進行數據庫操作時,預處理語句(Prepared Statements)是確保數據安全和提高效率的重要手段。本文將詳細介紹mysqli::stmt_init函數與prepare()方法的正確用法,並結合實際示例加以解析。
mysqli::stmt_init是MySQLi 提供的一個方法,用於初始化一個空的mysqli_stmt (語句)對象。這個對象隨後可以用於預處理SQL 語句。
語法如下:
mysqli_stmt mysqli::stmt_init ( void )
它通常搭配prepare()方法使用,用於準備SQL 語句。
prepare()方法用於準備一個SQL 語句,該語句將在後續執行,並可使用參數綁定。這樣可以有效防止SQL 注入攻擊。
語法如下:
bool mysqli_stmt::prepare ( string $query )
以下是使用mysqli::stmt_init和prepare()的標準流程:
連接數據庫
初始化預處理語句對象
使用prepare()準備語句
綁定參數(如果有)
執行語句
獲取結果(如果是查詢語句)
關閉語句和連接
假設我們有一個用戶表users ,包含字段: id , username , email 。我們希望根據用戶名查詢該用戶的郵箱。
<?php
// 第一步:建立數據庫連接
$mysqli = new mysqli("localhost", "db_user", "db_password", "db_name");
// 檢查連接是否成功
if ($mysqli->connect_error) {
die("連接失敗: " . $mysqli->connect_error);
}
// 第二步:初始化預處理語句對象
$stmt = $mysqli->stmt_init();
// 第三步:準備 SQL 語句
$sql = "SELECT email FROM users WHERE username = ?";
if (!$stmt->prepare($sql)) {
die("SQL 預處理失敗: " . $stmt->error);
}
// 第四步:綁定參數
$username = "testuser";
$stmt->bind_param("s", $username); // "s" 表示字符串類型
// 第五步:执行語句
$stmt->execute();
// 第六步:綁定結果並獲取數據
$stmt->bind_result($email);
if ($stmt->fetch()) {
echo "用戶郵箱是: " . $email;
} else {
echo "未找到該用戶。";
}
// 第七步:关闭語句与连接
$stmt->close();
$mysqli->close();
?>
雖然可以直接使用query()方法執行SQL,但這樣容易受到SQL 注入攻擊的威脅。 prepare()與參數綁定能有效防止這一問題。
stmt_init()是創建一個空的語句對象,而prepare()是將SQL 模板加載到該對像中。你也可以跳過stmt_init() ,直接調用$mysqli->prepare()來一步完成初始化和準備。
是的,只要SQL 模板結構一致,語句對象可以復用,改變綁定的參數即可。
以下示例演示瞭如何通過表單提交數據,並安全地將其插入數據庫中:
<?php
$mysqli = new mysqli("localhost", "db_user", "db_password", "db_name");
if ($_SERVER["REQUEST_METHOD"] == "POST") {
$username = $_POST["username"] ?? "";
$email = $_POST["email"] ?? "";
$stmt = $mysqli->stmt_init();
if ($stmt->prepare("INSERT INTO users (username, email) VALUES (?, ?)")) {
$stmt->bind_param("ss", $username, $email);
if ($stmt->execute()) {
echo "用戶註冊成功!";
} else {
echo "執行失敗:" . $stmt->error;
}
$stmt->close();
}
}
$mysqli->close();
?>
<form method="POST" action="https://m66.net/register.php">
使用者名稱:<input type="text" name="username" required><br>
郵箱:<input type="email" name="email" required><br>
<input type="submit" value="註冊">
</form>
mysqli::stmt_init和prepare()的組合為PHP 提供了強大的數據庫安全機制。通過參數綁定不僅能防止SQL 注入,還能提高執行效率。在實際開發中,推薦始終使用預處理語句來操作數據庫。
是否想繼續了解更多關於MySQLi 中bind_param()和bind_result()的高級用法?