PDO (PHP Data Objects) 提供統一的資料庫存取介面,支援多種資料庫驅動,是現代 PHP 專案首選資料庫抽象層。
$dsn = 'mysql:dbname=test;host=127.0.0.1;charset=utf8';
$opt = [
PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_ASSOC,
PDO::ATTR_EMULATE_PREPARES => false, // 使用原生預處理
PDO::ATTR_PERSISTENT => true, // 持久連線
];
$pdo = new PDO($dsn, 'user', 'pass', $opt);
try {
$pdo->beginTransaction();
$pdo->exec("INSERT INTO users (name) VALUES ('Alice')");
$pdo->exec("INSERT INTO users (name) VALUES ('Bob')");
$pdo->commit();
} catch (Exception $e) {
$pdo->rollBack();
echo "Failed: " . $e->getMessage();
}
若腳本異常結束未提交,PDO 自動回滾,保障資料一致性。
| 模式常數 | 行為 | 適用場景 |
|---|---|---|
| PDO::ERRMODE_SILENT | 僅設定錯誤碼,需手動檢查 errorCode()/errorInfo() | 舊代碼相容 |
| PDO::ERRMODE_WARNING | 觸發 E_WARNING,不中斷執行 | 除錯階段 |
| PDO::ERRMODE_EXCEPTION | 拋出 PDOException,中斷流程 | 生產環境推薦 |
設定方式:$pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$stmt = $pdo->prepare("SELECT * FROM users WHERE email = :email AND status = :status");
$stmt->bindValue(':email', $email, PDO::PARAM_STR);
$stmt->bindValue(':status', 1, PDO::PARAM_INT);
$stmt->execute();
$user = $stmt->fetch(); // PDO::FETCH_ASSOC
防止 SQL 注入、提升重複執行效能。
PARAM_STR, PARAM_INT, PARAM_BOOL, PARAM_NULL, PARAM_LOB, PARAM_INPUT_OUTPUTFETCH_ASSOC, FETCH_NUM, FETCH_BOTH, FETCH_OBJ, FETCH_CLASS, FETCH_LAZY, FETCH_KEY_PAIRCURSOR_FWDONLY (預設), CURSOR_SCROLLlastInsertId() 取得自增 ID。rowCount() 僅對 DELETE/UPDATE/INSERT 有效,SELECT 不可靠。fetchAll() 一次取回,或迴圈 fetch() 節省記憶體。