Document

SUBSCRIBE TO GET FULL ACCESS TO THE E-BOOKS FOR FREE 🎁SUBSCRIBE NOW

Professional Dropdown with Icon

SUBSCRIBE NOW TO GET FREE ACCESS TO EBOOKS

Scripts ops : healthcheck, rotate, notify

À la fin de ce tutoriel script bash devops, vous saurez assembler un petit outil ops : healthcheck HTTP/TCP avec retries et timeouts, rotation simple de fichiers de log, et notify webhook (curl JSON) uniquement en cas d’échec — le tout avec set -euo pipefail, logging structuré et trap. Ce n’est pas un redo de bash scripting (shebang / if / for) ni une copie des systemd timers : on fabrique la charge utile que le timer pourra ensuite planifier.

Niveau : Intermédiaire · Temps estimé : 45–55 min · Versions testées : Ubuntu 22.04 / 24.04, Debian 12 ; notes Rocky/Alma 9 · Dernière vérification : 2026-09-11

Slug proposé : linux-scripts-ops · Série : Linux Shell & Automation · Remplace / fusionne : N/A — création (lot 2)

Prérequis

  • Hub Linux Shell & Automation ; bash avancé (set -euo, fonctions, trap)
  • Bases P5 : bash scripting (déjà vu le mini healthcheck — ici on le professionnalise)
  • Utile : systemd timers pour brancher le script en ExecStart ensuite
  • VM / WSL jetable ; travail sous /tmp/lab-scripts-ops ; aucun secret versionné (webhook via variable d’environnement)

Coût : 0 €. Lab entièrement jetable.

Ce que nous allons construire (script bash devops)

Squelette ops (set -euo + trap + log)
  → Healthcheck HTTP/TCP (retries, timeout, exit codes)
  → Rotate logs (taille / rétention)
  → Notify webhook JSON (échec seulement)
  → ops-watch.sh : healthcheck → log → rotate → notify
  → Pont timer systemd (mention)
  → Nettoyage

(Schéma à remplacer par une image locale Excalidraw / draw.io, alt : « Scripts ops DevOps : healthcheck bash, rotate logs, notify webhook ».)

Chapitre lot 2 de la colonne Shell. Après pipelines texte, on livre des patrons réutilisables : un junior DevOps les copie dans un lab, les versionne, puis les déclenche via timer ou CI — sans Ansible encore.

Étape 1 — Squelette ops : set -euo, trap, logging

Un script ops se distingue d’un one-liner par trois réflexes : arrêt net sur erreur, cleanup garanti, logs horodatés exploitables.

mkdir -p /tmp/lab-scripts-ops
cat > /tmp/lab-scripts-ops/lib-ops.sh << 'EOF'
#!/usr/bin/env bash
set -euo pipefail

LAB_DIR="${LAB_DIR:-/tmp/lab-scripts-ops}"
LOG_FILE="${LOG_FILE:-$LAB_DIR/ops.log}"
mkdir -p "$LAB_DIR"

log() {
  local level=$1; shift
  printf '%s [%s] %sn' "$(date -Iseconds)" "$level" "$*" | tee -a "$LOG_FILE" >&2
}

cleanup() {
  local ec=$?
  [[ $ec -eq 0 ]] || log ERROR "exit=$ec"
  return "$ec"
}
trap cleanup EXIT

log INFO "squelette ops prêt — LOG_FILE=$LOG_FILE"
EOF
bash /tmp/lab-scripts-ops/lib-ops.sh
tail -n 3 /tmp/lab-scripts-ops/ops.log
Élément Rôle ops
set -euo pipefail Échec explicite ; pas de variable fantôme ; pipes fiables
trap … EXIT Toujours logger / nettoyer, même sur erreur
tee -a Console et fichier pour debug immédiat

Pas de mots de passe dans le script : coffre, secrets manager, ou export WEBHOOK_URL=… en session lab uniquement.

