Laravel4、特定のログを別ファイルにする

タグ: Laravel4  

特定のログを別ファイルにする方法です。

ツイートの流れがあり、サービスプロバイダーを書き換える前提の方法はこちら。

これは前提として、ツイートでサービスプロバイダーでクラス変更を行う方法としてどうやるのかという、お題があっての実現方法です。これだけを読んだLaravel初心者のかたが、こんなに面倒臭いことしないとできないのかと思うといけませんので、一応簡単な方法も紹介しておきます。

例えば、app/start/global.phpの最後に、次のように書いておけば、別ファイルでログが保存できます。

$myLogger = new Illuminate\Log\Writer( new Monolog\Logger( 'SQL log' ) );
$myLogger->useFiles( app_path().'/storage/logs/sql.log' );
Event::listen( 'illuminate.query', function( $query ) use( $myLogger )
{
    $myLogger->info( $query );
} );

これで、実行されるSQLのログは取れますが、プレースホルダーの内容が、エクスクラメーションマーク(?)になったままです。これでは読みづらいので、Stackoverflowからの内容を流用し、以下のようにすると、わかりやすくなります。実行時間もログされますしね。

$myLogger = new Illuminate\Log\Writer( new Monolog\Logger( 'SQL log' ) );
$myLogger->useFiles( app_path().'/storage/logs/sql.log' );

// 以下のコードは、stackoverflowから拾ったもの
// http://stackoverflow.com/questions/19131731/laravel-4-logging-sql-queries

Event::listen( 'illuminate.query',
               function( $query, $bindings, $time, $name ) use( $myLogger )
{
    $data = compact( 'bindings', 'time', 'name' );

    // Format binding data for sql insertion
    foreach( $bindings as $i => $binding )
    {
        if( $binding instanceof \DateTime )
        {
            $bindings[$i] = $binding->format( '\'Y-m-d H:i:s\'' );
        }
        else if( is_string( $binding ) )
        {
            $bindings[$i] = "'$binding'";
        }
    }

    // Insert bindings into query
    $query = str_replace( array( '%', '?' ), array( '%%', '%s' ), $query );
    $query = vsprintf( $query, $bindings );

    $myLogger->info( $query, $data );
} );

話の流れがなく、単に別ファイルにログを分けたいと思った時の方法でした。