Wenn Datenbank-Migrationen schiefgehen: Rollback vs. Roll-Forward
Ihr Team hat gerade eine Datenbank-Migration in der Produktion ausgeführt. Fünf Minuten später wird das Monitoring-Dashboard rot. Die Fehlerraten steigen. Nutzer melden Probleme. Jetzt müssen Sie schnell eine Entscheidung treffen: Machen Sie die Änderung rückgängig oder schieben Sie eine weitere Korrektur nach vorne?
Dieser Moment trennt Teams, die einen Plan haben, von Teams, die in Panik verfallen. Und die Antwort ist nie so einfach wie „einfach zurücksetzen“. Die Art der Änderung, die betroffenen Daten und der Zustand Ihres Systems bestimmen, welcher Weg sicherer ist.
Die zwei Wege zur Wiederherstellung
Es gibt grundsätzlich zwei Möglichkeiten, sich von einer fehlerhaften Datenbank-Migration zu erholen. Sie funktionieren unterschiedlich, bergen unterschiedliche Risiken und gelten für unterschiedliche Situationen.
Rollback bedeutet, die gerade ausgeführte Migration rückgängig zu machen. Sie führen die Down-Migration aus, das genaue Gegenteil dessen, was Sie getan haben. Wenn Sie eine Spalte hinzugefügt haben, entfernt die Down-Migration sie. Wenn Sie einen Datentyp geändert haben, ändert die Down-Migration ihn zurück.
Roll-Forward bedeutet, die problematische Migration zu belassen und eine neue Migration zu schreiben, die das Problem behebt. Sie gehen nicht zurück. Sie bewegen sich mit einer Korrektur vorwärts.
Beide Strategien haben ihre Berechtigung. Der Trick ist, zu wissen, welche für Ihre Situation geeignet ist, bevor Sie sie brauchen.
Wann ist ein Rollback sinnvoll?
Rollback funktioniert am besten für Änderungen, die sicher rückgängig gemacht werden können. Dies sind in der Regel nicht-destruktive Operationen, bei denen das Rückgängigmachen der Änderung keinen Datenverlust oder keine Datenbeschädigung verursacht.
Gute Kandidaten für ein Rollback sind:
- Hinzufügen einer nullable Spalte
- Erstellen eines neuen Index
- Hinzufügen einer neuen Tabelle
- Erstellen einer View oder Funktion
Diese Änderungen sind additiv. Wenn Sie sie rückgängig machen, entfernen Sie etwas, das hinzugefügt wurde. Dabei gehen keine vorhandenen Daten verloren oder werden beschädigt.
Stellen Sie sich ein Szenario vor, in dem Sie eine Spalte last_login_at zu Ihrer Benutzertabelle hinzugefügt haben. Die Spalte ist nullable, daher sind vorhandene Zeilen in Ordnung. Nach der Bereitstellung stellen Sie fest, dass der Anwendungscode einen Fehler hat, der falsche Zeitstempel schreibt. Ein Rollback durch Entfernen der Spalte ist sicher. Es werden keine Daten beschädigt, da die Spalte leer war oder Daten enthielt, die Sie nicht erhalten müssen.
Wann ist ein Roll-Forward sinnvoll?
Roll-Forward wird zur besseren Wahl, wenn die Migration destruktiv ist oder wenn das Rückgängigmachen mehr Schaden anrichten würde als das ursprüngliche Problem.
Situationen, in denen Roll-Forward sicherer ist:
- Entfernen einer Spalte oder Tabelle
- Ändern eines Datentyps auf eine Weise, die die Genauigkeit beeinträchtigt
- Massenhaftes Ändern vorhandener Datenwerte
- Zusammenführen von Tabellen
- Entfernen einer NOT NULL-Einschränkung, von der andere Systeme abhängen
Stellen Sie sich vor, Sie haben eine Migration ausgeführt, die eine Spalte legacy_status entfernt hat. Die Daten in dieser Spalte sind weg. Das Schreiben einer Down-Migration, die die Spalte wieder hinzufügt, stellt die Daten nicht wieder her. Benutzer, die von diesem Statusfeld abhängig waren, sehen jetzt Nullwerte. Ihr bester Schritt ist es, eine neue Migration zu schreiben, die die Spalte neu erstellt und sie aus einem Backup oder aus Anwendungsprotokollen befüllt.
Ein weiterer häufiger Fall: Sie haben eine Spalte von VARCHAR in INTEGER geändert und dabei Zeichenfolgenwerte in Zahlen umgewandelt. Ein Rollback durch Zurückändern des Typs zu VARCHAR ist riskant, da die Integer-Werte möglicherweise nicht sauber zurück in Zeichenfolgen konvertiert werden können. Ein Wert von 42 wird zu "42", aber was ist mit Werten, die während der Konvertierung abgeschnitten oder gerundet wurden? Sie haben Informationen verloren. Roll-Forward ermöglicht es Ihnen, eine sorgfältige Migration zu schreiben, die diese Randfälle explizit behandelt.
Down-Migrations schreiben, die tatsächlich funktionieren
Wenn Sie sich für die Unterstützung von Rollbacks entscheiden, müssen Ihre Down-Migrations mit Bedacht erstellt werden. Sie können keine mechanischen Umkehrungen der Up-Migration sein. Jede Down-Migration muss die Daten berücksichtigen, die zum Zeitpunkt des Rollbacks vorhanden sind.
Hier ist, was eine Down-Migration gefährlich macht:
Betrachten Sie ein konkretes Beispiel. Sie haben eine nullable Spalte last_login_at zur Tabelle users hinzugefügt, aber der Anwendungscode hat einen Fehler. Eine sichere Down-Migration und eine Roll-Forward-Korrektur würden wie folgt aussehen:
-- Sichere Down-Migration: Spalte entfernen, aber nur nach Sicherheitsprüfung
BEGIN;
-- Schritt 1: Überprüfen, ob kein Anwendungscode oder Views von dieser Spalte abhängen
-- (Diese Prüfung erfolgt in der Deployment-Pipeline, nicht in SQL)
-- Schritt 2: Spalte entfernen
ALTER TABLE users DROP COLUMN IF EXISTS last_login_at;
COMMIT;
-- Roll-Forward-Migration: Spalte mit dem korrekten Namen hinzufügen
BEGIN;
-- Spalte mit dem beabsichtigten Namen und Typ hinzufügen
ALTER TABLE users ADD COLUMN last_login_at TIMESTAMP;
-- Optional: Nachbefüllung aus Anwendungsprotokollen oder einem Backup
-- UPDATE users SET last_login_at = ... WHERE id IN (...);
COMMIT;
Die Down-Migration ist sicher, weil die Spalte nullable und additiv ist. Die Roll-Forward-Migration behebt das Problem, ohne die Schemaänderung rückgängig zu machen.
- Sie nimmt an, dass sich die Daten im gleichen Zustand befinden wie bei der Ausführung der Up-Migration
- Sie ignoriert Zeilen, die nach der Up-Migration hinzugefügt oder geändert wurden
- Sie macht Schemaänderungen blind rückgängig, ohne die Datenintegrität zu prüfen
Eine sichere Down-Migration zum Hinzufügen einer NOT NULL-Spalte mit einem Standardwert sollte:
- Überprüfen, ob das Entfernen der Spalte keine Anwendungsabfragen beschädigt
- Alle Zeilen behandeln, die nach dem Hinzufügen der Spalte eingefügt wurden
- Sicherstellen, dass keine Fremdschlüsselbeziehungen von der Spalte abhängen
Bei einer Datentypänderung von VARCHAR zu INTEGER muss die Down-Migration Werte behandeln, die keine saubere Zeichenfolgendarstellung haben. Möglicherweise müssen Sie Integer zurück in Zeichenfolgen umwandeln, aber auch NULL-Werte und Randfälle behandeln, die die ursprünglichen Zeichenfolgenwerte nicht hatten.
Die echten Risiken, die Sie nicht ignorieren können
Rollback klingt einfach, birgt aber ernsthafte Risiken, die Teams erst entdecken, wenn etwas schiefgeht.
Datenverlust ist das größte Risiko. Wenn eine Migration eine Spalte entfernt, sind die Daten weg. Keine Down-Migration kann sie zurückbringen, es sei denn, Sie haben ein Backup. Wenn Sie vor der Migration kein Backup erstellt haben, bedeutet Rollback die Akzeptanz eines dauerhaften Datenverlusts.
Migrationsabhängigkeiten schaffen versteckte Fallen. Wenn Migration zwei von einer Spalte abhängt, die von Migration eins hinzugefügt wurde, zerbricht ein Rollback auf den Stand vor Migration eins alles. Ihre Anwendung könnte abstürzen, weil sie Spalten erwartet, die nicht mehr existieren. Ihre Daten könnten inkonsistent werden, weil Zeilen auf Werte verweisen, die entfernt wurden.
Roll-Forward hat seine eigenen Risiken. Das größte ist die Zeit. Sie müssen eine neue Migration schreiben, sie durch die Pipeline bringen und bereitstellen. Während dieser Zeit läuft Ihre Anwendung mit dem fehlerhaften Zustand. Benutzer erleben Fehler. Ihr Team steht unter Druck, es schnell zu beheben, was die Wahrscheinlichkeit erhöht, einen weiteren Fehler zu machen.
Roll-Forward erfordert auch genaue Kenntnisse des aktuellen Datenbankzustands. Sie können die Korrektur nicht auf der Grundlage von Annahmen schreiben. Sie müssen genau wissen, wie die Daten jetzt aussehen, nicht wie sie aussahen, als die Migration entworfen wurde.
Die Entscheidung treffen, bevor Sie sie brauchen
Der schlechteste Zeitpunkt, um zwischen Rollback und Roll-Forward zu entscheiden, ist, wenn die Produktion brennt. Dann sind Sie gestresst, die Uhr tickt und Ihr Urteilsvermögen ist beeinträchtigt.
Ein besserer Ansatz ist, jede Migration zu klassifizieren, bevor sie ausgeführt wird. Weisen Sie jeder Migration eine Wiederherstellungskategorie zu:
- Sicher für Rollback: Additive Änderungen wie neue Spalten, Tabellen oder Indizes
- Erfordert Backup vor Rollback: Änderungen, die vorhandene Daten modifizieren oder nullable Spalten entfernen
- Nur Roll-Forward: Destruktive Änderungen wie das Entfernen von Spalten, Ändern von Datentypen oder Zusammenführen von Tabellen
Dokumentieren Sie diese Klassifizierung in Ihren Migrationsdateien oder in Ihrem Deployment-Runbook. Wenn etwas schiefgeht, liest Ihr Team die Klassifizierung und führt die vordefinierte Strategie aus. Keine Diskussion. Kein Hinterfragen.
Eine schnelle Entscheidungs-Checkliste
Bevor Sie eine Migration in der Produktion ausführen, stellen Sie diese Fragen:
Der folgende Entscheidungsbaum kann Ihnen helfen, die Checkliste unter Druck anzuwenden:
- Ist die Änderung additiv oder destruktiv?
- Kann die Down-Migration den exakten vorherigen Zustand wiederherstellen, einschließlich der Daten?
- Haben Sie ein verifiziertes Backup, das vor der Migration erstellt wurde?
- Wurde die Down-Migration in einer Staging-Umgebung getestet?
- Hängt diese Migration von anderen Migrationen ab, die davor ausgeführt wurden?
- Wie hoch sind die Kosten der Ausfallzeit, während Sie eine Roll-Forward-Korrektur schreiben?
Wenn Sie nicht alle diese Fragen beantworten können, führen Sie die Migration noch nicht in der Produktion aus.
Die konkrete Erkenntnis
Rollback und Roll-Forward sind keine austauschbaren Strategien. Sie gelten für verschiedene Arten von Änderungen und bergen unterschiedliche Risiken. Die Teams, die Datenbankvorfälle gut bewältigen, sind nicht diejenigen, die am schnellsten SQL tippen können. Es sind diejenigen, die vor der Migration über die Wiederherstellung nachgedacht haben. Sie haben ihre Änderungen klassifiziert, ihre Down-Migrations getestet und ein Backup bereit gehabt. Als das Dashboard rot wurde, gerieten sie nicht in Panik. Sie führten den Plan aus, den sie bereits gemacht hatten.