Étape 2 — Healthcheck HTTP / TCP robuste

Le mini ping/curl de Basics valide l’idée. En ops : timeouts, retries, et un exit code clair pour le timer / la CI.

cat > /tmp/lab-scripts-ops/healthcheck.sh << 'EOF'
#!/usr/bin/env bash
set -euo pipefail
# shellcheck source=/dev/null
source /tmp/lab-scripts-ops/lib-ops.sh

URL="${1:-https://example.com/}"
RETRIES="${RETRIES:-3}"
TIMEOUT="${TIMEOUT:-5}"
SLEEP_BETWEEN="${SLEEP_BETWEEN:-1}"

check_http() {
  local url=$1 attempt=1 code
  while (( attempt <= RETRIES )); do
    code=$(curl -sS -o /dev/null -w '%{http_code}' 
      --connect-timeout "$TIMEOUT" --max-time "$TIMEOUT" 
      -L "$url" || echo "000")
    if [[ "$code" =~ ^2 ]]; then
      log INFO "health OK url=$url code=$code attempt=$attempt"
      return 0
    fi
    log WARN "health fail url=$url code=$code attempt=$attempt/$RETRIES"
    (( attempt++ ))
    sleep "$SLEEP_BETWEEN"
  done
  log ERROR "health DOWN url=$url after $RETRIES tries"
  return 1
}

check_http "$URL"
EOF
chmod +x /tmp/lab-scripts-ops/healthcheck.sh
/tmp/lab-scripts-ops/healthcheck.sh https://example.com/
# Échec volontaire (lab) :
RETRIES=2 SLEEP_BETWEEN=0 /tmp/lab-scripts-ops/healthcheck.sh https://httpbin.org/status/500 || true

Variante TCP rapide (port ouvert, sans HTTP) :

# nc -z -w 3 host 443 && echo OK || echo DOWN
timeout 3 bash -c 'echo >/dev/tcp/example.com/443' && echo "tcp 443 OK"
Pratique Pourquoi
curl -w '%{http_code}' Mesure exploitable (2xx = OK)
Retries bornés Absorbe un glitch réseau sans masquer une panne
|| echo 000 Évite un crash opaque si curl ne répond pas
Exit 1 Timer / CI / notify peuvent réagir

Étape 3 — Rotation simple de logs

logrotate système est parfait en prod. En lab / petit agent : une rotate maison par taille évite un fichier qui grossit sans fin.

cat > /tmp/lab-scripts-ops/rotate.sh << 'EOF'
#!/usr/bin/env bash
set -euo pipefail
source /tmp/lab-scripts-ops/lib-ops.sh

TARGET="${1:-$LOG_FILE}"
MAX_BYTES="${MAX_BYTES:-4096}"
KEEP="${KEEP:-3}"

rotate_if_needed() {
  local f=$1 size
  [[ -f "$f" ]] || { log INFO "rien à rotator ($f)"; return 0; }
  size=$(wc -c < "$f")
  if (( size < MAX_BYTES )); then
    log INFO "rotate skip size=$size < $MAX_BYTES"
    return 0
  fi
  local i
  for (( i=KEEP; i>=1; i-- )); do
    [[ -f "${f}.${i}" ]] && mv -f "${f}.${i}" "${f}.$((i+1))"
  done
  mv -f "$f" "${f}.1"
  : > "$f"
  rm -f "${f}.$((KEEP+1))"
  log INFO "rotated $f -> ${f}.1 (keep=$KEEP)"
}

rotate_if_needed "$TARGET"
EOF
chmod +x /tmp/lab-scripts-ops/rotate.sh
# Forcer une rotate : gonfler le log puis lancer
yes "pad $(date -Iseconds)" 2>/dev/null | head -n 200 >> /tmp/lab-scripts-ops/ops.log || true
MAX_BYTES=2048 /tmp/lab-scripts-ops/rotate.sh /tmp/lab-scripts-ops/ops.log
ls -la /tmp/lab-scripts-ops/ops.log*

