2012-02-23 90 views
3

代碼:如何抑制來自DBI的任意警告/錯誤消息?

# A: 
$dbh->do(qq/insert into foo(cl) values('test')/); 
# B: 
$dbh->do(qq/insert into foo(cl) values('test')/) or warn $dbh->errstr; 
# C: 
eval { $dbh->do(qq/insert into foo(cl) values('test')/); }; 
warn "error : [email protected] " if [email protected]; 

所有將輸出:

DBD::mysql::db do failed: Duplicate entry 'test' for key 'cl' at a.pl line 9. 

我不希望這個任意警告/錯誤信息發送到stderr。我想使用warn $dbh->errstr

perl a.pl 2>/dev/null會壓制錯誤消息,但我想知道如何在腳本中執行此操作?

回答

8

您需要安裝自己的錯誤處理程序。例如。

$dbh->do($statement, { HandleError => \&handle_error }); 

的錯誤處理DBI POD

描述的另一種選擇是:

  • 設置PrintWarn屬性值(在一些論壇思南的回答禮貌

  • 通過信號處理程序捕獲所有警告:$SIG{'__WARN__'} = sub {};

2

現在我一般做以下

  1. 創建DBI手柄時,務必通過RaiseError => 1PrintError => 0。現在,您不必爲每個DBI調用添加錯誤處理程序。
  2. 對於那些我不關心重複鍵錯誤,捕捉和忽略例外聲明:

    use Try::Tiny; 
    try { $dbh->do(...) } 
    catch { die $_ unless /execute failed: Duplicate entry/ }; 
    

這是我找到的最好方式 - INSERT IGNORE忽略所有錯誤,不只是重複密鑰錯誤,並且REPLACE將使用刪除並插入來覆蓋現有行。 INSERT INTO ... ON DUPLICATE KEY UPDATE id=id可能可以使用,但我認爲捕捉錯誤更明確。