Behind the scene - Rails Migrate
All migration files in Rails
are by default prefixed with the timestamp which serves as the version number for the migration file. For an instance a migration file with name
20160310141700_create_users.rb
is prefixed with timestamp 20160310141700
.
Rails
maintains a table named schema_migrations
which has a single column named version
to store the version number of the migration files that have been already executed on DB.
Do all migration files are executed when we run rake db:migrate ?
The answer in NO.
Whenever we run the rake db:migrate
it reads all the version numbers stored in DB, as well as all the version number for the files present in folder db/migrate
. It then decides which are the migrations which are not yet applied on DB, and then execute only those. By this Rails ensures that each migration is applied only once. It runs change
or up
method in all the selected migration files.
By default rake db:migrate
task also runs db:schema:dump
, so that your db/schema.rb
reflects the latest structure of the database.
When we have a couple of developers working on a project then they can commit there migration files in any order, since rails running on an individual system already knows which migration files have been executed on DB and which not.
So for the same reason it is not wise to modify the old migration file, instead add a new one. Because it will not be executed on systems which have already executed it earlier.
Running migrtaions upto a particular version number
Since the version
numbers are timestamp, we can specify a particular version
number upto which migration needs to be executed.
If the current version number is less than 20160310141700
then above rake task will execute up
method on rails migration till 20160310141700
. Otherwise it will run migrations downward from current version, executing down
method on all rails migration excluding 20160310141700
.
If you want to look deep into source code on how it is really applied on low level, then you can look for class ActiveRecord::Migrator