エラーおよびエラー処理

PDO が提供するエラー処理方法は 3 通り存在し、 アプリケーションの開発形態によって使い分けることができます。

  • PDO::ERRMODE_SILENT

    デフォルトのモードです。ステートメントおよびデータベースオブジェクトの エラーについて、PDO は単にそのエラーコードのみを設定します。 これを取得するには PDO::errorCode() および PDO::errorInfo() メソッドを使用します。 ステートメントオブジェクトへのコールによってエラーが発生した場合は、 そのオブジェクトの PDOStatement::errorCode() あるいは PDOStatement::errorInfo() メソッドを呼び出します。 データベースオブジェクトへのコールによってエラーが発生した場合は、 その代わりにデータベースオブジェクト上の同じメソッドを呼び出します。

  • PDO::ERRMODE_WARNING

    エラーコードを設定することに加え、PDO は 伝統的な E_WARNING メッセージも出力します。この設定はデバッグ/テストの際に有用で、 アプリケーションの動作を妨げることなしに問題点を確認できるように なります。

  • PDO::ERRMODE_EXCEPTION

    エラーコードを設定することに加え、PDO は PDOException をスローします。エラーコードや 関連情報が、クラスのプロパティとして設定されます。 この設定もまたデバッグ時に有用で、エラーが発生した時点で スクリプトの実行を停止させることによりコード内の問題点を 見つけやすくなります (例外によりスクリプトが終了した際には、トランザクションは自動的に ロールバックされることを覚えておきましょう)。

    このモードが有用である理由のひとつとして、伝統的な PHP 形式の警告よりも より明確にエラー処理コードが書けることがあります。例外を発生させず、 データベースへのコールのたびに毎回明示的に返り値をチェックすることに 比べると、コードの量やネストを減らすことができます。

    PHP の例外についての詳細な情報は、 例外 を参照ください。

PDO のエラーコードは、SQL-92 の SQLSTATE エラーコード文字列に 標準化されています。 ネイティブのコードを適切な SQLSTATE コードに変換するのは、個々の PDO ドライバの仕事となります。 PDO::errorCode() メソッドは SQLSTATE コードを返します。 エラーについての詳細な銃尾法が知りたい場合、PDO では PDO::errorInfo() メソッドも提供しており、 これは SQLSTATE コード、ドライバ固有のエラーコードおよびドライバ固有の エラーメッセージを含む配列を返します。

例1 PDO インスタンスの作成およびエラーモードの設定

<?php
$dsn 
'mysql:dbname=testdb;host=127.0.0.1';
$user 'dbuser';
$password 'dbpass';

try {
    
$dbh = new PDO($dsn$user$password);
    
$dbh->setAttribute(PDO::ATTR_ERRMODEPDO::ERRMODE_EXCEPTION);
} catch (
PDOException $e) {
    echo 
'Connection failed: ' $e->getMessage();
}

?>

注意:

PDO::__construct() は、接続に失敗した場合は常に PDOException をスローします。 これは、現在設定されている PDO::ATTR_ERRMODE が何であっても同じです。例外を処理しないと、fatal エラーとなります。

例2 PDO インスタンスの作成およびコンストラクタでのエラーモードの設定

<?php
$dsn 
'mysql:dbname=test;host=127.0.0.1';
$user 'googleguy';
$password 'googleguy';

/*
    ERRMODE を WARNING にした場合でも、コンストラクタを try/catch で囲むのは有効です。
    接続に失敗した場合、ERRMODE が何であろうが PDO::__construct が PDOException をスローするからです。
*/
try {
    
$dbh = new PDO($dsn$user$password, array(PDO::ATTR_ERRMODE => PDO::ERRMODE_WARNING));
} catch (
PDOException $e) {
    echo 
'Connection failed: ' $e->getMessage();
    exit;
}

// このテーブルが存在しないとして、このコードを実行すると E_WARNING レベルのエラーになります。例外にはなりません。
$dbh->query("SELECT wrongcolumn FROM wrongtable");
?>

上の例の出力は以下となります。

Warning: PDO::query(): SQLSTATE[42S02]: Base table or view not found: 1146 Table 'test.wrongtable' doesn't exist in
/tmp/pdo_test.php on line 18