Funk-lab/admin/k8s/n8n.md
alkatrazz 12f219c83b docs: documenter Open WebUI, n8n et mettre à jour l'état du projet
- CLAUDE.md : état au 2026-05-29 — Open WebUI + n8n , LiteLLM sur
  0.0.0.0, postfix Gmail SMTP, suppression  workloads IA
- admin/k8s/open-webui.md : architecture, déploiement, credentials,
  dépannage, différence avec Hermes TUI
- admin/k8s/n8n.md : architecture, 2 workflows documentés (alertes +
  rapport horaire), 8 idées de workflows futurs, opérations courantes,
  dépannage

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-29 18:10:46 +02:00

8.4 KiB

n8n — Automatisation de workflows

n8n est le moteur d'automatisation du lab. Il orchestre les tâches récurrentes, connecte les services entre eux et envoie des rapports/alertes par email via LiteLLM + Postfix.


Accès

URL http://n8n.lab.local
Namespace k8s ai
Port interne 5678
API key générée dans Settings → n8n API

Architecture

Déclencheurs                 Pipeline                        Sortie
────────────                 ────────                        ──────
AlertManager webhook    →    Formatage JSON                  Email Gmail
Cron (toutes les heures) →  Requêtes Prometheus        →    (via Postfix :25)
Webhook manuel          →    LiteLLM hermes-default
                             (résumé/analyse)

SMTP : n8n envoie via Postfix sur 192.168.10.1:25 (pas d'auth, réseau interne). Postfix relaie vers smtp.gmail.com:587 avec App Password.

LLM : n8n appelle LiteLLM sur http://192.168.10.1:4000/v1/chat/completions avec model: hermes-default.


Déploiement (ArgoCD)

Manifests dans k8s/apps/n8n/ :

  • deployment.yaml — pod n8n
  • service.yaml — ClusterIP :5678
  • ingress.yaml — IngressRoute Traefik
  • pvc.yaml — données applicatives (NFS)
  • secret.yaml — secrets (non commité, à créer manuellement)

Application ArgoCD : k8s/apps-of-apps/apps/n8n.yaml

Créer le secret (première installation)

kubectl create secret generic n8n-secret -n ai \
  --from-literal=db-password="PASSWORD" \
  --from-literal=encryption-key="$(openssl rand -hex 32)"

Le mot de passe est dans le vault Ansible (vault_pg_n8n_password).


Credentials configurées

Nom Type Détail
Postfix local SMTP 192.168.10.1:25, sans auth, STARTTLS désactivé

Pour créer une credential OpenAI/LiteLLM manuellement : Settings → Credentials → New → OpenAI → Base URL: http://192.168.10.1:4000/v1, API Key: lm-studio


Workflows actifs

1. Alertes Prometheus → Résumé LLM → Gmail

ID : 4lfZ0sHZqQ5HYEph
Déclencheur : Webhook POST sur http://n8n.lab.local/webhook/alerts
Configuré dans : k8s/infra/monitoring/values.yaml (receiver AlertManager)

Pipeline :

AlertManager POST
    │
    ├── Respond to Webhook (répond OK immédiatement)
    │
    ▼
Format Alertes (Code)
  → extrait alertname, instance, severity, summary, description
    │
    ▼
Résumé LLM (HTTP Request → LiteLLM)
  → system: "assistant ops, résumé concis en français"
    │
    ▼
Envoyer Email (SMTP)
  → Subject: [Funk] N alerte(s) — firing/resolved
  → Body: résumé LLM

Test manuel :

curl -X POST http://n8n.lab.local/webhook/alerts \
  -H "Content-Type: application/json" \
  -d '{
    "version":"4","status":"firing","receiver":"n8n-webhook",
    "alerts":[{
      "status":"firing",
      "labels":{"alertname":"HighMemory","instance":"192.168.10.12:9100","severity":"warning"},
      "annotations":{"summary":"RAM élevée","description":"RAM > 85%"}
    }]
  }'

2. Rapport Horaire Système — Funk

ID : i2KAGxBFDps7IjIP
Déclencheur : Cron toutes les heures (:00)

Pipeline :

Schedule (toutes les heures)
    │
    ├── CPU (Prometheus)          avg 1h par nœud
    ├── Mémoire (Prometheus)      avg_over_time 1h
    ├── Mémoire Max (Prometheus)  max_over_time 1h
    ├── Disque (Prometheus)       snapshot actuel
    ├── Services (Prometheus)     up/down
    └── Services Changes          changements d'état sur 1h
    │
    ▼
Format Rapport (Code)
  → tableau métriques par nœud (avg/max mémoire, CPU moyen 1h)
  → liste services stables/instables
    │
    ▼
Analyse LLM (HTTP Request → LiteLLM)
  → system: "résumé état général, points d'attention, recommandation"
    │
    ▼
Préparer Email (Code)
  → assemble : résumé LLM + séparateur + tableau métriques
    │
    ▼
