Ce que cela construit
Une petite instance qui récupère toutes les autres machines que vous possédez, via un tunnel privé, et vous envoie un courriel lorsque quelque chose est sur le point de casser. Métriques de nœud, sondes blackbox entre sites, règles d'alerte avec des seuils sensés, et une configuration Alertmanager qui regroupe les notifications au lieu de vous en envoyer quatre cents à trois heures du matin.
Il n'y a pas de tableau de bord dans cette construction. Les tableaux de bord sont agréables et ne sont pas de la surveillance ; un graphique que personne ne regarde n'a jamais réveillé personne. Ajoutez-en un plus tard si vous le voulez, par-dessus les mêmes données.
Avant de commencer
- Un R-4 pour le moniteur. Cent nœuds à intervalles de quinze secondes représentent quelques centaines de milliers d'échantillons par minute, ce qu'il gère sans s'en apercevoir.
- Placez-le ailleurs que votre parc. Tout moniteur partageant un bâtiment avec tout ce qu'il surveille reste admirablement silencieux précisément le jour où vous avez besoin qu'il crie. Si votre parc est européen, Toronto ou Singapour est l'endroit sensé pour cela.
- Un tunnel vers chaque nœud surveillé, depuis le guide WireGuard. Les exportateurs exposent beaucoup de choses sur une machine et ne devraient se trouver nulle part près d'une interface publique.
1. Sur chaque nœud surveillé
apt update && apt install -y prometheus-node-exporter
mkdir -p /etc/systemd/system/prometheus-node-exporter.service.d
cat > /etc/systemd/system/prometheus-node-exporter.service.d/bind.conf <<EOF
[Service]
Environment=ARGS=--web.listen-address=10.7.0.11:9100 --collector.systemd --collector.processes
EOF
systemctl daemon-reload && systemctl restart prometheus-node-exporter
ss -ltn | grep 9100Remplacez par l'adresse du tunnel de chaque nœud. Se lier au tunnel plutôt qu'à tout signifie que le pare-feu est une deuxième ligne de défense plutôt que la seule.
2. Sur le moniteur
apt install -y prometheus prometheus-alertmanager prometheus-blackbox-exporterÉcrivez /etc/prometheus/prometheus.yml :
global:
scrape_interval: 15s
evaluation_interval: 15s
external_labels:
fleet: main
alerting:
alertmanagers:
- static_configs:
- targets: ['127.0.0.1:9093']
rule_files:
- /etc/prometheus/rules/*.yml
scrape_configs:
- job_name: nodes
file_sd_configs:
- files: ['/etc/prometheus/targets/*.yml']
- job_name: probe_https
metrics_path: /probe
params:
module: [http_2xx]
static_configs:
- targets:
- https://app.example.com/health
- https://cloud.example.com/status.php
relabel_configs:
- source_labels: [__address__]
target_label: __param_target
- source_labels: [__param_target]
target_label: instance
- target_label: __address__
replacement: 127.0.0.1:9115La découverte basée sur des fichiers plutôt qu'une liste statique vaut le répertoire supplémentaire. Ajouter un nœud devient un fichier, et le fichier peut être écrit par ce qui provisionne vos machines. /etc/prometheus/targets/ams.yml :
- targets: ['10.7.0.11:9100']
labels: { site: AMS-01, role: web }
- targets: ['10.7.0.12:9100']
labels: { site: AMS-01, role: db }Ces étiquettes sont ce qui rend les alertes lisibles plus tard. Une alerte disant db in AMS-01 est exploitable ; une disant 10.7.0.12 vous envoie vers un tableur.
3. Des règles qui valent le coup
/etc/prometheus/rules/fleet.yml :
groups:
- name: fleet
rules:
- alert: NodeDown
expr: up{job="nodes"} == 0
for: 3m
labels: { severity: page }
annotations:
summary: "{{ $labels.instance }} in {{ $labels.site }} stopped answering"
- alert: DiskFillingUp
expr: predict_linear(node_filesystem_avail_bytes{fstype=~"ext4|xfs|zfs|btrfs"}[6h], 4*3600) < 0
for: 30m
labels: { severity: page }
annotations:
summary: "{{ $labels.instance }} fills {{ $labels.mountpoint }} within four hours"
- alert: MemoryPressure
expr: node_memory_MemAvailable_bytes / node_memory_MemTotal_bytes < 0.10
for: 15m
labels: { severity: warn }
- alert: IOWaitHigh
expr: avg by (instance) (rate(node_cpu_seconds_total{mode="iowait"}[5m])) > 0.25
for: 20m
labels: { severity: warn }
- alert: CertificateExpiring
expr: probe_ssl_earliest_cert_expiry - time() < 10*86400
labels: { severity: warn }
- alert: ProbeFailing
expr: probe_success == 0
for: 5m
labels: { severity: page }predict_linear est la règle qui justifie cette construction. Un seuil sur l'espace libre vous dit qu'un disque est plein ; une tendance de six heures extrapolée vers l'avant vous dit qu'il sera plein vers quatre heures cet après-midi, ce qui est un problème que vous pouvez encore résoudre calmement. Les alertes disque basées sur un pourcentage fixe sont soit bruyantes sur les petits volumes, soit inutiles sur les grands.
4. Alertmanager
route:
receiver: mail
group_by: [alertname, site]
group_wait: 45s
group_interval: 5m
repeat_interval: 12h
routes:
- matchers: [severity="warn"]
repeat_interval: 72h
inhibit_rules:
- source_matchers: [alertname="NodeDown"]
target_matchers: [severity="warn"]
equal: [instance]
receivers:
- name: mail
email_configs:
- to: [email protected]
from: [email protected]
smarthost: mail.example.com:587
auth_username: [email protected]
auth_password: "<the mailbox password>"La règle d'inhibition est la différence entre un message et quarante. Quand un nœud tombe, chaque avertissement concernant ce nœud est supprimé, parce que vous le savez déjà : le nœud est down.
Le regroupement par alertname et site signifie qu'un site entier perdant de l'électricité produit un seul courriel listant chaque machine, plutôt qu'un courriel par machine. Ce serveur de courrier est celui du guide courriel, et avoir votre chemin d'alerte qui dépend d'une infrastructure que vous surveillez aussi est un compromis connu ; un second récepteur pointant vers un webhook ailleurs est une assurance bon marché.
systemctl enable --now prometheus prometheus-alertmanager prometheus-blackbox-exporterLa rétention vaut la peine d'être définie délibérément. Quatre-vingt-dix jours de cent nœuds représentent quelques dizaines de gigaoctets :
echo 'ARGS="--storage.tsdb.retention.time=90d --storage.tsdb.retention.size=40GB"' > /etc/default/prometheus
systemctl restart prometheusVérifiez-le
La syntaxe d'abord, parce qu'un fichier de règles avec une faute de frappe échoue silencieusement au chargement et vous le découvrez pendant l'incident :
promtool check config /etc/prometheus/prometheus.yml
promtool check rules /etc/prometheus/rules/fleet.ymlEnsuite, confirmez que chaque cible est scrapée :
curl -s http://127.0.0.1:9090/api/v1/targets | grep -o "\"health\":\"[a-z]*\"" | sort | uniq -cChaque cible devrait rapporter up. Une rapportant down est soit une règle de pare-feu, soit un exportateur lié à la mauvaise adresse.
Maintenant le seul test qui prouve que toute la chaîne fonctionne, c'est de casser quelque chose exprès. Sur n'importe quel nœud surveillé :
systemctl stop prometheus-node-exporterTrois minutes plus tard, l'alerte devrait être en attente, puis se déclencher. Regardez-la évoluer :
curl -s http://127.0.0.1:9090/api/v1/alerts | head -c 400
amtool --alertmanager.url=http://127.0.0.1:9093 alert queryEnviron une minute après le déclenchement, le courriel arrive. Si l'alerte se déclenche mais qu'aucun courriel n'apparaît, le problème est les identifiants smarthost, et journalctl -u prometheus-alertmanager le dira clairement. Redémarrez l'exportateur et confirmez que vous recevez aussi la notification de résolution, puisqu'un système d'alerte qui ne vous dit jamais que les choses s'améliorent vous entraîne à l'ignorer.
systemctl start prometheus-node-exporterEnsuite
Ajoutez des sondes blackbox entre les sites, de chaque site vers chaque autre site, et vous obtenez une matrice de latence de votre propre parc qui est bien plus utile pendant un incident que n'importe quelle page de statut. La nôtre est à statut, et le looking glass répond à l'autre moitié de la question quand une route semble fausse.