首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 網頁程式設計 >> PHP 程式設計 >> PHP 綜合知識

SQL 注入攻擊原理與防範完整指南(PHP 版)

     編輯:PHP 綜合知識

什麼是 SQL Injection?

SQL 注入是指攻擊者透過輸入精心構造的惡意字串,改變原本 SQL 語句的邏輯,進而竊取、竄改、刪除資料庫資料,甚至取得伺服器控制權。

經典注入流程

  1. 尋找注入點: 登入表單、搜尋框、URL 參數、Cookie、HTTP Header 等。
  2. 構造惡意 SQL: 如 ' OR 1=1 --、'; DROP TABLE users; --。
  3. 送出請求: 經由前端送至後端,後端未過濾直接拼接進 SQL。
  4. 資料庫執行: DBMS 解析並執行被篡改的 SQL。
  5. 回傳結果: 攻擊者獲得資料或執行權限操作。

實戰演示:登入繞過

假設脆弱程式碼:

<?php
$conn = mysqli_connect("localhost", "root", "", "demo");
$name = $_POST['username'];
$pwd  = $_POST['password'];
$sql  = "SELECT * FROM users WHERE username='$name' AND password=MD5('$pwd')";
$res  = mysqli_query($conn, $sql);
if (mysqli_num_rows($res) > 0) {
    // 登入成功
}
?>

攻擊者在帳號欄輸入:admin' --,密碼隨意。
實際執行 SQL 變為:SELECT * FROM users WHERE username='admin' --' AND password=MD5('...'),-- 註解掉後續條件,直接以 admin 身分登入。

更嚴重:Union 注入、盲注、時間盲注、堆疊查詢

  • Union 注入: 結合 UNION SELECT 讀取其他資料表。
  • 布林盲注: 透過頁面回應真/偽推斷資料。
  • 時間盲注: 利用 SLEEP() 延遲判斷。
  • 堆疊查詢: 多條 SQL 以分號分隔,可執行 DROP TABLE 等破壞性指令(視驅動支援度)。

核心防禦:參數化查詢(Prepared Statements)

永遠不要用字串拼接組裝 SQL!

mysqli 參數化範例

<?php
$stmt = $mysqli->prepare("SELECT * FROM users WHERE username=? AND password=MD5(?)");
$stmt->bind_param("ss", $name, $pwd);
$stmt->execute();
$result = $stmt->get_result();
if ($result->num_rows > 0) { /* 登入成功 */ }
$stmt->close();
?>

PDO 參數化範例(推薦)

<?php
$stmt = $pdo->prepare("SELECT * FROM users WHERE username=:user AND password=MD5(:pwd)");
$stmt->execute([':user' => $name, ':pwd' => $pwd]);
if ($stmt->rowCount() > 0) { /* 登入成功 */ }
?>

輔助防禦措施

  • 最小權限原則: 資料庫帳號僅授予必要權限(SELECT/INSERT/UPDATE),避免 DROP、CREATE、FILE 權限。
  • 輸入驗證與白名單: 對預期格式(如整數、Email、字母數字)嚴格驗證。
  • 錯誤訊息不外露: 生產環境關閉 display_errors,記錄至 log,避免洩露資料表結構。
  • WAF/資料庫防火牆: 部署 ModSecurity、云端 WAF 攔截可疑請求。
  • ORM/Query Builder: 使用 Laravel Eloquent、Doctrine、Medoo 等,內建參數化。

常見迷思

「用 addslashes() 或 mysql_real_escape_string() 就安全了?」
錯。編碼繞過、字元集問題、二次注入等情況仍可突破。唯有參數化查詢才是根本解法。

總結:所有動態 SQL 必須使用預處理語句,搭配最小權限、錯誤隱藏、WAF,建立纵深防禦。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved