composer require ttbooking/laravel-log-viewer
config/app.php under providers:
Rap2hpoutre\LaravelLogViewer\LaravelLogViewerServiceProvider::class,
php artisan vendor:publish --provider="Rap2hpoutre\LaravelLogViewer\LaravelLogViewerServiceProvider" --tag="config"
routes/web.php:
Route::get('/logs', [\Rap2hpoutre\LaravelLogViewer\LogViewerController::class, 'index']);
/logs to inspect real-time logs without tailing files manually.error, warning, etc.), or search for specific keywords (e.g., SQLSTATE[42S22]).Log Filtering
yesterday, last 7 days).error, critical) via the UI toggle buttons.auth, payment).Integration with Existing Logs
single, daily, syslog handlers).LogViewerController's getLogFiles() method.Security
auth, admin) to restrict access:
Route::get('/logs', [LogViewerController::class, 'index'])->middleware('can:view-logs');
Route::middleware(['ip', 'throttle:60,1'])->group(function () {
Route::get('/logs', [LogViewerController::class, 'index']);
});
Automated Log Review
schedule to trigger log reviews (e.g., daily error reports):
// app/Console/Kernel.php
protected function schedule(Schedule $schedule)
{
$schedule->command('log:review')->dailyAt('9:00');
}
$logs = $this->logViewer->getLogs(['level' => 'error']);
if ($logs->contains('payment_failed')) {
Notifiable::send(new PaymentFailedAlert($logs));
}
formatLogLine() method in a custom controller to redact sensitive data:
public function formatLogLine($line)
{
return preg_replace('/"password":"\w+"/', '"password":"[REDACTED]"', $line);
}
$oldLogs = $this->logViewer->getLogFiles()->where('date', '<', now()->subDays(30));
foreach ($oldLogs as $file) {
Storage::disk('logs')->move($file, "archive/{$file}");
}
Log Rotation Conflicts
logrotate), the viewer may show incomplete or missing logs.log_file_glob_pattern in config/laravel-log-viewer.php matches your rotation scheme (default: storage/logs/laravel-*.log).
'log_file_glob_pattern' => storage_path('logs/laravel-*.log'),
Large Log Files
'max_lines' => 10000,
tail functionality to load logs incrementally (requires custom controller extension).Permission Denied
www-data) lacks read permissions.chmod -R 755 storage/logs/
chown -R www-data:www-data storage/logs/
Lumen Compatibility
bootstrap/app.php:
$app->router->get('/logs', [\Rap2hpoutre\LaravelLogViewer\LogViewerController::class, 'index']);
getLogFiles() output:
dd($this->logViewer->getLogFiles());
syslog), extend the controller:
public function getLogFiles()
{
return [sys_get_temp_dir() . '/custom.log'];
}
log_file_glob_pattern is matching too many files. Use a more specific pattern (e.g., laravel-*.log instead of *.log).formatLogLine() method to add syntax highlighting or context:
public function formatLogLine($line)
{
return highlight_string($line, true);
}
// routes/api.php
Route::get('/api/logs', [LogViewerController::class, 'apiGetLogs']);
Extend the controller to support JSON responses:
public function apiGetLogs(Request $request)
{
return response()->json($this->logViewer->getLogs($request->all()));
}
database log handlers, create a custom adapter to query the failed_jobs or logs tables directly.'timezone' => 'America/New_York',
debug to info):
'log_levels' => [
'debug' => 'Info',
'info' => 'Info',
'notice' => 'Notice',
// ...
],
How can I help you explore Laravel packages today?