There are multiple
db namespace rake tasks, which are very useful for a Rails developer.
I don’t often see them covered in Rails tutorials as a task list, and it took me a while to figure out which commands I needed to use in my regular workflow.
Most beginner developers stick to
rake db:seed and
rake db:reset, but there are quite a few more options.
Migration is a version of a database (I still don’t understand what we are migrating and where, but oh well, such is conventional terminology).
Each new migration modifies a database schema (which starts out completely blank) by adding and removing data, changing data types etc.
Your schema is normally stored in
db/schema.rb, although for some developers, it will be in
(To create and use
config.active_record.schema_format = :sql in your
config/application.rb. Most beginners should be sticking to schema.rb, the default version.)
First, some schema-related rake tasks:
rake db:version- to see your current schema version. Schemar versions are normally also listed as timestamps, so you will see something like
Current version: 20151014015045.
rake db:forwardwill push the schema one step up.
rake db:schema:load– loads she schema into your database. Good practice is using it when you first put your app in production; then run migrations from there on.
rake db:schema:dump– dumps she schema.
Now back to migrations:
The easiest way to generate a migration is to run
rails g migration AddUseridToPosts user_id:integer.
Once a migration has been generated, it will be listed in your
db/migrate folder, usually with a format
rails g generates a timestamp prefix because that is the order that Rails uses to execute pending migrations.
If you are creating a migration manually or copying over from another file, you need to use any alphanumeric prefix (even if it’s one 1,2, and 3) that allows Rails to run pending migrations in correct order; or use a manual datestamp if that’s what your other migrations use.
The migration in the example above adds a new colume of
user_id, which is a type
integer, to a table named
Posts – assumption here is that one user
has_many posts and a post
belongs_to user (if you don’t know what that means, see Active Record Association Basics ).
You can generate a migration to add a new table altogether, to remove a table or a column, to change a data type of a column, etc.
Even if the migration is in your migrate folder, it does not mean it is in the database schema yet. To incorporate it into the schema, you have any pending migrations into it. And that’s when
rake db:migrate task comes in.
Before I get started, see this rails source to see the database.rake file that describes exactly what each task does.
Rake tasks undergo changes between different versions of Rails, so it’s good to keep an eye out for anything that might be coming soon.
Rake migration tasks
rake db:migrate– runs the change or up method for all pending migrationsone by one in order indicated by name prefixes. If there are no such migrations, running the task won’t produce any outcome. But when there are, it also executes
db:schema:dumpas it needs to dump the schema and build it anew considering the migration(s) that have been added.
rake db:migrate VERSION=version_number/timestamp– runs specific migration to which the datestamp refers.
rake db:migrate VERSION=0>– roll back all migrations
rake db:migrate RAILS_ENV=test– runs migrations in an indicated envrionment.
You should be able to get timestamp as a prefix to a migration file name if you used a rails g command as explained above.
rake db:migrate:up– runs up command for a given migration version (default is current version)
rake db:migrate:down– runs down command aka rolls back command for a given migration version
down are actually old-school commands;
up makes a change to the schema and
down reverses the
rake db:migrate:redo– “Rollbacks the database one migration and re migrate up (options:
rake db:migrate:redo STEP=x= rolls back x many migrations and re-runs them
rake db:migrate:rollback– roll back last migration to get user back one step.
rake db:migrate:rollback STEP=x– roll back x many steps
Now this is interesting:
rake db:migrate= undo and re-do migrations again for current environment. It does not rollback migrations. You would want to use it when, say, running
rails destroy scaffold Nameas it will remove a corresponding migration and the schema would need to be re-created. You would still need to run
rake db:seedif you have any seed data.
rake db:create is rather straightforward and an opposite of
rake db:drop; it needs to be run when a Rails project is first created or after a database has been dropped, as it the case with
rake db:migrate:reset above).
Note the difference compared to:
rake db:setup =
rake db:schema:load OR
rake db:structure:load +
schema.rbinto your database)
db/structure.sqlif you have specified that in your config, otherwise it will load
Which means that
rake db:reset drops the database; recreates it from
db/structure.sql in your current environment (and NOT from migrations); seeds database from
seeds.rb. Note that if you have had anything imported into your database from, say, a
csv file, that content will also be gone.
- Note that
rake db:migrate:resetwon’t seed your database and
Another rake task is also useful to see where you are with regard to migrations:
rake db:migrate:status– display status of all migrations. It will alert you if there are no schema migrations in your project yet.
And a heavy hitter to get you re-started with a clean slate:
rake db:purge– “Empty the database from DATABASE_URL or config/database.yml for the current RAILS_ENV (use db:drop:all to drop all databases in the config). Without RAILS_ENV it defaults to purging the development and test databases.”
rake db:purge task was only added in January 2014 and is less known.)
There is a great Rails Guide explaining a lot of these here.
Remember to restart your rails server when working with these.
Should these tasks not meet your needs, you can always create a custom rake task to do exactly what you need.