Wie können Sie eine fehlgeschlagene Rails-Migration zurücksetzen? Ich würde erwarten, dass rake db:rollback
dies die fehlgeschlagene Migration rückgängig macht, aber nein, es wird die vorherige Migration zurückgesetzt (die fehlgeschlagene Migration minus eins). Und rake db:migrate:down VERSION=myfailedmigration
funktioniert auch nicht. Ich bin ein paar Mal darauf gestoßen und es ist sehr frustrierend. Hier ist ein einfacher Test, den ich durchgeführt habe, um das Problem zu duplizieren:
class SimpleTest < ActiveRecord::Migration
def self.up
add_column :assets, :test, :integer
# the following syntax error will cause the migration to fail
add_column :asset, :test2, :integer
end
def self.down
remove_column :assets, :test
remove_column :assets, :test2
end
end
Ergebnis:
== SimpleTest: Migration ================================================ ======== - add_column (: Assets ,: Test ,: Ganzzahl) -> 0,0932s - add_column (: Asset ,: Fehler) Rechen abgebrochen! Ein Fehler ist aufgetreten, alle späteren Migrationen wurden abgebrochen: falsche Anzahl von Argumenten (2 für 3)
ok, lass es uns zurückrollen:
$ rake db: Rollback == AddLevelsToRoles: Zurücksetzen ============================================= == - remove_column (: Rollen ,: Ebene) -> 0,0778 s == AddLevelsToRoles: zurückgesetzt (0.0779s) ======================================
huh? Das war meine letzte Migration vor SimpleTest, nicht die fehlgeschlagene Migration. (Und oh, es wäre schön, wenn die Migrationsausgabe die Versionsnummer enthalten würde.)
Versuchen wir also, den Down für die fehlgeschlagene Migration SimpleTest auszuführen:
$ rake db: migrate: down VERSION = 20090326173033 $
Es passiert nichts und auch keine Ausgabe. Aber vielleicht lief die Migration trotzdem? Beheben wir also den Syntaxfehler in der SimpleTest-Migration und versuchen Sie, ihn erneut auszuführen.
$ rake db: migrate: up VERSION = 20090326173033 == SimpleTest: Migration ================================================ ======== - add_column (: Assets ,: Test ,: Ganzzahl) Rechen abgebrochen! MySQL :: Fehler: Doppelter Spaltenname 'Test': ALTER TABLE` Assets` ADD` Test` Int (11)
Nee. Offensichtlich hat die Migration: down nicht funktioniert. Es scheitert nicht, es wird einfach nicht ausgeführt.
Es gibt keine andere Möglichkeit, diese doppelte Tabelle zu entfernen, als manuell in die Datenbank zu gehen und sie zu entfernen und dann den Test auszuführen. Es muss einen besseren Weg geben.
quelle
Um zu einer bestimmten Version zu gelangen, verwenden Sie einfach:
Wenn eine Migration jedoch teilweise fehlschlägt, müssen Sie sie zuerst bereinigen. Ein Weg wäre:
down
Methode der Migration, um nur den Teil rückgängig zu machen, derup
funktioniert hatdown
)quelle
OK, Leute, hier ist, wie du es tatsächlich machst. Ich weiß nicht, worüber die obigen Antworten sprechen.
Sie können nach unten und wieder nach oben migrieren, wenn Sie überprüfen möchten, ob Sie es jetzt haben.
quelle
bundle exec rake db:migrate:redo
. Es wird einen Schritt zurück und einen Schritt vorwärts gehen, sodass Sie überprüfen können, ob Ihre letzte Migration vollständig ausgeführt wird. Dies ist immer dann eine gute Vorgehensweise, wenn Sie eine Migration zusammen mit einigen Code-Updates vorantreiben müssen.Ich bin damit einverstanden, dass Sie PostgreSQL verwenden, wenn dies möglich ist. Wenn Sie jedoch mit MySQL nicht weiterkommen, können Sie die meisten dieser Probleme vermeiden, indem Sie zuerst Ihre Migration in Ihrer Testdatenbank versuchen:
Sie können zum vorherigen Status zurückkehren und es erneut versuchen
quelle
2015 mit Rails 4.2.1 und MySQL 5.7 kann eine fehlgeschlagene Migration nicht mit Standard-Rake-Aktionen behoben werden, die Rails bereitstellt, wie dies 2009 der Fall war.
MySQL unterstützt kein Rollback von DDL-Anweisungen (im MySQL 5.7-Handbuch ). Und damit kann Rails nichts anfangen.
Außerdem können wir überprüfen, wie Rails den Job ausführt: Eine Migration wird in eine Transaktion eingeschlossen, je nachdem, wie der Verbindungsadapter reagiert
:supports_ddl_transactions?
. Nach einer Suche nach dieser Aktion an der Rails-Quelle (Version 4.2.1) stellte ich fest, dass nur Sqlite3 und PostgreSql Transaktionen unterstützen und standardmäßig nicht unterstützt werden.Bearbeiten Somit die aktuelle Antwort auf die ursprüngliche Frage: Eine fehlgeschlagene MySQL-Migration muss manuell behoben werden.
quelle
Der einfache Weg, dies zu tun, besteht darin, alle Ihre Aktionen in eine Transaktion einzubinden:
Wie Luke Francl bemerkte, "unterstützen die MyISAM-Tabellen von MySql keine Transaktionen" - weshalb Sie MySQL im Allgemeinen oder zumindest MyISAM im Besonderen vermeiden sollten.
Wenn Sie die InnoDB von MySQL verwenden, funktioniert das oben Genannte einwandfrei. Alle Fehler in oben oder unten werden zurückgesetzt.
ACHTUNG Einige Arten von Aktionen können nicht über Transaktionen zurückgesetzt werden. Im Allgemeinen können Tabellenänderungen (Löschen einer Tabelle, Entfernen oder Hinzufügen von Spalten usw.) nicht rückgängig gemacht werden.
quelle
Führen Sie nur die Abwärtsmigration von der Konsole aus:
http://gilesbowkett.blogspot.com/2007/07/how-to-use-migrations-from-console.html (klicken Sie sich zu seiner Pastete durch)
quelle
Ich hatte einen Tippfehler (in "add_column"):
und dann Ihr Problem (kann teilweise fehlgeschlagene Migration nicht rückgängig machen). Nach einigem fehlgeschlagenen googeln habe ich folgendes ausgeführt:
Wie Sie sehen, habe ich die Korrekturzeile einfach von Hand hinzugefügt und dann wieder entfernt, bevor ich sie eingecheckt habe.
quelle
Die obige Antwort von Alejandro Babio liefert die beste aktuelle Antwort.
Ein weiteres Detail möchte ich hinzufügen:
Wenn die
myfailedmigration
Migration fehlschlägt, wird sie nicht als angewendet betrachtet. Dies kann durch Ausführen überprüft werden. Diesrake db:migrate:status
würde eine Ausgabe ähnlich der folgenden anzeigen:Der verbleibende Effekt der
add_column :assets, :test, :integer
Ausführung auf die fehlgeschlagene Migration muss auf Datenbankebene mit eineralter table assets drop column test;
Abfrage rückgängig gemacht werden.quelle