ActiveRecord::Migration::CommandRecorder
records commands done during a migration and knows how to reverse those commands. The CommandRecorder
knows how to invert the following commands:
-
add_column
-
add_foreign_key
-
add_index
-
add_reference
-
add_timestamps
-
change_column
-
change_column_default (must supply a :from and :to option)
-
change_column_null
-
create_join_table
-
create_table
-
disable_extension
-
drop_join_table
-
drop_table (must supply a block)
-
enable_extension
-
remove_column (must supply a type)
-
remove_columns (must specify at least one column name or more)
-
remove_foreign_key (must supply a second table)
-
remove_index
-
remove_reference
-
remove_timestamps
-
rename_column
-
rename_index
-
rename_table
Methods
Constants
ReversibleAndIrreversibleMethods | = | [:create_table, :create_join_table, :rename_table, :add_column, :remove_column, :rename_index, :rename_column, :add_index, :remove_index, :add_timestamps, :remove_timestamps, :change_column_default, :add_reference, :remove_reference, :transaction, :drop_join_table, :drop_table, :execute_block, :enable_extension, :disable_extension, :change_column, :execute, :remove_columns, :change_column_null, :add_foreign_key, :remove_foreign_key ] |
Attributes
[RW] | commands | |
[RW] | delegate | |
[RW] | reverting |
Class Public methods
new(delegate = nil)
📝 Source code
# File activerecord/lib/active_record/migration/command_recorder.rb, line 44
def initialize(delegate = nil)
@commands = []
@delegate = delegate
@reverting = false
end
🔎 See on GitHub
Instance Public methods
inverse_of(command, args, &block)
Returns the inverse of the given command. For example:
recorder.inverse_of(:rename_table, [:old, :new])
# => [:rename_table, [:new, :old]]
This method will raise an IrreversibleMigration
exception if it cannot invert the command
.
📝 Source code
# File activerecord/lib/active_record/migration/command_recorder.rb, line 86
def inverse_of(command, args, &block)
method = :"invert_#{command}"
raise IrreversibleMigration, <<-MSG.strip_heredoc unless respond_to?(method, true)
This migration uses #{command}, which is not automatically reversible.
To make the migration reversible you can either:
1. Define #up and #down methods in place of the #change method.
2. Use the #reversible method to define reversible behavior.
MSG
send(method, args, &block)
end
🔎 See on GitHub
record(*command, &block)
Record command
. command
should be a method name and arguments. For example:
recorder.record(:method_name, [:arg1, :arg2])
📝 Source code
# File activerecord/lib/active_record/migration/command_recorder.rb, line 71
def record(*command, &block)
if @reverting
@commands << inverse_of(*command, &block)
else
@commands << (command << block)
end
end
🔎 See on GitHub
revert()
While executing the given block, the recorded will be in reverting mode. All commands recorded will end up being recorded reverted and in reverse order. For example:
recorder.revert{ recorder.record(:rename_table, [:old, :new]) }
# same effect as recorder.record(:rename_table, [:new, :old])
📝 Source code
# File activerecord/lib/active_record/migration/command_recorder.rb, line 57
def revert
@reverting = !@reverting
previous = @commands
@commands = []
yield
ensure
@commands = previous.concat(@commands.reverse)
@reverting = !@reverting
end
🔎 See on GitHub