Présentation

La plupart des tutoriels de notification Wazuh s'arrêtent à « interroger un fichier JSON toutes les quelques secondes et le transférer ». Ce projet adopte l'approche inverse : il connecte directement le module Integrator de Wazuh à un workflow n8n via un webhook de production authentifié, afin que les alertes circulent en temps réel et soient validées et dédupliquées avant d'être présentées à quiconque.

Lorsque le webhook n8n est injoignable au moment de la livraison, les alertes sont mises en file d'attente de manière persistante sur disque, et un timer systemd vide automatiquement cette file dès que n8n est de nouveau disponible — ce qui a été testé en arrêtant n8n en plein traitement et en confirmant la reprise automatique.

Il a été construit, mis en défaut et corrigé sur une infrastructure réelle — avec notamment un véritable agent sur endpoint Windows, une simulation de force brute contrôlée, une alerte déclenchée accidentellement par moi-même, et un véritable problème opérationnel (un afflux d'alertes issu d'un scan de conformité) diagnostiqué et résolu pendant la validation en laboratoire. Chaque affirmation de cette étude de cas s'appuie sur une paire de captures d'écran appariées : l'une issue du dashboard Wazuh, l'autre de l'e-mail correspondant, avec le même identifiant de règle et le même horodatage.

Architecture

ÉtapeComposantRôle
1Hôte superviséLe manager Linux et l'agent de l'endpoint Windows génèrent les événements bruts : journaux d'authentification, activité sudo, modifications d'intégrité des fichiers, contrôles de conformité
2Wazuh ManagerDécode et classe les événements, attribue un identifiant de règle et un niveau de sévérité
3Wazuh IntegratorUn script personnalisé se déclenche à partir du niveau ≥ 7, s'authentifie à l'aide d'un jeton secret transmis en en-tête et publie vers le webhook — piloté par les événements, sans boucle d'interrogation
4Webhook n8nPoint d'entrée authentifié par jeton en en-tête ; répond 202 immédiatement après l'authentification, puis transmet au traitement
5NormalisationAplatit l'alerte brute dans une structure homogène et associe le niveau de la règle à un libellé de sévérité
6ValidationRejette les payloads malformés ou incomplets avant qu'ils ne se propagent
7DéduplicationSuit les identifiants d'événements déjà traités ; les doublons sont écartés silencieusement
8Routage par sévéritéAiguille selon le libellé de sévérité ; les sources de faible sévérité et les sources bruyantes explicitement exclues ne génèrent jamais d'e-mail
9Mise en formeGénère un rapport HTML ; l'objet de l'e-mail suffit à lui seul pour le triage
10Envoi GmailExpédie via un compte authentifié en OAuth2, sous une identité d'expéditeur dédiée

Si le webhook est injoignable à l'étape 4, l'alerte est écrite dans une file d'attente locale sur disque au lieu d'être perdue. Un timer systemd relance l'envoi toutes les 60 secondes et vide automatiquement la file dès que n8n est de nouveau disponible.

Schéma d'architecture du pipeline

Cas de test — chaque affirmation étayée par une paire de captures d'écran appariées

Chaque cas ci-dessous associe la détection côté Wazuh à la notification qui en résulte — même identifiant de règle, même horodatage — ce qui démontre le fonctionnement du pipeline de bout en bout, et non une démonstration simulée.

Cas 1 — Détection d'une force brute contrôlée

Une simulation contrôlée de force brute SSH visant un utilisateur inexistant, menée au sein du laboratoire local autorisé, a été détectée nativement par Wazuh (règle 5712, niveau 10) puis transmise automatiquement, sans aucune intervention manuelle.

Cas 2 — Déduplication vérifiée

Le même identifiant d'événement a été soumis deux fois de suite. La première exécution a parcouru toute la chaîne jusqu'à Gmail ; la seconde a été proprement filtrée à l'étape de déduplication et n'a jamais atteint la boîte de réception — un incident, une notification.

Cas 3 — Une alerte accidentelle, entièrement authentique

Lors du débogage d'un problème de permissions sur une clé SSH, trois fautes de frappe consécutives dans le mot de passe sudo ont déclenché une véritable détection Wazuh (règle 5404, « Three failed attempts to run sudo ») sans aucune mise en scène. L'alerte est arrivée dans la boîte de réception en temps réel.

Cas 4 — Un véritable endpoint Windows, et une leçon de tuning

Un véritable agent Wazuh a été déployé sur un hôte Windows 11. Son module Security Configuration Assessment a exécuté un scan complet du benchmark CIS — 482 contrôles, dont 350 en échec, nombre d'entre eux de niveau 7 ou plus. La déduplication reposant sur l'identifiant d'événement, et chaque contrôle possédant le sien, chaque contrôle en échec a produit sa propre alerte, indépendante et valide — un véritable afflux d'alertes.

La déduplication par identifiant d'événement est pertinente pour supprimer une copie retransmise d'un même incident, mais elle ne peut pas regrouper un lot de sous-événements réellement distincts issus d'une même source bruyante — ce filtrage doit intervenir en amont. Le pipeline s'est comporté exactement comme configuré ; le volume a révélé l'absence de filtre de périmètre sur une source qui n'avait jamais vocation à alerter qui que ce soit.

Correctif

Action immédiate : stopper l'afflux à la source. Correctif durable : exclure le groupe de règles sca du chemin de transfert en temps réel, tout en le laissant visible dans le Wazuh Dashboard pour une revue périodique — implémenté dans wazuh/custom-n8n (EXCLUDED_RULE_GROUPS).

Enseignements

  • L'approche événementielle l'emporte sur l'interrogation périodique. Le raccordement direct de l'Integrator a maintenu la latence d'alerte observée à quelques secondes à peine sur l'ensemble des cas de test.
  • La déduplication exige un périmètre, pas seulement une clé. Une clé fondée sur le seul identifiant d'événement convient aux incidents réels, mais une source bruyante qui génère un nouvel identifiant par sous-contrôle la contourne entièrement — le correctif relève du filtre à la source, pas de la logique de déduplication.
  • Un test d'indisponibilité n'est probant que si l'on arrête le service en plein traitement. Arrêter le conteneur et observer la file sur disque se vider automatiquement au redémarrage prouve la reprise ; la simuler dans le code ne prouve rien.
  • Le meilleur mode de défaillance est un mode bruyant. L'afflux lié au scan de conformité a été diagnostiqué et sa cause racine identifiée en quelques minutes, car le pipeline a remonté chaque alerte individuellement au lieu de masquer silencieusement les erreurs.

Mesures de sécurité

  • Le webhook de production n8n exige une authentification par jeton transmis en en-tête — et non un jeton intégré à l'URL.
  • Le script Wazuh Integrator lit le jeton depuis un fichier appartenant à root et à accès restreint au groupe (640, root:wazuh) ; il n'est jamais codé en dur ni journalisé.
  • L'envoi via Gmail utilise OAuth2 — aucun mot de passe d'application n'est stocké en clair.
  • n8n écoute uniquement sur 127.0.0.1 ; l'accès distant passe par un tunnel SSH, sans jamais d'exposition directe.
  • Le pare-feu de l'hôte applique un refus par défaut, avec des règles d'autorisation explicites limitées aux ports nécessaires.
  • Les secrets, jetons et identifiants de credentials sont exclus du dépôt ; les captures d'écran ont été relues avant publication — seules des adresses de laboratoire privées RFC1918 y sont visibles.