如何使remove_column可逆?

2024-03-31

我有一个删除列的迁移:

def change
  remove_column :foos, :bar, :boolean
end

当我尝试rake db:rollback迁移时,我收到以下错误:

remove_column is only reversible if given a type.

The ActiveRecord::迁移 http://api.rubyonrails.org/classes/ActiveRecord/Migration.html文档说以下是签名remove_column:

remove_column(table_name, column_name, type, options)

所以在这种情况下我的类型应该是:boolean,我预计这种迁移是可逆的。我缺少什么?

我当然可以将其分解为up and down迁移以避免这个问题,但我想了解为什么change语法在这种情况下不起作用。


只需将第三个参数(列的 :type)添加到remove_column方法使该迁移可逆。所以OP的原始代码实际上确实有效,如下所示:

remove_column :foos, :bar, :boolean

这个答案的其余部分是试图发现为什么这个方法不起作用,但OP最终让它起作用。


我在文档中看到一些相反的信息ActiveRecord::迁移 http://api.rubyonrails.org/classes/ActiveRecord/Migration.html:

一些命令如删除列无法逆转。如果您想定义在这些情况下如何向上和向下移动,则应该像以前一样定义向上和向下方法。

有关可逆命令的列表,请参阅 ActiveRecord::Migration::CommandRecorder。

而这个来自ActiveRecord::迁移::CommandRecorder http://api.rubyonrails.org/classes/ActiveRecord/Migration/CommandRecorder.html:

ActiveRecord::Migration::CommandRecorder 记录迁移期间完成的命令,并知道如何反转这些命令。 CommandRecorder 知道如何反转以下命令:

添加列

添加索引

添加时间戳

创建表

创建连接表

删除时间戳

重命名_列

重命名索引

重命名表

无论如何,这个文档似乎已经过时了......深入研究github上的源码 https://github.com/rails/rails/blob/e1d4673102f7c4e58964a6de864402ae9a615688/activerecord/lib/active_record/migration/command_recorder.rb#L128:

让你悲伤的方法是:

def invert_remove_column(args)
  raise ActiveRecord::IrreversibleMigration, "remove_column is only reversible if given a type." if args.size <= 2
  super
end

我尝试了一下...在我的 Rails 4.1.2 应用程序上设置了迁移,并且迁移是双向的——向上和向下。这是我的迁移:

class TestRemoveColumn < ActiveRecord::Migration
  def change
    remove_column :contacts, :test, :boolean
  end
end

我也尝试过:boolean缺少参数并出现与您所说的相同的错误。您确定您使用的是 Rails 4.1.2 的最终版本 - 不是候选版本之一?如果你是,我建议放一个binding.pry进入 Rails 源代码invert_remove_column方法来检查参数列表并查看发生了什么。为此,只需运行bundle open activerecord然后探索:lib/active_record/migration/command_recorder.rb:128.

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何使remove_column可逆? 的相关文章

随机推荐