PHP 入門

PHP エラーログ記録

エラーをファイルに記録することで、プロダクション環境(本番環境)の問題をトラブルシューティングする際、機密性の高いスタックトレースやサーバーのファイルパスがエンドユーザーに露出するのを防ぐことができます。開発フェーズ(デベロップメント)では画面に直接エラーを表示させるのが便利ですが、error_log() 関数は、後でいつでも確認できるように診断情報を「サイレント」に記録する手段を提供します。

1. error_log() 関数

error_log() 関数は、エラーメッセージをサーバーのログシステムや特定のファイルに送信するための最も核心的なメカニズムです。

最も一般的な構文構造は error_log(string $message, int $message_type = 0, string $destination = null, string $extra_headers = null) です。 $message_type3 に設定すると、PHPは $destination で指定されたファイルにエラーメッセージを追記(アペンド)します。

<?php
// ログファイルの絶対パスを定義
$logFile = __DIR__ . '/logs/app_errors.log';

// データベース接続失敗をシミュレート
$dbConnected = false;

if (!$dbConnected) {
    // タイムスタンプ付きのエラーメッセージを生成
    $timestamp = date('[Y-m-d H:i:s]');
    $errorMessage = "$timestamp データベース接続に失敗しました。ファイル:" . __FILE__ . PHP_EOL;

    // カスタムファイルにエラーを記録(引数 3 はファイルへの追記を意味する)
    error_log($errorMessage, 3, $logFile);
}
?>

この例では、引数 3 がPHPに直接ファイルへの書き込みを指示し、第3引数でファイルのシステムパス(パス)を指定しています。特に注意すべき点として、ウェブサーバーのユーザー(例: www-dataapache)がログファイルを保存するディレクトリに対して書き込み権限(パーミッション)を持っている必要があります。そうでなければログは生成されません。

2. php.ini による PHP エラーログの設定

コード内の潜在的な問題ごとに手動で error_log() を呼び出す代わりに、PHPの実行環境(ランタイム)を直接設定して、すべてのエラーを自動的に専用のファイルに送信させることができます。これは、 php.ini ファイル内の log_errorserror_log ディレクティブを変更することで実現します。

  • log_errors = On: エラーログ記録機能を有効にします。
  • error_log = /path/to/your/custom_log_file.log: エラー情報を書き込む具体的なファイルパスを指定します。

サーバーの php.ini を変更する権限がない場合でも、サーバー設定で許可されていれば、スクリプト内部でこれらの設定を動的に上書き(オーバーライド)することが可能です。

<?php
// 現在のスクリプト実行中のエラーを特定のファイルに強制的に記録する
ini_set('log_errors', '1');
ini_set('error_log', __DIR__ . '/logs/runtime_errors.log');

// 未定義の変数へのアクセスによる Notice は、これで自動的にキャッチされログファイルに書き込まれます
echo $undefinedVariable; 
?>

3. 例外ログのハンドリング

try...catch ブロックを使用する際、プロフェッショナルなベストプラクティスは、例外のテクニカルな詳細をまずログに記録し、その後にユーザーに対して友好的で汎用的なメッセージを表示することです。これにより、ログの明快さを保ちつつ、調査可能なデータを提供し、同時にユーザーエクスペリエンス(UX)とセキュリティを両立させることができます。

<?php
try {
    // ハイリスクな操作:存在しないファイルを開こうとする
    if (!file_exists('data.txt')) {
        throw new Exception("重要なデータファイルが見つかりません。");
    }
} catch (Exception $e) {
    // 開発者が確認できるようにテクニカルな詳細をログに記録
    error_log("エラー:" . $e->getMessage() . " 発生行:" . $e->getLine(), 3, 'error.log');

    // 一般ユーザーには汎用的で友好的なメッセージを表示
    echo "現在、技術的な問題が発生しています。しばらく経ってからもう一度お試しください。";
}
?>

4. エラーログのワークフロー

以下は、アプリケーションが内部でエラーを処理し、ユーザーに情報を提示する際の一連のワークフローです。

  1. アプリケーションロジックの実行 (Application Logic)
  2. エラーが発生したか? (Error Occurs?)
    • いいえ (No) → 通常通りページをレンダリング (Render Page)。
    • はい (Yes) → 例外キャッチ (Catch Exception) フェーズへ。
  3. 例外キャッチ後の処理:
    • バックグラウンド操作: エラー詳細をログファイルに書き込む (Write error to log file)。
    • フロントエンド操作: ユーザーに汎用的なエラーメッセージを表示 (Display generic error to user)。
  4. 実行の継続 (Continue Execution)ページレンダリング (Render Page)