Idempotent : relancer sans dépasser MAX_BYTES ne fait rien. En prod, préférez logrotate.d + copytruncate si le process garde le FD ouvert — ici on reste volontairement simple.

Étape 4 — Notify webhook (échec seulement)

Alerter à chaque succès = bruit. Pattern ops : notify sur échec, payload JSON minimal, URL hors du dépôt.

cat > /tmp/lab-scripts-ops/notify.sh << 'EOF'
#!/usr/bin/env bash
set -euo pipefail
source /tmp/lab-scripts-ops/lib-ops.sh

# Lab : httpbin. Prod : export WEBHOOK_URL='https://hooks.example/...'
WEBHOOK_URL="${WEBHOOK_URL:-https://httpbin.org/post}"
HOST="$(hostname -s 2>/dev/null || echo lab)"
MSG="${1:-ops alert}"
STATUS="${2:-fail}"

notify() {
  local payload
  payload=$(printf '{"host":"%s","status":"%s","message":"%s","ts":"%s"}' 
    "$HOST" "$STATUS" "$MSG" "$(date -Iseconds)")
  log INFO "notify POST $WEBHOOK_URL"
  curl -sS -o /tmp/lab-scripts-ops/notify-out.json -w '%{http_code}' 
    -X POST -H 'Content-Type: application/json' 
    --connect-timeout 5 --max-time 10 
    -d "$payload" "$WEBHOOK_URL" | tee /tmp/lab-scripts-ops/notify-code.txt
  echo
  log INFO "notify done code=$(cat /tmp/lab-scripts-ops/notify-code.txt)"
}

notify
EOF
chmod +x /tmp/lab-scripts-ops/notify.sh
/tmp/lab-scripts-ops/notify.sh "lab smoke" "ok"
head -c 200 /tmp/lab-scripts-ops/notify-out.json; echo

Jamais de token dans Git : WEBHOOK_URL (ou fichier chmod 600 hors repo). Pour Slack/Discord/Teams, adaptez le JSON au schéma attendu — le mécanisme reste curl + échec conditionnel.

Étape 5 — Assembler ops-watch.sh

On enchaîne healthcheck → append log → rotate → notify si health ≠ 0.

cat > /tmp/lab-scripts-ops/ops-watch.sh << 'EOF'
#!/usr/bin/env bash
set -euo pipefail
LAB_DIR=/tmp/lab-scripts-ops
LOG_FILE=$LAB_DIR/ops.log
export LAB_DIR LOG_FILE
source "$LAB_DIR/lib-ops.sh"

URL="${1:-https://example.com/}"
ec=0
if ! RETRIES="${RETRIES:-2}" "$LAB_DIR/healthcheck.sh" "$URL"; then
  ec=1
fi
MAX_BYTES="${MAX_BYTES:-8192}" "$LAB_DIR/rotate.sh" "$LOG_FILE" || true
if (( ec != 0 )); then
  "$LAB_DIR/notify.sh" "healthcheck failed for $URL" "fail" || true
  exit 1
fi
log INFO "ops-watch OK url=$URL"
EOF
chmod +x /tmp/lab-scripts-ops/ops-watch.sh
/tmp/lab-scripts-ops/ops-watch.sh https://example.com/
# Scénario alerte (attendu exit 1) :
/tmp/lab-scripts-ops/ops-watch.sh https://httpbin.org/status/503 || echo "alerte déclenchée (attendu)"

Pont timer : dans systemd timers, pointez ExecStart=/tmp/lab-scripts-ops/ops-watch.sh https://example.com/ (chemins absolus, user timer d’abord). Ne recopiez pas les units ici — le timer déclenche, ce script décide.

Étape 6 — Vérification et nettoyage

