Laravel : Ajouter des informations supplémentaires aux logs
La gestion des logs sur Laravel, c'est génial ! Sans configuration ou avec seulement quelques lignes, on peut facilement choisir où enregistrer les logs, ses journaux d'informations absolument indispensables au bon maintient d'une application.
Malheureusement, on peut rapidement manquer d'information, notamment en production, pour bien comprendre comment le bug s'est produit et pouvoir ainsi le résoudre.
Fort heureusement, Laravel propose de personnaliser tout ça et l'on peut facilement ajouter des informations complémentaires à chaque log.
Ce tutoriel est issu d'un cas pratique où j'avais besoin d'ajouter ces 4 informations aux logs :
- Utilisateur connecté ou visiteur dans le cas contraire
- IP de l'utilisateur
- Méthode de la requête (GET, POST, PUT...)
- URI (= URL + paramètre GET de la requête)
Personnaliser l'écriture des logs
Ajouter des informations
Pour commencer, il vous faut créer une classe qui sera instanciée à chaque log et qui s'occupera de personnaliser les données. Personnellement, j'ai créé une classe CustomizeFormatter, dans app/Logging/CustomizeFormatter.php. Vous êtes libre de renommer cette classe et de la placer dans un autre dossier, ceci à peu d'importance.
Dans mon cas, j'avais besoin d'injecter (via l'injection des dépendances) la Request. Vous pouvez personnaliser le constructeur selon vos besoins, voir le supprimer.
<?php
namespace App\Logging;
use Illuminate\Http\Request;
use Monolog\Formatter\LineFormatter;
class CustomizeFormatter
{
protected $request;
public function __construct(Request $request = null) {
$this->request = $request;
}
}
Il faut ensuite une fonction qui prend en paramètre un tableau $record. Cette variable contient toutes les informations du log qui va être inséré dans les fichiers journaux. La variable doit ce même tableau, avec les données additionnelles. J'ai appelé cette fonction processLogRecord.
Voici ce que contient la variable $record, si on essaie de créer un log avec Log::info('test')
:
array:7 [ ▼
"message" => "test"
"context" => []
"level" => 200
"level_name" => "INFO"
"channel" => "local"
"datetime" => Monolog\DateTimeImmutable @1637680814 {#554 ▼
-useMicroseconds: true
date: 2021-11-23 16:20:14.637234 Europe/Monaco (+01:00)
}
"extra" => []
]
Nous allons ajouter nos informations complémentaires dans le tableau extra.
Pensez à bien merge vos données avec celles qui pourraient déjà être présente dans la variable $record['extra'], sous peine de perdre des données.
public function processLogRecord(array $record): array {
// Only if Request could be injected
if ($this->request) {
$record['extra'] += [
'user' => $this->request->user()->email ?? 'guest',
'ip' => $this->request->getClientIp(),
'method' => $this->request->getMethod(),
'uri' => $this->request->getUri()
];
}
return $record;
}
Choisir les informations à afficher pour chaque log
Une fois les données que vous souhaitez ajouter dans la variable $record['extra'], il vous faut créer une fonction __invoke() qui sera appelé à chaque instanciation de la classe et qui a pour but de :
- appeler la fonction pour ajouter des données complémentaires
- personnaliser le format d'affichage du log
Pour afficher une information précédemment ajoutée, l'IP par exemple, il vous suffit d'utiliser le shortcode suivant : %extra.ip%.
Vous pouvez utiliser et personnaliser le code ci-dessous, qui est une bonne base.
A noter qu'il faut utiliser \n pour effectuer un retour à la ligne.
public function __invoke($logger) {
foreach ($logger->getHandlers() as $handler) {
$handler->pushProcessor([$this, 'processLogRecord']);
$handler->setFormatter(new LineFormatter(
"[%datetime%] %channel%.%level_name%: %message%\nUser : %extra.user%\nIP : %extra.ip%\nURL: %extra.method% %extra.uri%\n%context% %extra%\n\n", 'Y-m-d H:i:s'));
}
}
Appliquer la personnalisation
Maintenant que notre classe est prête à personnaliser les données des logs, il ne reste plus qu'à configurer son utilisation.
Dans le fichier config/logging.php, rajouté une clé tap avec pour valeur un tableau qui contient la classe que vous venez de créer, le tout dans la configuration de log que vous souhaitez personnaliser.
'daily' => [
'driver' => 'daily',
'tap' => [\App\Logging\CustomizeFormatter::class], // Add this line
'path' => storage_path('logs/laravel.log'),
'level' => 'debug',
'days' => 14,
],
Vos logs devraient désormais être agrémentés de données supplémentaires ! Bon débogage !
Besoin d'aide pour votre projet Web ?
- Création de sites internet
- Référencement naturel (SEO)
- Développement d'application Web
- Développeur Laravel / VueJS
