L’envoi direct de notifications dans un contrôleur peut rendre votre code Laravel difficile à maintenir.
Cela peut entraîner une organisation confuse, rendant le code moins lisible et plus sujet aux erreurs.
Cet article propose de décaler la logique d’envoi vers des listeners, permettant un envoi asynchrone et une meilleure gestion des erreurs.
Initiez-vous à Laravel et réalisez votre première application en toute confiance.
Envoyer des notifications via des listeners dans Laravel est une pratique courante pour découpler la logique de votre application et rendre le code plus lisible et modulaire. Dans cet axe, nous allons expliquer comment déplacer l’envoi de notifications de votre contrôleur vers un listener, ce qui permet de gérer cette tâche de manière asynchrone et plus structurée. Cela permet aussi de retarder l’envoi et de gérer les échecs de manière efficace. Vous apprendrez comment refactoriser votre code pour intégrer cette logique, tester le fonctionnement et comprendre le flux complet de l’événement jusqu’à la réception de la notification.
Adapter CommentController pour Laravel listeners
Dans Laravel, les contrôleurs gèrent les requêtes HTTP, mais parfois, certaines actions, comme l’envoi de notifications, peuvent être déplacées dans des listeners pour améliorer l’organisation du code. Regardons d’abord la méthode store dans CommentController.
Avant modification :
Dans la version actuelle de votre code, la notification est envoyée directement dans le contrôleur :
if(auth()->id() !== $article->user_id) // Si le commentateur n'est pas l'auteur de l'article
{
$when = now()->addSeconds(10);
$article->user->notify((new NewComment($comment))->delay($when));
}
Ici, lorsque le commentaire est ajouté, la notification est envoyée immédiatement après l’ajout du commentaire, avec un délai de 10 secondes.
Après modification :
Nous allons déplacer la logique d’envoi de la notification dans un listener. Pour cela, vous allez déclencher un événement qui sera écouté par un listener. Remplacez les lignes du contrôleur par ceci :
if(auth()->id() !== $article->user_id) //si le commentateur n'est pas l'auteur de l'article
{
event(new CommentWasCreated($comment));
}
Cet événement CommentWasCreated sera capturé par un listener qui se chargera de l’envoi de la notification.
Modification du listener CommentWasCreated
Maintenant, nous allons modifier le listener CommentWasCreated pour qu’il gère l’envoi de la notification. Ce listener se trouve dans le dossier App\Listeners.
Avant modification :
Initialement, la méthode handle du listener ne fait rien :
public function handle(CommentEvent $event)
{
// ici
}
Après modification :
Nous allons ajouter la logique d’envoi de la notification dans la méthode handle. Voici le code modifié :
public function handle(CommentEvent $event)
{
$when = now()->addSeconds(10);
$event->comment->article->user->notify((new NewComment($event->comment))->delay($when));
}
Explications :
- now()->addSeconds(10) :Définit un délai de 10 secondes avant l’envoi de la notification.
- $event->comment->article->user :Obtient l’utilisateur qui est l’auteur de l’article.
- notify() :Envoie la notification en utilisant la classe NewComment.
- delay($when) :Ajoute un délai avant l’envoi de la notification.
Implémenter shouldDiscoverEvents en Laravel
Laravel permet de découvrir automatiquement les événements et les listeners sans avoir à les enregistrer manuellement. Pour activer cette fonctionnalité, vous devez ajouter la méthode suivante dans App\Providers\EventServiceProvider :
public function shouldDiscoverEvents()
{
return true;
}
Cela permet à Laravel de découvrir et d’enregistrer automatiquement tous vos événements et listeners.
Explication :
Cette fonction permet à Laravel de découvrir automatiquement les listeners sans avoir besoin de les enregistrer manuellement dans le fichier de configuration EventServiceProvider.
Gestion file d'attente et échecs avec Laravel
Pour s’assurer que la notification est correctement mise en file d’attente et que les erreurs sont gérées, nous devons modifier le listener CommentWasCreated pour qu’il implémente l’interface ShouldQueue.
CommentWasCreated implements ShouldQueue
{
//
}
Cela permet de mettre la notification dans une file d’attente et d’assurer une gestion asynchrone.
Gestion des échecs
Si une erreur se produit lors de l’envoi de la notification, nous pouvons utiliser la méthode failed() pour gérer l’échec :
public function failed(CommentEvent $event, $exception)
{
dd($event, $exception);
}
Cela affichera l’erreur et l’événement si l’envoi échoue, ce qui est utile pour le débogage.
Tester les notifications asynchrones avec un commentaire
Pour tester cette configuration, créez un commentaire dans votre application, par exemple « Hello World! ». Vous devriez voir la notification apparaître dans votre boîte de réception (via Mailtrap, par exemple), après le délai de 10 secondes. Si une erreur se produit, elle sera affichée grâce à la méthode failed().
Résultat attendu :
- Vous recevrez un e-mail contenant le message de la notification.
- Laravel Horizon vous permet de surveiller vos jobs en file d’attente. Si tout fonctionne correctement, vous verrez le job marqué comme « complété ». Si une erreur se produit, vous le verrez comme « échoué » avec l’erreur correspondante..
El lorsqu’en clique sur cette notification vous avez voir les information supplémentaire de ce commentaire comme ceci :
Formez-vous gratuitement avec Alphorm !
Maîtrisez les compétences clés en IT grâce à nos formations gratuites et accélérez votre carrière dès aujourd'hui.
FAQ
Comment envoyer des notifications via des listeners Laravel ?
Pourquoi utiliser des listeners pour les notifications Laravel ?
Comment gérer les échecs d'envoi de notifications dans Laravel ?
Comment tester l'envoi de notifications avec Laravel ?
Quelle est l'importance de shouldDiscoverEvents dans Laravel ?
Conclusion
En utilisant des listeners pour envoyer des notifications dans Laravel, vous améliorez la modularité et l’efficacité de votre code. Avez-vous essayé d’autres méthodes pour gérer les notifications asynchrones dans vos applications Laravel ?