2012-02-19 174 views
0

如何在使用mysqli時正確處理交易和準備語句的錯誤?mysqli - 處理交易錯誤

段:

<?php 
$conn = require_once 'dbconn.php'; 
$conn->autocommit(FALSE); 

$stmt_ins_option = $conn->prepare('INSERT INTO options(option_name) VALUES(?)'); 
$option_name = 'foo'; 
$stmt_ins_option->bind_param('s', $option_name); 
$stmt_ins_option->execute(); 
$conn->commit(); 
if($conn->errno) { 
    $conn->rollback(); 
    echo $conn->error; 
} 

,因爲有該列UNIQUE約束它不會增加它第二次。

但是,腳本也不會報告任何錯誤。

我錯過了什麼?

回答

3

execute在失敗時返回false,因此您可能需要在提交前檢查它。另外,由於您以前提交了事務,因此在您的代碼中回滾不起作用。我喜歡寫東西

try 
{ 
    .... 
    if (!$stmt_ins_option->execute()) 
    { 
    throw new Exception("Cannot insert record. Reason :".$stmt_ins_option->error); 
    // surely, it's better to define your own exception hierarchy 
    } 
    $conn->commit(); 
} 
catch (Exception $e) 
{ 
    $conn->rollback(); 
    // display error/re-raise/ or whatever you think makes sense for your function 
} 
+1

有什麼辦法讓mysqli類拋出異常,而不是每次都檢查錯誤嗎? – Flavius 2012-02-19 16:02:47

+0

@Flavius:我不瘦(我可能是錯的,我有一段時間沒有使用PHP)。但是,您總是可以選擇編寫自己的類,該類繼承自'mysqli'並重寫一對方法,以便引發異常。 – a1ex07 2012-02-19 16:19:20

0

有沒有什麼辦法讓mysqli的類丟不必每次

根據this answer您可以使用以下調用檢查錯誤異常而不是我啓用例外這樣的錯誤:

mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT); 

mysqli_driver::$report_mode

(愚蠢的堆棧溢出不讓我發表評論)