Laravel Logging and Debug Logs: A Complete Guide to Log Channels and Error Handling
Developing applications involve combining multiple steps together. Every single steps count and they need to work in harmony to generate the perfect results. Alongside that, Its essential to have a good platform where you can track each step if they are performing correctly to achieve the desired outcome. In such case, logging comes very handy. You can think of them as some check-marks for each step, which needs to be successful for following step. Logging help you to find out every check-mark's real status and debug if something along the way goes wrong and then find out where and why. Laravel log is an amazing way to track the logs and informations of different events. In this article we will explore the ins and outs of Laravel logging and how to use it's different channels in depth .
Laravel Logs: The Secret Weapon for Effortless Debugging
Laravel logging comes with a library called Monolog, and its logging architecture is built on the top if it. You can define different and multiple channels to setup the proper channel to log the informations. Laravel provides its built in log configuration file under config/logging.php. You will see different channels provided in this file:
<?php
use Monolog\Handler\NullHandler;
use Monolog\Handler\StreamHandler;
use Monolog\Handler\SyslogUdpHandler;
return [
'default' => env('LOG_CHANNEL', 'stack'),
'channels' => [
'stack' => [
'driver' => 'stack',
'channels' => ['single'],
'ignore_exceptions' => false,
],
'single' => [
'driver' => 'single',
'path' => storage_path('logs/laravel.log'),
'level' => env('LOG_LEVEL', 'debug'),
],
'daily' => [
'driver' => 'daily',
'path' => storage_path('logs/laravel.log'),
'level' => env('LOG_LEVEL', 'debug'),
'days' => 14,
],
'slack' => [
'driver' => 'slack',
'url' => env('LOG_SLACK_WEBHOOK_URL'),
'username' => 'Laravel Log',
'emoji' => ':boom:',
'level' => env('LOG_LEVEL', 'critical'),
],
'papertrail' => [
'driver' => 'monolog',
'level' => env('LOG_LEVEL', 'debug'),
'handler' => SyslogUdpHandler::class,
'handler_with' => [
'host' => env('PAPERTRAIL_URL'),
'port' => env('PAPERTRAIL_PORT'),
],
],
'stderr' => [
'driver' => 'monolog',
'handler' => StreamHandler::class,
'handler_with' => [
'stream' => 'php://stderr',
],
],
'syslog' => [
'driver' => 'syslog',
'level' => env('LOG_LEVEL', 'debug'),
],
'errorlog' => [
'driver' => 'errorlog',
'level' => env('LOG_LEVEL', 'debug'),
],
'null' => [
'driver' => 'monolog',
'handler' => NullHandler::class,
],
'emergency' => [
'path' => storage_path('logs/laravel.log'),
],
],
];
From the .env, we can define default log channel, otherwise it uses stack and stack has single channel to use for logging as default. You can see the single channel is setup to log informations in logs/laravel.log of storage path. This means, by default all the loggings can be found in this directory.
- Lets write some log messages
Lets try to log some example informations to see how it actually works.
Lets add a route:
use App\Http\Controllers\LogController;
Route::get('/log', [LogController::class, 'index']);
When using logs, we can do different types of logs meaning their status. We can set the type like emergency, error, info, debug alert etc.
Lets add these logs as example to the controller like below:
<?php
namespace App\Http\Controllers;
use Illuminate\Support\Facades\Log;
class LogController extends Controller
{
public function index()
{
Log::emergency('Emergency log message');
Log::alert('Alert log message');
Log::critical('Critical log message');
Log::error('Error log message');
Log::warning('Warning log message');
Log::notice('Notice log message');
Log::info('Info log message');
Log::debug('Debug log message');
return 'Log messages have been recorded!';
}
}
Now run the application and hit the /log url, you should see the message the logs have been successfully added:
php artisan serve
Now you can check the file storage/logs/laravel.log and you will see this output:
- What if I want to use a custom log file?
When you open the laravel.log file, you will see your logging informations of course, but you will also see some other informations too as laravel uses this file for its other logging too. So you might want to use separate channel or file for different kind of logging.
For such case you have to add a new channel in the config/logging.php like this:
'custom' => [
'driver' => 'single',
'path' => storage_path('logs/custom.log'),
'level' => 'debug',
],
To log in this custom channel, you can code like below:
Log::channel('custom')->info('This is a custom log message.');
Now you will find a new log file under storage/logs/custom.log, which will only hold the log informations of custom channel provided from your code.
Understanding the Power of Laravel Logging: Exploring Different Channels
Laravel provides a beautiful architecture to integrate logging very swiftly. Normally we use the default log channel provided in settings, which laravel.log file for these operations. Also we can use custom channel for our convenience. But thats not the end of it, Laravel provides more than that to help you log more easily on multiple channels for your convenience and for that, you dont need to make a lot of changes to log those informations in your own channel. For example, you want to get an instant log informations or notifications to communication application like slack, whenever your production server finds a bug, you can just set the channel configuration and you will receive those directly in slack. Isnt that cool? Today we will try to understand the different log channels provided by Laravel, so we can make the best of this functionality.
- What are the channels I can use?
You can change these channels as your convenience in the config file. Here are a list of channels those can be used as you like:
- Stack: A stack of multiple channels.
- Single: A single log file.
- Daily: A new log file for each day.
- Slack: Send logs to a Slack channel.
- Syslog: Use the system logger.
- Errorlog: Log to the PHP error log.
- Papertrail: Send logs to Papertrail.
If you dont understand these right now, dont worry, I will go them one by one to have better insight on these.
- The stack channel
The stack channel actually consists of an array of mixture of channels, so that your all log information will be posted to every channels in it.
return [
'default' => env('LOG_CHANNEL', 'stack'),
'channels' => [
'stack' => [
'driver' => 'stack',
'channels' => ['daily', 'slack'],
'ignore_exceptions' => false,
],
'daily' => [
'driver' => 'daily',
'path' => storage_path('logs/laravel.log'),
'level' => 'debug',
'days' => 14,
],
'slack' => [
'driver' => 'slack',
'url' => env('LOG_SLACK_WEBHOOK_URL'),
'username' => 'Laravel Log',
'emoji' => ':boom:',
'level' => 'critical',
],
// Additional channels...
],
];
- The Single channel
It is by default used by laravel. Single channel by its definition logs informations to a single file which is logs/laravel.log uner storage directory.
- Daily channel
Daily channel will log daily to the file configured, so that the file doesnt become very large with all the old records of log informations. You can also define how many days these log information should retain. After that, they will be refreshed.
'daily' => [
'driver' => 'daily',
'path' => storage_path('logs/laravel.log'),
'level' => 'debug',
'days' => 14,
],
- Slack channel
Slack is a communication application, which also can be used as channel for logging too. When you go to slack’s account, you can create webhook to use it for logging channel. Then you just have to pass the url and username to connect with your app. Here is a demo:
'slack' => [
'driver' => 'slack',
'url' => env('LOG_SLACK_WEBHOOK_URL'),
'username' => 'Laravel Log', // Optional: The username that will appear on Slack
'emoji' => ':boom:', // Optional: The emoji that will appear next to the username
'level' => 'critical', // The minimum log level at which this channel should be triggered
],
- Syslog channel
Syslog messages are system log messages that are typically used to log system events. These messages are managed by the system logging daemon, which on most Unix-like systems is syslogd or rsyslogd.
'syslog' => [
'driver' => 'syslog',
'level' => 'debug', // Set the desired log level
'facility' => LOG_USER, // Optional, the syslog facility
],
To check messages, you might want to check the system log messages typically located in /var/log/syslog or /var/log/messages.
- Errorlog channel
This channel is used to produce error to php error log messages. Usually on shared hosting servers or apache or php servers can be ideal for generating such kind of logs if you are interested in this way:
'channels' => [
// Other channels...
'errorlog' => [
'driver' => 'errorlog',
'level' => 'debug',
],
],
You can typically find these logs under apache/error.log, /var/log/php_errors.log, /var/log/apache2/error.log, /var/log/nginx/error.log. These can be different based upon the system you use.
This location can also be configured from php.ini from your server’s php intallation:
; Example from php.ini
error_log = /path/to/php_error.log
- Papertrail channel
Papertrail is a cloud-based log management service that aggregates log messages from various sources, allowing for real-time monitoring, searching, and alerting. Laravel integrates seamlessly with Papertrail, enabling you to send your application logs directly to Papertrail for centralized log management.
You need to create a papertrail account and fill the required information in laravel log config like below:
return [
'default' => env('LOG_CHANNEL', 'stack'),
'channels' => [
// Other channels...
'papertrail' => [
'driver' => 'monolog',
'level' => 'debug',
'handler' => \Monolog\Handler\SyslogUdpHandler::class,
'handler_with' => [
'host' => env('PAPERTRAIL_URL'),
'port' => env('PAPERTRAIL_PORT'),
],
],
],
];
Stack Channels for Powerful Log Management
We have learnt about different channels that can be used for logging in Laravel. Among those channels, one of the most popular and used channel is stack. Its actually not a unique channel like others, rather it is a mixture of multiple channels. I suppose it very helpful because thats how you can configure as many channels as you want to get log informations simultaneously in all the way at the same time. Lets explore how exactly to use this stack channel in details.
- How to use stack channel
Lets imagine a scenario, you want to get your log informations daily and also you want to log on your slack application. For such scenario, you first define the daily and custom log channel configuration in log settings.
Then, you can use stack channel to set this up for both of this channel to work parallelly to produce log messages to each of these channels.
Here is an example:
return [
'default' => env('LOG_CHANNEL', 'stack'),
'channels' => [
'stack' => [
'driver' => 'stack',
'channels' => ['daily', 'slack'],
'ignore_exceptions' => false,
],
'daily' => [
'driver' => 'daily',
'path' => storage_path('logs/laravel.log'),
'level' => 'debug',
'days' => 14,
],
'slack' => [
'driver' => 'slack',
'url' => env('LOG_SLACK_WEBHOOK_URL'),
'username' => 'Laravel Log',
'emoji' => ':boom:',
'level' => 'critical',
],
// Additional channels...
],
];
You can see, we have set up the daily channel with 14 days of retaining old informations, and logging to laravel.log in storage/logs directory.
Also with slack, you have to provide your informations to connect with slack account with this config.
Then on top, the stack channel is taking an array of channels, where we have defined daily and slack as to use them both for logging.
And over that, we are also setting up stack as our default channel, unless you provide any other channel from env with LOG_CHANNEL parameter.
So now you can use directly the Log facade to generate messages to default stack channel:
use Illuminate\Support\Facades\Log;
Log::debug('This is a debug message');
Log::info('This is an info message');
Log::warning('This is a warning message');
Log::error('This is an error message');
- What if stack is not my default channel?
Yes, that can also be a situation, that you want to specifically produce messages to stack but also stack is not your default channel. So then, you will have to define the stack channel with Log facade like this:
Log::channel('stack')->info('This message will be logged to both the daily file and Slack');
- Advantages of Using Stack Channels
Centralized Logging: Stack channels allow you to centralize logging configurations, making it easier to manage and ensure consistency across different log outputs.
Redundancy: Logging to multiple channels ensures that even if one channel fails, the log messages are still captured in other channels.
Flexibility: You can combine various logging mechanisms (files, remote services, third-party tools) to suit your monitoring and debugging needs.
Laravel Log: How to Use Daily Channel
When logging, laravel by default use single as primary channel for logging. That means, it will log into a single file, and that file after some days, months, or years of usage might become too large if we continue. Its not very suitable approach for large scale applications if you consider disc space and other complexities in concern. To help with that, Laravel also provides another channel named daily, which can create separate log file and also manage disc space all together. Now we will see how to use this channel for logging in large scale applications.
- How to setup daily channel
To setup logging daily in laravel, you have to set the config like below in config/logging.php:
'daily' => [
'driver' => 'daily',
'path' => storage_path('logs/laravel.log'),
'level' => env('LOG_LEVEL', 'debug'),
'days' => 14,
],
Now, here driver needs to be setup as daily, path can be by default logs/laravel.log in storage directory.
Also please set the default log channels as daily in the .env:
LOG_CHANNEL=daily
When you use the daily channel, it actually creates every day a new log file on the given directory. It assigns the current date on the file, which helps you not to put pressure on a single file for all the logs from start to end. This also helps you to find out the specific log or error message on the given timestamp. Cool, right?
- How to manage storage space then?
These log files also can put pressure on storage of course. For example, if the application starts to create new log files everyday, there will be a log which would take too much space. To resolve this you can also use days parameter, and the value here will work as the number of days that laravel should retain the log files from current. In other words, if you set the value 14, it will keep only the files from current date to previous 14 days, and will delete all the files before that. You can tweak this value for your own comfortable amount.
- If it creates new file, then why the path parameter is required?
Yes, you might wonder that, as Laravel automatically creates a new file each day assigning date on file, then why need to pass a file path like single channel. It is actually works as default naming for each file, and also Laravel add the date stamp with this file name.
For example, if you provide laravel.log in the path, it will generate the file names like below everyday:
storage/logs/
├── laravel-2024-06-10.log
├── laravel-2024-06-11.log
├── laravel-2024-06-12.log
├── laravel-2024-06-13.log
└── laravel-2024-06-14.log
- Now generate logs
To generate logs daily, here is how you can do it:
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Log;
class ExampleController extends Controller
{
public function index()
{
// Log different types of messages
Log::info('Info log from ExampleController');
Log::warning('Warning log from ExampleController');
Log::error('Error log from ExampleController');
return view('welcome');
}
}
Alternatively you can use, logger helper:
// Log an informational message
logger('This is an informational message using the logger helper.');
Summary
You can see, how amazing and quick it is to use these logging in laravel. Logging can help you to test your codes in different places, so you can easily track the bugs if there and track the reasons or triggers. When you have built a functionality, you can set logging in several places as expected result, and then check if those logs are reported in time.
It is very convenient to integrate so much channels you need to keep your application’s performance under you surveillance. You dont just have to always come back to sign into your server and run commands to see updated logs, rather by setting up the channel you can direct notifications to mobile by email or channels like slack or paperback.
Also we have seen, stack channel is very handy when you need multiple logging features in your application. For simple applications, you might prefer default or single logging system, but for large scale or complex applications, stack is very helpful for devs.
Laravel makes it very flexible to use many different options for logs so that you dont miss out anything as your requirement. Thank you for reaching us out. Let me know your thoughts in the comments.
I wish you a happy day.
Comments