Laravelのログ出力でdaily
チャネルを利用した場合、storage/logs/laravel-2024-05-25.log
といったファイルに出力されます。.env
のLOG_DAILY_DAYS
で1以上を設定し保存数を制限する場合は問題にならないのですが、0を設定し無制限にログファイルを残しておく場合にファイルが増えてしまいます。
ログファイルの保存ディレクトリ、ファイル名をある程度制御できるようにします。
Laravelのバージョンは11で試しています。
簡単だけどダメな方法
一見正しく動作しそうな方法を紹介します。
開発中は期待通りに動作しますが、本番環境にデプロイした際に期待通りにならなくなります。
config/logging.php
のpath
にdate('Y-m')
を差し込み、月ごとのディレクトリに出力をします。
'channels' => [
'single' => [
'driver' => 'single',
'path' => storage_path('logs/' . date('Y-m') . '/laravel.log'),
'level' => env('LOG_LEVEL', 'debug'),
'replace_placeholders' => true,
],
]
何がダメなのか
php artisan config:cache
コマンドによる設定キャッシュを行った際に、path
の値がコマンド実行時点の値でキャッシュされてしまうので、出力先が固定されてしまいます。
タスクスケジュールで定期的に `php artisan config:cache` をじkk
独自チャネルを作成する
出力先のディレクトリを動的に変更するには、独自チャネルを生成し、Monologのインスタンス生成時にpathを設定する必要があります。
下記のページを参考に独自チャネルを追加します。
CreateCustomLogger クラスの作成
Monologのインスタンスを生成するクラスを作成します。
<?php
namespace App\Logging;
use Monolog\Logger;
use Monolog\Handler\StreamHandler;
use Monolog\Processor\PsrLogMessageProcessor;
use Monolog\Formatter\LineFormatter;
class CreateCustomLogger
{
/**
* Create a custom Monolog instance.
*/
public function __invoke(array $config): Logger
{
$path = str_replace(
['{year}', '{month}', '{day}'],
[date('Y'), date('m'), date('d')],
$config['path']
);
$handler = new StreamHandler(
$path,
$config['level'] ?? 'debug',
$config['bubble'] ?? true,
$config['permission'] ?? null,
$config['locking'] ?? false
);
$handler->setFormatter(new LineFormatter(null, 'Y-m-d H:i:s', true, true, true));
return new Logger('log', [$handler], [new PsrLogMessageProcessor()]);
}
}
独自チャネルの設定を追加
config/logging.php
に独自チャネルの設定を追加します。
'channels' => [
'example-custom-channel' => [
'driver' => 'custom',
'via' => App\Logging\CreateCustomLogger::class,
'path' => storage_path('logs/{year}-{month}/laravel-{year}-{month}-{day}.log'),
'level' => env('LOG_LEVEL', 'debug'),
],
],
解説と注意点
config/logging,php
のpath
に含まれる{year}
、{month}
、{day}
をCreateCustomLogger
クラスで変換することで動的にログファイルの出力先のディレクトリを動的に変更しています。
Monologのインスタンスが生成された時点で出力先のディレクトリが決定するため、処理が日をまたいだ場合でも、Monologのインスタンスで持っているpathの出力先に出力されます。
[AD]