Wann vor dem Release gesichert werden muss
Ein Symlink-Rollback reicht nicht immer. Wenn Datenbankmigrationen Teil des Deployments sind, muss ein aktuelles DB-Backup existieren – bevor der erste Migrationschritt ausgeführt wird, nicht danach.
Inhaltsverzeichnis
- 1. Warum ein Symlink-Rollback allein nicht ausreicht
- 2. Wann ein Backup vor dem Release Pflicht ist
- 3. Backup-Methoden: mysqldump vs. Percona XtraBackup
- 4. Backup als GitLab-Pipeline-Job integrieren
- 5. Backup-Verifikation: Das Backup wirklich prüfen
- 6. Backup-Timing: Unmittelbar vor der Migration
- 7. DB-Rollback: Wie ein Datenbank-Rollback abläuft
- 8. Backup-Aufbewahrung und Rotation
- 9. Mit vs. ohne Backup-Job: direkter Vergleich
- 10. Zusammenfassung
- 11. FAQ
1. Warum ein Symlink-Rollback allein nicht ausreicht
Der Symlink-Rollback in Magento-Deployments ist schnell und sicher für die Codeebene. Er wechselt den current-Symlink zurück auf ein älteres Release-Verzeichnis und stellt damit den alten Code sofort wieder her. Was er nicht kann: Datenbankänderungen rückgängig machen. Wenn setup:upgrade im neuen Release Tabellen verändert, Spalten hinzugefügt oder Konfigurationsdaten geschrieben hat, existieren diese Änderungen in der Datenbank – auch nach einem Code-Rollback.
Das Resultat eines Symlink-Rollbacks ohne DB-Rollback bei schemaändernden Migrationen: Der alte Code läuft mit dem neuen Datenbankschema. Je nach Art der Migration kann das harmlos sein (additive Spalten, die der alte Code ignoriert) oder kritisch (geänderte Spaltennamen oder -typen, auf die der alte Code zuzugreifen versucht). Ohne ein aktuelles Datenbankbackup gibt es keine Möglichkeit, einen konsistenten Zustand aus altem Code und alter Datenbank wiederherzustellen.
Der Backup-Job in der GitLab-Pipeline ist deshalb kein optionales Nice-to-have, sondern ein expliziter Sicherheitsschritt für jeden Release mit Datenbankmigrationen. Er muss vor dem Migrations-Schritt ausgeführt werden, nicht danach. Ein Backup, das nach einer fehlgeschlagenen Migration erstellt wird, sichert den kaputten Zustand, nicht den sauberen Ausgangszustand.
2. Wann ein Backup vor dem Release Pflicht ist
Ein Datenbank-Backup vor dem Release ist Pflicht, wenn das Release eine oder mehrere der folgenden Bedingungen erfüllt: Es enthält Datenbankmigrationen (Setup/Patch/Schema-Dateien in eigenen Modulen oder Magento-Core-Updates). Es enthält setup:upgrade-Aufrufe, die das Datenbankschema verändern. Es enthält Datentransformationen, die bestehende Datensätze modifizieren oder löschen. Es enthält Konfigurationsänderungen, die Datenbankeinträge in der core_config_data-Tabelle anlegen oder modifizieren.
Ein Backup ist optional, aber empfohlen, bei reinen Code-Releases ohne Datenbankinteraktion. Selbst hier kann ein Backup sinnvoll sein, wenn das Release auf einem System deployt wird, das keine zuverlässige automatische Backup-Infrastruktur hat. Der Grundsatz gilt: Kein Deploy auf Production ohne bekannten, verifizierten Backup-Zeitpunkt. Das Backup muss nicht zwingend im Deploy-Moment erstellt werden – ein verifizierbares Backup aus den letzten Stunden kann für reine Code-Releases ausreichen.
3. Backup-Methoden: mysqldump vs. Percona XtraBackup
mysqldump ist das Standard-Werkzeug für MySQL-Backups in Magento-Deployments. Es erzeugt eine SQL-Dump-Datei, die alle Tabellen, Daten und Indexe enthält. Nachteile: Bei großen Magento-Datenbanken (mehrere Gigabyte) kann mysqldump mehrere Minuten dauern und während dieser Zeit erhöhte Datenbanklast erzeugen. Mit dem --single-transaction-Flag wird der Dump innerhalb einer Transaktion durchgeführt, was konsistente Daten ohne Table-Locks gewährleistet – vorausgesetzt, alle Tabellen nutzen InnoDB.
Percona XtraBackup erstellt Hot-Backups ohne den normalen Datenbankbetrieb zu unterbrechen und ist für große Produktionsdatenbanken deutlich schneller. Für Magento-Setups mit Datenbanken unter 5 GB ist mysqldump --single-transaction in der Regel ausreichend und einfacher zu konfigurieren. Für größere Datenbanken oder Hochverfügbarkeits-Setups ist XtraBackup die professionellere Wahl. Die Entscheidung hängt von der Datenbankgröße und den akzeptablen Backup-Zeiten im Deployment-Fenster ab.
# Database backup job — runs before any deployment with DB migrations
backup:database:
stage: deploy
variables:
# Backup retention: keep 7 release backups
BACKUP_DIR: "/var/backups/magento/releases"
BACKUP_RETENTION: "7"
script:
- eval $(ssh-agent -s)
- echo "$SSH_PRIVATE_KEY" | tr -d '\r' | ssh-add -
- echo "$SSH_KNOWN_HOSTS" > ~/.ssh/known_hosts
- BACKUP_TS=$(date +%Y%m%d-%H%M%S)
- BACKUP_FILE="magento-pre-release-$BACKUP_TS.sql.gz"
- |
ssh "$DEPLOY_USER@$DEPLOY_HOST" bash -s << SSH
set -euo pipefail
mkdir -p "$BACKUP_DIR"
cd "$DEPLOY_PATH/current"
# Read DB credentials from Magento env.php
DB_HOST=\$(php -r "
\\\$env = include 'app/etc/env.php';
echo \\\$env['db']['connection']['default']['host'];
")
DB_NAME=\$(php -r "
\\\$env = include 'app/etc/env.php';
echo \\\$env['db']['connection']['default']['dbname'];
")
DB_USER=\$(php -r "
\\\$env = include 'app/etc/env.php';
echo \\\$env['db']['connection']['default']['username'];
")
DB_PASS=\$(php -r "
\\\$env = include 'app/etc/env.php';
echo \\\$env['db']['connection']['default']['password'];
")
# Create consistent backup using single transaction (InnoDB safe)
mysqldump \
--host="\$DB_HOST" \
--user="\$DB_USER" \
--password="\$DB_PASS" \
--single-transaction \
--quick \
--routines \
--triggers \
--add-drop-table \
"\$DB_NAME" | gzip -9 > "$BACKUP_DIR/$BACKUP_FILE"
echo "Backup created: $BACKUP_DIR/$BACKUP_FILE"
ls -lh "$BACKUP_DIR/$BACKUP_FILE"
SSH
needs: []
when: manual
only:
- tags
5. Backup-Verifikation: Das Backup wirklich prüfen
Ein Backup, das nicht verifiziert wurde, ist kein Backup – es ist eine Datei mit unbekanntem Inhalt. Die Verifikation eines mysqldump-Backups besteht aus zwei Ebenen. Die erste Ebene ist die Dateiintegrität: Prüfsumme berechnen und speichern, Dateigröße plausibilisieren (ein komprimiertes Backup kleiner als 1 MB ist für eine Magento-Produktionsdatenbank verdächtig). Die zweite Ebene ist die inhaltliche Prüfung: Die komprimierte SQL-Datei mit gunzip -t auf Komprimierungsintegrität prüfen, die ersten Zeilen der Dump-Datei auf SQL-Header prüfen.
Eine vollständige Restore-Verifikation – Backup in eine Test-Datenbank einspielen und auf Vollständigkeit prüfen – ist für produktive Release-Pipelines zu aufwändig. Sie sollte als separater, regelmäßig ausgeführter Job existieren, nicht als Teil des Deployment-Prozesses. Was im Deployment-Prozess ausreicht: Dateiintegrität, Komprimierungsintegrität und eine plausible Dateigröße. Diese drei Checks dauern Sekunden und schützen vor den häufigsten Backup-Fehlern (leere Datei, abgebrochener Dump, Kompressionsfehler).
6. Backup-Timing: Unmittelbar vor der Migration
Das Backup muss unmittelbar vor dem Migrations-Schritt erstellt werden. Eine Stunde zwischen Backup und Migration ist in einem aktiven Produktionssystem keine akzeptable Lücke – in dieser Zeit können tausende Bestellungen, Kundendaten und Konfigurationsänderungen in die Datenbank geschrieben worden sein. Ein Rollback auf ein Backup von vor einer Stunde bedeutet den Verlust dieser Daten.
In der GitLab-Pipeline wird das Timing durch die Job-Reihenfolge und die needs-Direktive erzwungen: Der Backup-Job muss als direktes Prerequisite des Migrations-Jobs definiert sein. Kein Migrations-Job darf starten, bevor der Backup-Job erfolgreich abgeschlossen wurde. Diese Abhängigkeit schützt vor dem häufigsten Fehler: dem Backup, das erst nach einem Problem erstellt wird, wenn die Datenbank bereits in einem beschädigten Zustand ist.
# Deploy pipeline with mandatory backup before DB migration
stages:
- build
- test
- backup # Backup stage runs before deploy
- deploy
- verify
- rollback
# Backup job — must complete before any deploy with DB migration
backup:pre-release:
stage: backup
script:
- eval $(ssh-agent -s)
- echo "$SSH_PRIVATE_KEY" | tr -d '\r' | ssh-add -
- echo "$SSH_KNOWN_HOSTS" > ~/.ssh/known_hosts
- BACKUP_TS=$(date +%Y%m%d-%H%M%S)
- |
ssh "$DEPLOY_USER@$DEPLOY_HOST" bash -s << 'SSH'
set -euo pipefail
BACKUP_FILE="/var/backups/magento/releases/pre-release-$BACKUP_TS.sql.gz"
mkdir -p /var/backups/magento/releases
# Run backup using credentials from env.php
cd "$DEPLOY_PATH/current"
php bin/magento setup:backup --db
# Also create external backup for faster restore
mysqldump --defaults-file=/etc/mysql/backup.cnf \
--single-transaction --quick --routines --triggers \
magento | gzip -9 > "$BACKUP_FILE"
# Verify backup integrity
gunzip -t "$BACKUP_FILE" && echo "Backup integrity OK"
ls -lh "$BACKUP_FILE"
# Record backup location for rollback job
echo "$BACKUP_FILE" > /var/backups/magento/latest-pre-release.txt
SSH
when: manual
only:
- tags
# Deploy job must explicitly wait for backup
deploy:production:with-migration:
stage: deploy
needs:
- backup:pre-release # Cannot start without successful backup
script:
- echo "Backup verified — starting deployment with DB migration"
# ... deploy steps with setup:upgrade
when: manual
only:
- tags
7. DB-Rollback: Wie ein Datenbank-Rollback abläuft
Ein Datenbank-Rollback ist teurer als ein Code-Rollback und sollte deshalb nur ausgeführt werden, wenn der Code-Rollback allein nicht ausreicht. Die Entscheidung muss schnell getroffen werden: Wenn das Deployment fehlgeschlagen ist und die Datenbank in einem inkonsistenten Zustand ist, zählt jede Minute. Der DB-Rollback-Prozess muss dokumentiert, geübt und durch ein Skript automatisiert sein, damit er auch unter Druck korrekt ausgeführt werden kann.
Der Ablauf eines DB-Rollbacks: Maintenance-Mode aktivieren, um weitere Datenbankschreibvorgänge zu verhindern. Code-Rollback durchführen (Symlink zurück auf vorheriges Release). Datenbank aus dem Pre-Release-Backup wiederherstellen. Backup-Restore verifizieren (Tabellenzahl, kritische Konfigurationswerte prüfen). Maintenance-Mode deaktivieren. Der gesamte Prozess dauert bei einem mysqldump-basierten Backup typischerweise 5–15 Minuten, abhängig von der Datenbankgröße.
8. Backup-Aufbewahrung und Rotation
Pre-Release-Backups müssen nicht unbegrenzt aufbewahrt werden, aber sie müssen so lange verfügbar sein, wie ein Rollback noch sinnvoll möglich ist. Eine Aufbewahrungszeit von 7 Release-Backups ist für die meisten Magento-Projekte ausreichend: Sie deckt die letzten sieben Deployments ab, was typischerweise mehrere Wochen entspricht. Ältere Backups werden automatisch rotiert, um Speicherplatz zu sparen.
Die Rotation sollte als Teil des Backup-Jobs implementiert werden, nicht als separaten Cron-Job: Unmittelbar nach dem Erstellen des neuen Backups werden alle Backups außer den letzten sieben gelöscht. Das hält den Speicher kontrolliert und vermeidet die Situation, in der der Backup-Speicher vollläuft und neue Backups nicht mehr erstellt werden können. Die Dateigröße der Backups sollte ebenfalls protokolliert werden, damit ungewöhnliche Größenänderungen als Anomalie erkannt werden.
9. Mit vs. ohne Backup-Job: direkter Vergleich
Der Unterschied zwischen einem Deployment-Prozess mit und ohne Backup-Job zeigt sich ausschließlich im Störfall. In normalen Deployments wird das Backup nie benötigt. Im Störfall – einem fehlgeschlagenen Migrations-Schritt, einer beschädigten Datenbank oder einem unerwarteten Code-Fehler mit Datenbankkorrumpierung – ist das Backup der einzige Weg zurück zu einem konsistenten Zustand.
| Szenario | Ohne Backup-Job | Mit Backup-Job (Pipeline) | Konsequenz |
|---|---|---|---|
| Migration schlägt fehl | Kein Rollback möglich | DB-Restore aus Backup | 5–15 Min. Restore vs. unbegrenzte Downtime |
| Code-Rollback bei DB-Migration | Inkonsistenter Zustand | Code + DB konsistent zurück | Sauberer Ausgangszustand wiederhergestellt |
| Backup-Zeitpunkt | Letztes nächtliches Backup | Unmittelbar vor Migration | Datenverlust minimal vs. stundenlang |
| Backup-Verifikation | Unbekannt | Integrität geprüft | Backup funktioniert garantiert |
| Rollback-Dauer | Stunden oder unmöglich | 5–15 Minuten | Planbar, vorhersehbar, kommunizierbar |
Die Kosten des Backup-Jobs sind gering: Der mysqldump-Befehl mit --single-transaction dauert bei einer typischen Magento-Datenbank (1–5 GB) zwischen 1 und 5 Minuten. Das ist eine überschaubare Investition in die Fähigkeit, im Störfall kontrolliert reagieren zu können. Ein Deployment ohne Backup ist eine Wette darauf, dass alles gutgeht. Ein Deployment mit Backup ist ein kontrollierter Prozess.
10. Zusammenfassung
Datenbank-Backups vor Magento-Releases sind nicht optional für Deployments mit Datenbankmigrationen. Sie sind die einzige Absicherung gegen Datenverlust bei einem fehlgeschlagenen Migrations-Schritt. Das Backup muss unmittelbar vor der Migration erstellt werden, seine Integrität muss verifiziert werden, und es muss als explizites Prerequisite des Migrations-Jobs in der GitLab-Pipeline definiert sein.
Der DB-Rollback-Prozess muss dokumentiert, geübt und durch Skripte automatisiert sein. Im Störfall entscheiden Minuten über den Umfang des Schadens. Ein Team, das den DB-Rollback-Prozess erst im Störfall zum ersten Mal ausführt, ist nicht vorbereitet. Ein Team, das ihn regelmäßig auf Staging übt und durch die Pipeline automatisiert hat, kann auch unter Druck kontrolliert handeln. Das ist der Kern von Zero-Downtime-Design: nicht die Hoffnung, dass nichts schiefgeht, sondern die Vorbereitung auf den Fall, dass etwas schiefgeht.
Datenbank-Backups für Magento-Releases — Das Wichtigste auf einen Blick
Wann Pflicht
Bei allen Releases mit Datenbankmigrationen: setup:upgrade, eigene Schema-Patches, Core-Updates.
Backup-Methode
mysqldump --single-transaction für InnoDB-Tabellen. Für große DBs: Percona XtraBackup. Integrität immer prüfen.
Pipeline-Integration
Backup-Job als needs-Prerequisite des Migrations-Jobs. Kein Deploy ohne erfolgreich abgeschlossenen Backup-Job.
DB-Rollback
Maintenance → Code-Rollback → DB-Restore aus Pre-Release-Backup → Verify → Maintenance off. Prozess dokumentiert und geübt.