Ich habe mich gewundert, warum bei docker ps
bei einigen Containern ein (healthy) hinter der uptime steht, bei anderen aber nicht. Dem bin ich mal nachgegangen.

(healthy)
Mit dem Status (healthy) zeigt docker an, dass der Container vollständig einsatzbereit ist. Ohne diesen Zusatz ist nur sichergestellt, dass der Prozess des Containers läuft. Ob der z.B. darin integrierte Apache Server richtig läuft, ist völlig unklar. Diese Information kann der Dockerservice nur vom Container selbst über den sog. healthcheck erfragen. Manche Container stellen diesen zu Verfügung, wie bei mir ClamAV, Nextcloud tut dies aber nicht von sich aus.

healthcheck
Der Healthcheck besteht ganz simple aus einem Kommando, das den korrekten Zustand des Containers abfragt. In vielen Fällen ist das ein URL-Aufruf.
Healthcheck selber definieren
Da Nextcloud von sich aus keinen Healthcheck zur Verfügung stellt, rüsten wir ihn jetzt im docker-compose.yml einfach nach.
Dazu fügst du einfach den folgenden Block in die Datei ein.
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost/status.php"]
interval: "30s" # alle 30 Sekunden prüfen
timeout: "10s" # max. 10 Sekunden auf Antwort warten
retries: "3" # nach 3 Fehlversuchen gilt der Container als unhealthy
start_period: "1m" # Wartezeit nach dem Start, bevor geprüft wird
Ich habe den Block vor die volumes:
Sektion gesetzt.
Die Konfiguration erklärt sich fast von selbst. Unter test: steht das Kommando, das gegen den Container abgesetzt wird. In unserem Fall wird mit curl die status.php Seite vom Container abgerufen. Durch interval:
wird dies alle 30 Sekunden wiederholt. timeout:
gibt an, dass max. 10 Sekunden auf ein Ergebnis des Kommandos gewartet werden soll. Mit retries:
werden drei Wiederholungen erlaubt. Da der Container beim Start u.U. etwas Zeit benötigt, alles vollständig hochzufahren, verzögern wir mit start_period: den ersten healthcheck Aufruf um eine Minute nach Containerstart.
Das Ergebnis zeigt sich nach einem docker-compose up -d
und einer angemessenen Wartezeit.

health Status abfragen
Der (healthy) soll natürlich nicht nur der Optik auf der Übersichtsseite dienen, wir können ihn auch auswerten. Mit docker inspect nextcloud
erhalten wir detaillierte Informationen zum Zustand unseres Containers im JSON Format. Darin befindet sich auch ein Eintrag "Status": "healthy"
. Da wir den Gesamtzustand überhaupt nicht benötigen, filtern wir uns nur den Wert raus, den wir brauchen.
docker inspect --format='{{.State.Health.Status}}' nextcloud
Dies liefert uns nur den String „healthy“. Um den automatisch auszuwerten habe ich ein kleines bash Script geschrieben
#!/bin/bash
# containerhealth <container-name>
CONTAINER="${1}"
if [ -z "${CONTAINER}" ]; then
echo "Usage: ${0} <container-name>"
exit 2
fi
# Health-Status abfragen
STATUS=$(docker inspect --format='{{.State.Health.Status}}' "${CONTAINER}" 2>/dev/null)
# Prüfen, ob Container überhaupt existiert
if [ $? -ne 0 ]; then
echo "Container '${CONTAINER}' not found"
exit 2
fi
case "${STATUS}" in
healthy)
# exit code 0 wenn healthy
exit 0
;;
unhealthy|starting)
# exit code 1 bei unhealthy oder starting
exit 1
;;
"")
# Wenn leer -> kein Healthcheck definiert, exit code 3
exit 3
;;
*)
# Unerwarteter Status, exit code 2
exit 2
Das Script liefert nur dann einen exit Code 0, wenn der Status des angegebenen Containers "healthy"
ist.
Fazit
Stellt ein Container nicht von sich aus einen Healthcheck zur Verfügung, können wir ihn relativ einfach selber nachrüsten.
Das komplette docker-compose.yml kannst du dir hier runterladen.