Class: ActiveRecord::Migrator
Do not use. This class is for internal use only.
Relationships & Source Files | |
Inherits: | Object |
Defined in: | activerecord/lib/active_record/migration.rb |
Constant Summary
-
MIGRATOR_SALT =
# File 'activerecord/lib/active_record/migration.rb', line 16152053462845
Class Attribute Summary
Class Method Summary
-
.current_version
For cases where a table doesn’t exist like loading from schema cache.
- .new(direction, migrations, schema_migration, internal_metadata, target_version = nil) ⇒ Migrator constructor
Instance Attribute Summary
- #down? ⇒ Boolean readonly private
-
#invalid_target? ⇒ Boolean
readonly
private
Return true if a valid version is not provided.
- #up? ⇒ Boolean readonly private
- #use_advisory_lock? ⇒ Boolean readonly private
Instance Method Summary
-
#current
Alias for #current_migration.
- #current_migration (also: #current)
- #current_version
- #load_migrated
- #migrate
- #migrated
- #migrations
- #pending_migrations
- #run
- #runnable
- #connection private
-
#ddl_transaction(migration, &block)
private
Wrap the migration in a transaction only if supported by the adapter.
- #execute_migration_in_transaction(migration) private
- #finish private
- #generate_migrator_advisory_lock_id private
-
#migrate_without_lock
private
Used for running multiple migrations up to or down to a certain value.
- #ran?(migration) ⇒ Boolean private
-
#record_environment
private
Stores the current environment in the database.
- #record_version_state_after_migrating(version) private
-
#run_without_lock
private
Used for running a specific migration.
- #start private
- #target private
- #use_transaction?(migration) ⇒ Boolean private
- #validate(migrations) private
- #with_advisory_lock private
Constructor Details
.new(direction, migrations, schema_migration, internal_metadata, target_version = nil) ⇒ Migrator
# File 'activerecord/lib/active_record/migration.rb', line 1421
def initialize(direction, migrations, schema_migration, , target_version = nil) @direction = direction @target_version = target_version @migrated_versions = nil @migrations = migrations @schema_migration = schema_migration @internal_metadata = validate(@migrations) @schema_migration.create_table @internal_metadata.create_table end
Class Attribute Details
.migrations_paths (rw)
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1407
attr_accessor :migrations_paths
Class Method Details
.current_version
For cases where a table doesn’t exist like loading from schema cache
# File 'activerecord/lib/active_record/migration.rb', line 1410
def current_version connection_pool = ActiveRecord::Tasks::DatabaseTasks.migration_connection_pool schema_migration = SchemaMigration.new(connection_pool) = InternalMetadata.new(connection_pool) MigrationContext.new(migrations_paths, schema_migration, ).current_version end
Instance Attribute Details
#down? ⇒ Boolean
(readonly, private)
[ GitHub ]
# File 'activerecord/lib/active_record/migration.rb', line 1579
def down? @direction == :down end
#invalid_target? ⇒ Boolean
(readonly, private)
Return true if a valid version is not provided.
# File 'activerecord/lib/active_record/migration.rb', line 1524
def invalid_target? @target_version && @target_version != 0 && !target end
#up? ⇒ Boolean
(readonly, private)
[ GitHub ]
# File 'activerecord/lib/active_record/migration.rb', line 1575
def up? @direction == :up end
#use_advisory_lock? ⇒ Boolean
(readonly, private)
[ GitHub ]
# File 'activerecord/lib/active_record/migration.rb', line 1596
def use_advisory_lock? connection.advisory_locks_enabled? end
Instance Method Details
#connection (private)
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1489
def connection ActiveRecord::Tasks::DatabaseTasks.migration_connection end
#current
Alias for #current_migration.
# File 'activerecord/lib/active_record/migration.rb', line 1442
alias :current :current_migration
#current_migration Also known as: #current
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1439
def current_migration migrations.detect { |m| m.version == current_version } end
#current_version
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1435
def current_version migrated.max || 0 end
#ddl_transaction(migration, &block) (private)
Wrap the migration in a transaction only if supported by the adapter.
# File 'activerecord/lib/active_record/migration.rb', line 1584
def ddl_transaction(migration, &block) if use_transaction?(migration) connection.transaction(&block) else yield end end
#execute_migration_in_transaction(migration) (private)
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1528
def execute_migration_in_transaction(migration) return if down? && !migrated.include?(migration.version.to_i) return if up? && migrated.include?(migration.version.to_i) Base.logger.info "Migrating to #{migration.name} (#{migration.version})" if Base.logger ddl_transaction(migration) do migration.migrate(@direction) (migration.version) end rescue => e msg = +"An error has occurred, " msg << "this and " if use_transaction?(migration) msg << "all later migrations canceled:\n\n#{e}" raise StandardError, msg, e.backtrace end
#finish (private)
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1549
def finish migrations.index(target) || migrations.size - 1 end
#generate_migrator_advisory_lock_id (private)
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1616
def generate_migrator_advisory_lock_id db_name_hash = Zlib.crc32(connection.current_database) MIGRATOR_SALT * db_name_hash end
#load_migrated
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1484
def load_migrated @migrated_versions = Set.new(@schema_migration.integer_versions) end
#migrate
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1452
def migrate if use_advisory_lock? with_advisory_lock { migrate_without_lock } else migrate_without_lock end end
#migrate_without_lock (private)
Used for running multiple migrations up to or down to a certain value.
# File 'activerecord/lib/active_record/migration.rb', line 1503
def migrate_without_lock if invalid_target? raise UnknownMigrationVersionError.new(@target_version) end record_environment runnable.each(&method(:execute_migration_in_transaction)) end
#migrated
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1480
def migrated @migrated_versions || load_migrated end
#migrations
[ GitHub ]#pending_migrations
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1475
def pending_migrations already_migrated = migrated migrations.reject { |m| already_migrated.include?(m.version) } end
#ran?(migration) ⇒ Boolean
(private)
#record_environment (private)
Stores the current environment in the database.
# File 'activerecord/lib/active_record/migration.rb', line 1513
def record_environment return if down? @internal_metadata[:environment] = connection.pool.db_config.env_name end
#record_version_state_after_migrating(version) (private)
[ GitHub ]#run
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1444
def run if use_advisory_lock? with_advisory_lock { run_without_lock } else run_without_lock end end
#run_without_lock (private)
Used for running a specific migration.
# File 'activerecord/lib/active_record/migration.rb', line 1494
def run_without_lock migration = migrations.detect { |m| m.version == @target_version } raise UnknownMigrationVersionError.new(@target_version) if migration.nil? record_environment execute_migration_in_transaction(migration) end
#runnable
[ GitHub ]#start (private)
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1553
def start up? ? 0 : (migrations.index(current) || 0) end
#target (private)
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1545
def target migrations.detect { |m| m.version == @target_version } end
#use_transaction?(migration) ⇒ Boolean
(private)
# File 'activerecord/lib/active_record/migration.rb', line 1592
def use_transaction?(migration) !migration.disable_ddl_transaction && connection.supports_ddl_transactions? end
#validate(migrations) (private)
# File 'activerecord/lib/active_record/migration.rb', line 1557
def validate(migrations) name, = migrations.group_by(&:name).find { |_, v| v.length > 1 } raise DuplicateMigrationNameError.new(name) if name version, = migrations.group_by(&:version).find { |_, v| v.length > 1 } raise DuplicateMigrationVersionError.new(version) if version end
#with_advisory_lock (private)
[ GitHub ]# File 'activerecord/lib/active_record/migration.rb', line 1600
def with_advisory_lock lock_id = generate_migrator_advisory_lock_id got_lock = connection.get_advisory_lock(lock_id) raise ConcurrentMigrationError unless got_lock load_migrated # reload schema_migrations to be sure it wasn't changed by another process before we got the lock yield ensure if got_lock && !connection.release_advisory_lock(lock_id) raise ConcurrentMigrationError.new( ConcurrentMigrationError::RELEASE_LOCK_FAILED_MESSAGE ) end end