Un serveur Linux en production sans monitoring, c'est comme conduire de nuit sans tableau de bord : vous ne savez pas à quelle vitesse vous allez, combien il reste d'essence, ni si le moteur est en train de surchauffer. Quand le problème devient visible, il est souvent trop tard. Le service est déjà tombé, les utilisateurs se plaignent, et vous êtes en mode pompier à 3h du matin.
Le monitoring n'est pas un luxe réservé aux grandes infrastructures. Même un VPS à 5 euros par mois mérite une surveillance minimale. La différence entre un incident maîtrisé et une catastrophe, c'est souvent une alerte envoyée 15 minutes avant que le disque ne soit plein ou que l'OOM killer ne fasse des ravages.
Dans cet article, on passe en revue les métriques fondamentales à surveiller sur un serveur Linux en production. Pour chaque catégorie, je vous donne les 5 commandes Linux essentielles utiles, les seuils d'alerte recommandés et les pièges à éviter. L'objectif est pragmatique : vous repartez avec une checklist actionnable.
CPU et charge système
La charge CPU est la première métrique que l'on regarde quand un serveur rame. Mais attention à ne pas confondre utilisation CPU et load average. L'utilisation CPU mesure le pourcentage de temps que le processeur passe à travailler. Le load average, lui, représente le nombre moyen de processus en attente d'exécution sur une période donnée (1, 5 et 15 minutes). Un load average de 4.0 sur une machine à 4 cœurs signifie que le système est à saturation. Au-delà, les processus font la queue.
La commande uptime donne un aperçu rapide, mais pour une analyse plus fine, mpstat (du paquet sysstat) décompose l'utilisation par cœur et par type (user, system, iowait, idle). Le %iowait est particulièrement révélateur : une valeur élevée indique que le CPU attend le disque, ce qui pointe vers un goulot d'étranglement I/O plutôt qu'un manque de puissance de calcul.
# Load average rapide
uptime
# 14:23:07 up 42 days, load average: 1.82, 2.15, 1.93
# Détail par coeur, rafraîchi toutes les 2 secondes
mpstat -P ALL 2
# Top 10 des processus les plus gourmands en CPU
ps aux --sort=-%cpu | head -11
# Suivi en temps réel avec tri par CPU
top -bn1 -o %CPU | head -20
Conseil pratique : Configurez une alerte quand le load average dépasse 0.7 fois le nombre de cœurs pendant plus de 5 minutes. Par exemple, sur un serveur 4 cœurs, alertez à partir d'un load average de 2.8 soutenu. Cela laisse une marge avant la saturation complète.
Mémoire et swap
La gestion de la mémoire sous Linux est souvent mal comprise. Voir 95% de RAM utilisée n'est pas forcément un problème : Linux utilise agressivement la mémoire disponible comme cache disque, ce qui accélère les lectures. Ce qui compte, c'est la mémoire disponible (colonne available dans free -h), pas la mémoire libre (free). La mémoire disponible inclut les caches que le noyau peut libérer instantanément si une application en a besoin.
Le swap, en revanche, est un signal d'alerte. Si le système swappe activement (vérifiable avec vmstat colonnes si et so), les performances se dégradent drastiquement car le disque est des milliers de fois plus lent que la RAM. Le paramètre vm.swappiness contrôle l'agressivité du swapping : une valeur de 10 convient pour la plupart des serveurs de production, contre 60 par défaut.
Le pire scénario, c'est l'OOM killer. Quand le noyau n'a plus de mémoire disponible, il tue le processus le plus gourmand. Et ce n'est pas toujours celui que vous auriez choisi. Surveillez les logs pour détecter ces événements avant qu'ils ne deviennent récurrents.
# Vue d'ensemble mémoire et swap
free -h
# total used free shared buff/cache available
# Mem: 15Gi 8.2Gi 512Mi 256Mi 6.8Gi 6.5Gi
# Swap: 2.0Gi 128Mi 1.9Gi
# Activité swap en temps réel (si/so = swap in/out par seconde)
vmstat 2 5
# Vérifier la swappiness actuelle
cat /proc/sys/vm/swappiness
# Réduire la swappiness (persistant via sysctl.conf)
echo "vm.swappiness=10" | sudo tee -a /etc/sysctl.d/99-tuning.conf
sudo sysctl -p /etc/sysctl.d/99-tuning.conf
# Détecter les événements OOM killer dans les logs
sudo dmesg | grep -i "oom|out of memory"
sudo journalctl -k | grep -i "oom"
Conseil pratique : Alertez quand la mémoire disponible descend sous 15% de la RAM totale pendant plus de 10 minutes. Et surveillez l'utilisation du swap : toute activité swap soutenue (si+so > 0 pendant plusieurs minutes) mérite investigation.
Espace disque et I/O
Le disque plein est probablement la cause numéro un des pannes évitables. Un fichier de log qui grossit sans rotation, une base de données qui remplit sa partition, un /tmp saturé par des fichiers temporaires oubliés : les scénarios sont classiques mais continuent de piéger des administrateurs expérimentés. La commande df -h montre l'occupation des partitions, tandis que du -sh permet de traquer les répertoires les plus volumineux.
Un piège moins connu : la saturation des inodes. Même avec de l'espace disque libre, si le nombre d'inodes est épuisé (des millions de petits fichiers par exemple), plus aucun fichier ne peut être créé. Vérifiez avec df -i. Côté performances I/O, iostat révèle le débit et la latence des disques. Une latence moyenne (await) supérieure à 20ms sur un SSD est suspecte.
Pour identifier quel processus consomme le plus d'I/O disque, iotop est indispensable. Il fonctionne comme top mais pour les opérations disque. Particulièrement utile quand le %iowait du CPU est élevé et que vous cherchez le coupable.
# Espace disque par partition
df -h
# Inodes disponibles (souvent oublié !)
df -i
# Trouver les 10 plus gros répertoires dans /var
sudo du -sh /var/*/ 2>/dev/null | sort -rh | head -10
# Statistiques I/O disque (intervalle 2s, 5 relevés)
iostat -xz 2 5
# Identifier les processus les plus gourmands en I/O
sudo iotop -oP -d 2
# Trouver les fichiers modifiés dans les dernières 24h (utile pour traquer les logs)
find /var/log -type f -mtime -1 -exec ls -lh {} ; | sort -k5 -rh | head -10
Conseil pratique : Mettez en place deux seuils d'alerte pour le disque : un avertissement à 80% d'occupation et une alerte critique à 90%. N'oubliez pas de surveiller aussi les inodes avec
df -i, surtout sur les serveurs de mail ou les systèmes avec beaucoup de fichiers de session.
Réseau
Le monitoring réseau couvre plusieurs aspects : la bande passante consommée, le nombre de connexions actives, les erreurs d'interface et les connexions dans des états suspects. La commande ss (remplaçante moderne de netstat) est votre couteau suisse. Elle affiche les sockets TCP/UDP avec leurs états, les files d'attente et les processus associés.
Les connexions en état TIME_WAIT méritent une attention particulière. Un nombre élevé (plusieurs milliers) indique souvent un problème de configuration : connexions HTTP non réutilisées, absence de keep-alive, ou simplement un trafic très élevé. Pour la bande passante en temps réel, iftop montre le trafic par connexion, tandis que nethogs l'agrège par processus, ce qui est plus pratique pour identifier quel service consomme la bande passante.
Surveillez aussi les erreurs et les paquets perdus sur les interfaces réseau. Un taux d'erreur non nul peut indiquer un problème matériel (câble défectueux, carte réseau en fin de vie) ou une saturation du buffer réseau.
# Nombre de connexions TCP par état
ss -s
# Connexions établies, triées par nombre par IP distante
ss -tn state established | awk '{print $5}' | cut -d: -f1 | sort | uniq -c | sort -rn | head -10
# Compter les connexions TIME_WAIT
ss -tn state time-wait | wc -l
# Bande passante par processus
sudo nethogs eth0
# Statistiques d'interface (erreurs, drops, overruns)
ip -s link show eth0
# Débit réseau en temps réel
sar -n DEV 2 5
Conseil pratique : Alertez si le nombre de connexions
TIME_WAITdépasse 10 000 ou si le taux de paquets perdus (dropped) est supérieur à 0.1%. Ces symptômes indiquent souvent un problème de dimensionnement ou de configuration réseau qui va s'aggraver.
Processus et services
Savoir quels services tournent et dans quel état est fondamental. Avec systemd, la commande systemctl liste les unités actives, en échec ou masquées. Un service en état failed qui passe inaperçu pendant des jours est un classique. Automatisez la vérification : un simple script qui exécute systemctl --failed et envoie une alerte si le résultat n'est pas vide suffit à éviter bien des surprises.
Les processus zombies sont un autre indicateur à surveiller. Un zombie est un processus terminé dont le parent n'a pas lu le code de retour. Quelques zombies sont inoffensifs, mais un nombre croissant indique un bug dans le processus parent. Enfin, journalctl est indispensable pour analyser les logs de services. Utilisez les filtres par unité et par période pour ne pas vous noyer dans la masse.
# Services en échec
systemctl --failed
# État d'un service spécifique avec les dernières lignes de log
systemctl status nginx.service
# Logs d'un service depuis la dernière heure
journalctl -u nginx.service --since "1 hour ago" --no-pager
# Compter les processus zombies
ps aux | awk '$8 == "Z" {count++} END {print "Zombies:", count+0}'
# Identifier les processus zombies et leur parent
ps -eo pid,ppid,stat,cmd | awk '$3 ~ /Z/'
# Vérification automatique des services critiques
for svc in nginx postgresql redis; do
systemctl is-active --quiet $svc || echo "ALERTE: $svc est down !"
done
Conseil pratique : Créez un script de healthcheck qui vérifie vos services critiques toutes les minutes via cron. Un simple
systemctl is-active --quietsuivi d'une notification (mail, webhook Slack) couvre 80% des besoins de surveillance basique des services.
Uptime et disponibilité
Le monitoring interne est nécessaire mais insuffisant. Si votre serveur est injoignable depuis Internet, vos scripts locaux ne pourront pas vous prévenir. C'est pourquoi le monitoring externe est indispensable : un service tiers vérifie régulièrement que vos endpoints répondent correctement. Des outils comme UptimeRobot (gratuit pour 50 monitors), Hetrixtools ou encore le projet open source Uptime Kuma permettent de surveiller la disponibilité HTTP, les certificats SSL et les temps de réponse.
Le concept de healthcheck endpoint est une bonne pratique. Plutôt que de simplement vérifier qu'un port répond, exposez une route /health qui teste les dépendances critiques (base de données, cache, file system). Si la base est injoignable, le healthcheck retourne un code 503 et votre monitoring externe le détecte immédiatement.
Mesurez aussi l'uptime réel de vos services avec des métriques précises. Le fichier /proc/uptime donne le temps écoulé depuis le dernier redémarrage du système, mais ce qui intéresse vos utilisateurs c'est la disponibilité applicative, pas celle du noyau.
# Uptime du système
uptime
cat /proc/uptime # premier chiffre = secondes depuis le boot
# Historique des redémarrages
last reboot | head -5
# Test de healthcheck HTTP local
curl -sf -o /dev/null -w "%{http_code} - %{time_total}s
" http://localhost:8080/health
# Script de monitoring externe simple (à exécuter depuis un autre serveur)
#!/bin/bash
URL="https://monsite.fr/health"
RESPONSE=$(curl -sf -o /dev/null -w "%{http_code}" --max-time 10 "$URL")
if [ "$RESPONSE" != "200" ]; then
echo "ALERTE: $URL retourne $RESPONSE" | mail -s "Down: monsite.fr" admin@monsite.fr
fi
# Vérifier l'expiration du certificat SSL
echo | openssl s_client -connect monsite.fr:443 -servername monsite.fr 2>/dev/null |
openssl x509 -noout -dates
Conseil pratique : Surveillez vos certificats SSL au moins 30 jours avant expiration. Un certificat expiré cause une panne visible immédiatement par tous vos utilisateurs. Automatisez le renouvellement avec Certbot et ajoutez une alerte de secours au cas où l'automatisation échoue.
Mettre en place des alertes efficaces
Collecter des métriques sans configurer d'alertes, c'est comme installer des détecteurs de fumée sans les brancher. Mais l'excès inverse est tout aussi problématique : trop d'alertes mène à l'alert fatigue, où les notifications sont systématiquement ignorées. La clé est de définir des seuils pertinents et un système d'escalade progressif.
Adoptez une classification à trois niveaux. Les alertes info sont logguées mais ne déclenchent pas de notification (ex: utilisation CPU à 60%). Les alertes warning envoient une notification non urgente, typiquement par email ou canal Slack (ex: disque à 80%). Les alertes critical déclenchent une notification intrusive : SMS, appel PagerDuty, push mobile (ex: service down, disque à 95%). Cette gradation évite de crier au loup et garantit que les alertes critiques reçoivent l'attention qu'elles méritent.
Le templating des alertes est aussi important que les seuils. Une alerte doit contenir : le serveur concerné, la métrique en alerte, la valeur actuelle, le seuil dépassé et idéalement un lien vers le dashboard. Un message "CRITICAL: disk /var 94% on srv-prod-01" est actionnable. Un message "Alert triggered" ne l'est pas.
# Exemple de script d'alerte simple et complet
#!/bin/bash
# monitoring-alerts.sh - à lancer via cron toutes les 5 minutes
HOSTNAME=$(hostname)
ALERT_EMAIL="admin@monsite.fr"
SLACK_WEBHOOK="https://hooks.slack.com/services/XXX/YYY/ZZZ"
# Seuils
DISK_WARN=80
DISK_CRIT=95
MEM_WARN=85
LOAD_WARN=$(nproc | awk '{printf "%.1f", $1 * 0.7}')
# Vérification disque
df -h --output=pcent,target | tail -n+2 | while read usage mount; do
pct=${usage%%%}
if [ "$pct" -ge "$DISK_CRIT" ]; then
echo "CRITICAL: Disque $mount à ${pct}% sur $HOSTNAME" |
mail -s "[CRIT] Disque $mount - $HOSTNAME" "$ALERT_EMAIL"
elif [ "$pct" -ge "$DISK_WARN" ]; then
echo "WARNING: Disque $mount à ${pct}% sur $HOSTNAME"
fi
done
# Vérification mémoire disponible
MEM_AVAIL_PCT=$(free | awk '/Mem:/ {printf "%.0f", $7/$2*100}')
if [ "$MEM_AVAIL_PCT" -le 15 ]; then
echo "WARNING: Mémoire disponible à ${MEM_AVAIL_PCT}% sur $HOSTNAME"
fi
# Vérification services critiques
for svc in nginx postgresql redis-server; do
if ! systemctl is-active --quiet "$svc" 2>/dev/null; then
echo "CRITICAL: $svc est down sur $HOSTNAME" |
mail -s "[CRIT] Service $svc down - $HOSTNAME" "$ALERT_EMAIL"
fi
done
Conseil pratique : Appliquez la règle des "deux yeux" pour les alertes critiques : chaque alerte doit être acquittée explicitement. Si personne n'acquitte en 15 minutes, l'alerte est escaladée au niveau supérieur. Cela garantit qu'aucune alerte critique ne tombe dans l'oubli, même la nuit ou le week-end.
Conclusion : construire un monitoring durable
Surveiller un serveur Linux en production repose sur six piliers : CPU et charge, mémoire et swap, disque et I/O, réseau, processus et services, et disponibilité externe. Chaque catégorie a ses métriques clés, ses commandes de diagnostic et ses seuils d'alerte recommandés. Le plus important est de commencer simple : un script bash avec des vérifications basiques et des notifications par email couvre déjà l'essentiel.
Pour aller plus loin et construire un monitoring professionnel, la stack Prometheus + Grafana est aujourd'hui la référence. Prometheus collecte et stocke les métriques via node_exporter installé sur chaque serveur, tandis que Grafana fournit des dashboards visuels et un système d'alerting flexible. L'installation et la configuration de cette stack feront l'objet d'un prochain article.
En attendant, commencez dès aujourd'hui : déployez le script d'alerte de cet article sur vos serveurs, configurez la rotation des logs, vérifiez vos inodes et testez vos healthchecks. Chaque métrique surveillée est un incident évité.
Commentaires