bash -n /tmp/lab-scripts-ops/*.sh
command -v shellcheck >/dev/null && shellcheck /tmp/lab-scripts-ops/*.sh || 
  echo "shellcheck optionnel : sudo apt install shellcheck"
ls -la /tmp/lab-scripts-ops/
# Nettoyage lab
rm -rf /tmp/lab-scripts-ops
echo "lab scripts-ops nettoyé — OK"

Validé si : healthcheck renvoie 0 sur 2xx et 1 après retries sur 5xx, rotate crée ops.log.1 au-delà de MAX_BYTES, notify écrit un JSON vers httpbin, ops-watch.sh n’appelle notify qu’en échec, aucun secret dans les fichiers.

Erreurs fréquentes

Symptôme Cause Correction
unbound variable set -u + env manquante ${VAR:-défaut}
curl « OK » alors que 404 On testait seulement l’exit curl Lire %{http_code} (2xx)
Notify à chaque run Pas de garde ec != 0 Notify uniquement sur échec
Log qui explose le disque Pas de rotate MAX_BYTES + KEEP
Timer vert, script rouge silencieux Pas de journal / log fichier tee -a + journalctl -u si timer
Secret dans Git URL webhook commitée WEBHOOK_URL en env / coffre
source: not found Script lancé avec sh Shebang bash + bash script.sh

Quiz (3 questions)

1. Pourquoi mesurer %{http_code} plutôt que se fier au seul exit code de curl ?
– A. Parce que curl n’a jamais d’exit code
– B. Pour distinguer une réponse HTTP (ex. 500) d’un succès transport
– C. Pour désactiver TLS

2. Quand envoyer le webhook dans un script ops typique ?
– A. À chaque succès pour « confirmer »
– B. Sur échec (ou changement d’état), pour limiter le bruit
– C. Uniquement au boot du noyau

3. Rôle principal de la rotate par taille dans ce lab ?
– A. Remplacer systemd
– B. Borner la croissance du fichier de log
– C. Chiffrer les secrets

Réponses : 1‑B · 2‑B · 3‑B

FAQ

Faut-il réécrire le healthcheck de bash scripting ?
Non : le lab P5 introduit curl/ping → log. Ici on ajoute retries, codes HTTP, rotate, notify et un assembleur ops-watch.sh prêt pour un timer.

Webhook Slack / Discord / Teams ?
Même idée (curl -X POST -H Content-Type: application/json). Adaptez le corps JSON au format du canal ; gardez l’URL hors dépôt.

Pourquoi pas Ansible / un exporter Prometheus ?
Hors scope de cette leçon. Le shell reste le colle ops du quotidien ; Ansible et le monitoring métriques viennent ensuite. Ce chapitre livre des briques versionnables.

Pour aller plus loin

Maillage série Linux Shell & Automation

← Précédent Pipelines texte
→ Suivant jq / yq
Prérequis Bash avancé · Bash scripting · systemd timers
Hub Linux Shell & Automation

Meta publication (à remplir dans Rank Math / SEO)

  • Title SEO : Scripts ops bash : healthcheck, rotate, notify (2026)
  • Meta description (≤ 155) : Scripts bash ops : healthcheck HTTP, rotation de logs et notify webhook. Suite Shell Automation DevOps 2026.
  • Focus keyphrase : script bash devops
  • KW secondaires : healthcheck bash, notify webhook, rotation logs bash, set -euo pipefail, trap bash
  • Schemas Rank Math : Article + HowTo (étapes lab) + FAQ (3 questions ci-dessus)
  • Image mise en avant : assets/web/devopelastichayway/cover-linux-scripts-ops-1200x630.webp (Visuels Linux — WebP 1200×630)
  • Catégorie : Linux · Niveau : Intermédiaire
  • Slug : linux-scripts-ops
  • Statut : HOLD — draft only (ne pas publier)

← Retour parcours Linux — Basics, Admin, Réseau & Sécurité, Shell & Automation.