Переходы Rails: self.up и self.down в сравнении с изменением
Похоже, что новая версия рельсов имеет "изменение" по сравнению с методами self.up и self.down.
Итак, что происходит, когда нужно отменить миграцию, как она знает, какие действия выполнять. У меня есть следующий метод, который мне нужно реализовать на основе онлайн-учебника:
class AddImageToUsers < ActiveRecord::Migration
def self.up
add_column :users, :image_file_name, :string
add_column :users, :image_content_type, :string
add_column :users, :image_file_size, :integer
add_column :users, :image_updated_at, :datetime
end
def self.down
remove_column :users, :image_file_name, :string
remove_column :users, :image_content_type, :string
remove_column :users, :image_file_size, :integer
remove_column :users, :image_updated_at, :datetime
end
end
Как я могу сделать то же самое с помощью нового метода изменения?
Ответы
Ответ 1
Для многих операций рельсы могут угадать, что такое обратная операция (без проблем). Например, в вашем случае, что такое обратная операция add_column
для вызова при откате? Конечно, это remove_column
. Что такое обратное к create_table
? Это drop_table
. Поэтому в этих случаях рельсы умеют откатываться и определять метод down
является излишним (вы можете видеть в документации методы которые в настоящее время поддерживаются методом изменения).
Но обратите внимание, потому что для какой-то операции вам все еще нужно определить метод down
, например, если вы измените точность десятичного столбца, как угадать исходную точность при откате? Это невозможно, поэтому вам нужно определить метод down
.
Как я уже сказал, я предлагаю вам прочитать Руководство по миграции Rails.
Ответ 2
Лучше использовать Up, Down, Change:
В Rails 3 (реверсивный):, который должен добавить новый столбец вверх и заполнить все записи в таблице только вверх и удалить этот столбец только вниз
def up
add_column :users, :location, :string
User.update_all(location: 'Minsk')
end
def down
remove_column :users, :location
end
Но:
Вам пришлось избегать использования метода изменения, который позволяет сэкономить некоторое время. Например, если вам не нужно обновлять значение столбца сразу после его добавления, вы бы сократили этот код до следующего вида:
def change
add_column :users, :location, :string
end
Внизу он добавит столбец в таблицу и удалит его вниз. Гораздо меньше кода и его прибыли.
В Rails 4: еще один полезный способ написать то, что нам нужно в одном месте:
def change
add_column :users, :location, :string
reversible do |direction|
direction.up { User.update_all(location: 'Minsk') }
end
end
Ответ 3
class AddImageToUsers < ActiveRecord::Migration
def change
add_column :users, :image_file_name, :string
add_column :users, :image_content_type, :string
add_column :users, :image_file_size, :integer
add_column :users, :image_updated_at, :datetime
end
end