diff --git a/rmm-tasks/ESPO-12-Rueckweg.sh b/rmm-tasks/ESPO-12-Rueckweg.sh new file mode 100755 index 0000000..40d2be6 --- /dev/null +++ b/rmm-tasks/ESPO-12-Rueckweg.sh @@ -0,0 +1,89 @@ +#!/bin/bash +# ESPO-12-Rueckweg - setzt die Instanz auf den Stand vor dem Update zurueck. +# Aufruf: ohne Argumente. Verwendet den Snapshot, den ESPO-10 angelegt hat. +# +# Der Snapshot wird dabei VERBRAUCHT: Nach dem Zusammenfuehren existiert er nicht mehr, ein zweiter +# Rueckweg ist dann nicht moeglich. Zurueckgenommen wird ganz /srv - also auch die gerenderte Compose +# mit dem alten Image-Tag. Deshalb startet die Instanz danach von selbst wieder auf dem alten Stand. +set -u + +echo "ESPO-12-Rueckweg, Skriptstand 2026-09-24" + +VG=ubuntu-vg +SNAPSHOT=srv-vor-update +COMPOSE=/srv/espo/docker-compose.yml +WARTE_MAX=900 + +fehler() { echo "FEHLER: $*"; echo "ESPO12_ERGEBNIS: FEHLER"; exit 1; } + +# Bringt den Dienst wieder hoch, wenn der Rueckweg abgebrochen wird - eine stehende Instanz +# ist das schlechteste aller Ergebnisse. +dienst_zurueck() { + mountpoint -q /srv || mount /srv 2>/dev/null || true + [ -f "$COMPOSE" ] && docker compose -f "$COMPOSE" up -d --quiet-pull >/dev/null 2>&1 || true +} + +# 1. Vorbedingungen. +[ "$(id -u)" -eq 0 ] || fehler "nicht als root gestartet" +command -v lvconvert >/dev/null || fehler "LVM-Werkzeuge fehlen" +command -v docker >/dev/null && docker info >/dev/null 2>&1 || fehler "Docker laeuft nicht" + +# 2. Der Snapshot muss da und gueltig sein. Ein 'I' im Attributfeld heisst vollgelaufen und verworfen - +# dann traegt der Rueckweg nicht mehr, und ein Versuch waere schlimmer als ein ehrlicher Abbruch. +lvs --noheadings -o lv_name "$VG" 2>/dev/null | grep -qw "$SNAPSHOT" \ + || fehler "kein Snapshot '$SNAPSHOT' vorhanden - es gibt nichts zurueckzunehmen" +ATTR="$(lvs --noheadings -o lv_attr "$VG/$SNAPSHOT" 2>/dev/null | tr -d ' ')" +case "$ATTR" in + *I*) fehler "Snapshot '$SNAPSHOT' ist ungueltig (vollgelaufen) - der Rueckweg traegt nicht mehr" ;; +esac +echo "--- Snapshot" +lvs -o lv_name,lv_attr,origin,lv_size,data_percent "$VG/$SNAPSHOT" 2>/dev/null | sed 's/^/ /' + +# 3. Stack anhalten. Solange Container laufen, haelt Docker /srv offen. +echo "--- Stack anhalten" +docker compose -f "$COMPOSE" down 2>&1 | tail -n 5 + +# 4. /srv aushaengen. Ist der Ursprung geoeffnet, verschiebt LVM das Zusammenfuehren auf die naechste +# Aktivierung - also auf einen Neustart. Wir wollen es hier, jetzt und nachpruefbar. +if ! umount /srv 2>/dev/null; then + echo "--- /srv ist belegt von:" + { command -v fuser >/dev/null && fuser -vm /srv 2>&1 | head -n 20; } || echo " (fuser nicht verfuegbar)" + dienst_zurueck + fehler "/srv liess sich nicht aushaengen - es wurde nichts zurueckgenommen, der Dienst laeuft wieder" +fi + +# 5. Zusammenfuehren. +if ! lvconvert --merge "$VG/$SNAPSHOT" >/dev/null 2>&1; then + dienst_zurueck + fehler "Zusammenfuehren fehlgeschlagen - Stand unveraendert, der Dienst laeuft wieder" +fi +echo "Snapshot zusammengefuehrt - /srv steht auf dem Stand vor dem Update." + +# 6. Wieder einhaengen und mit der ebenfalls zurueckgenommenen Compose starten. +mount /srv || fehler "/srv liess sich nicht wieder einhaengen - Handarbeit noetig" +[ -f "$COMPOSE" ] || fehler "$COMPOSE fehlt nach dem Zurueckrollen - Handarbeit noetig" +START_AUSGABE="$(docker compose -f "$COMPOSE" up -d --quiet-pull 2>&1)" || { + echo "$START_AUSGABE" | tail -n 20 + fehler "Start nach dem Zurueckrollen fehlgeschlagen" +} + +# 7. Auf die Anwendung warten. +ENDE=$(( SECONDS + WARTE_MAX )) +while [ "$SECONDS" -lt "$ENDE" ]; do + [ "$(docker inspect -f '{{.State.Health.Status}}' espocrm 2>/dev/null)" = "healthy" ] && break + sleep 10 +done +[ "$(docker inspect -f '{{.State.Health.Status}}' espocrm 2>/dev/null)" = "healthy" ] \ + || fehler "espocrm nach ${WARTE_MAX}s nicht gesund - 'docker logs espocrm' ansehen" + +# 8. Ergebnis zeigen. +echo "--- Container" +docker compose -f "$COMPOSE" ps --format 'table {{.Name}}\t{{.Status}}' +echo "--- Instanz nach dem Rueckweg" +IMAGE="$(docker inspect -f '{{.Config.Image}}' espocrm 2>/dev/null)" +echo "Image: $IMAGE" +echo "Version: $(docker exec espocrm php -r '$v=""; foreach (["/var/www/html/application/Espo/Resources/defaults/config.php","/var/www/html/data/config.php","/var/www/html/data/config-internal.php"] as $f) { $a=@include $f; if (is_array($a) && !empty($a["version"])) { $v=$a["version"]; } } echo $v;' 2>/dev/null)" +echo "--- Hinweis" +echo "Der Snapshot ist verbraucht. Ein erneuter Rueckweg ist erst nach einem neuen ESPO-10 moeglich." +echo "Ursache des gescheiterten Updates klaeren, bevor es wiederholt wird." +echo "ESPO12_ERGEBNIS: OK"