Envoyer Rapport (SMTP)
  → Subject: [Funk] Rapport systeme - DD/MM/YYYY HH:MM:SS
  → Body HTML (pre tag) : résumé + métriques

Queries Prometheus utilisées :

Nœud Query
CPU 100 - (avg by(instance) (rate(node_cpu_seconds_total{mode="idle"}[1h])) * 100)
Mémoire avg_over_time((1 - node_memory_MemAvailable_bytes / node_memory_MemTotal_bytes)[1h:5m]) * 100
Mémoire Max max_over_time((1 - node_memory_MemAvailable_bytes / node_memory_MemTotal_bytes)[1h:5m]) * 100
Disque (filesystem_size - filesystem_free) / filesystem_size * 100 (mountpoint=/)
Services up
Services Changes changes(up[1h]) > 0

Workflows à ajouter

Court terme

Alerte disque > 80%
Cron toutes les 30 min → query Prometheus disk > 80 → si résultat non vide → email d'alerte.
Utile car AlertManager ne couvre pas toujours les seuils fins par nœud.

Redémarrage automatique pod crashé
Webhook AlertManager sur KubePodCrashLoopingkubectl rollout restart via HTTP Request vers l'API k8s (ou script SSH sur storage-01) → notification email.

Rapport hebdomadaire étendu
Cron dimanche 09h → même pipeline que le rapport horaire mais avec fenêtre 7 jours ([7d]) + statistiques min/max de la semaine.

Moyen terme

Budget Anthropic API
Cron quotidien → requête API Anthropic usage → si > seuil configuré → email d'alerte.
Évite les surprises de facturation Claude.

Notification nouveaux commits Funk-lab
GitHub webhook → n8n → email/notification résumé du commit.
Utile pour tracker les changements sur d'autres postes.

Monitor llama-server performance
Cron horaire → query Prometheus llamacpp_tokens_per_second → si tokens/s < seuil (GPU dégradé) → alerte email.

Rotation/nettoyage logs
Cron quotidien → SSH storage-01 → journalctl --vacuum-time=30d → rapport taille libérée.

Long terme

Auto-scaling modèle Hermes
Monitor charge LiteLLM → si charge élevée, switcher automatiquement vers claude-sonnet-4-6 via hermes-switch claude → revenir à qwen après N minutes.

RAG re-indexation automatique
Webhook Git (push sur admin/) → déclencher rag-ingest via SSH sur storage-01 → email confirmation nombre de chunks indexés.

Résumé quotidien Hermes
Cron 08h00 → interroger Hermes sur l'état du lab → recevoir un briefing matinal par email avec état services, alertes de la nuit, métriques clés.


Opérations courantes

# Logs n8n
kubectl logs deploy/n8n -n ai -f

# Redémarrer n8n
kubectl rollout restart deploy/n8n -n ai

# Lister les workflows via API
curl -s http://n8n.lab.local/api/v1/workflows \
  -H "X-N8N-API-KEY: <clé>" | python3 -m json.tool

# Activer/désactiver un workflow
curl -s -X POST http://n8n.lab.local/api/v1/workflows/<id>/activate \
  -H "X-N8N-API-KEY: <clé>"
curl -s -X POST http://n8n.lab.local/api/v1/workflows/<id>/deactivate \
  -H "X-N8N-API-KEY: <clé>"

# Dernières exécutions
curl -s "http://n8n.lab.local/api/v1/executions?limit=5" \
  -H "X-N8N-API-KEY: <clé>" | python3 -c \
  "import sys,json; [print(e['id'], e['status'], e.get('stoppedAt','')) for e in json.load(sys.stdin)['data']]"

Dépannage

Symptôme Cause Action
Email vide Expression $json.xxx évaluée à vide dans emailSend Utiliser un nœud Code intermédiaire qui assemble le corps, puis emailType: "html" + html: "={{ $json.htmlBody }}"
SMTP ETIMEDOUT Port 25 non ouvert pour les pods Vérifier nftables : tcp dport 25 ip saddr { 192.168.10.0/24, 10.42.0.0/16 }
LLM timeout hermes-default trop lent (> 2 min) Passer en mode async : ajouter "Respond to Webhook" en branche parallèle avant le LLM
Prometheus query vide Service DNS interne non résolu Utiliser l'URL service k8s : http://kube-prometheus-stack-prometheus.monitoring.svc.cluster.local:9090
Workflow ne se déclenche pas Webhook AlertManager mal configuré Tester : curl -X POST http://n8n.lab.local/webhook/alerts -d '{...}'

Configuration Ansible / k8s

  • Secrets k8s : kubectl get secret n8n-secret -n ai
  • Base de données : PostgreSQL n8n sur storage-01 (vault_pg_n8n_password)
  • PVC data : NFS, 5 Gi, claimName n8n-data
  • nftables : port 25 ouvert 10.42.0.0/16 (pods) dans le rôle gateway
  • AlertManager : receiver hermes-monitor dans k8s/infra/monitoring/values.yaml