What’s the syntax for dropping a database table column through a Rails migration?
23 Answers
remove_column :table_name, :column_name
For instance:
remove_column :users, :hobby
would remove the hobby Column from the users table.
5
And make sure to do this inside
up
anddown
methods, notchange
, as explained in the answer by @Powers.@XåpplI’-I0llwlg’I-Thanks for the comment. The change method can be used to drop a column in Rails 4 applications, but should not be used in Rails 3. I updated my answer accordingly.
– PowersYou can also use
remove_column :table_name, :column_name, :type, :options
within thechange
method, since if you specify the type reverting the migration is possible. From the documentation: Thetype
andoptions
parameters will be ignored if present. It can be helpful to provide these in a migration’schange
method so it can be reverted. In that case,type
andoptions
will be used by add_column.– NicolasIn Rails4, you can remove a column in the
change
method, but only if you specify the column type. E.g.remove_column, :table_name, :column_name, :column_type
. Otherwise you’ll get the following error when trying to run the migration:remove_column is only reversible if given a type
– DennisIt might be worth noting in the main answer that removing a column does not remove the corresponding index if it exists
– sameers
For older versions of Rails
ruby script/generate migration RemoveFieldNameFromTableName field_name:datatype
For Rails 3 and up
rails generate migration RemoveFieldNameFromTableName field_name:datatype
7
“rails g” can be used as an alternative to “rails generate”
– Nozrails g migration remove_field_name_from_table_name field_name:datatype
also worksNote also that
AddXXXtoTTT
anRemoveXXXFromTTT
may be followed by a white-spaced list of filed_name:data_type, and the appropriate add_column and remove_column statements will be created:rails g migration RemoveUnusefulFieldsFromUsers hair_color:string favorite_number:integer
removes two attributes using a single migration. Note also thatremove_column
is not supported bychange
method, so you have to write bothup
anddown
.Rails 4 seems to support
change
for this. Rollback works like it should.@AdamGrant I think that if you are using a
change
method that can be reverted* you’ll need to inform the data type (and all other field modifiers), so if you rollback that migration, the field can be correctly recreated. * When I say reverted, that’s in terms of database structure, of course, data from that column obviously will be lost.
Rails 4 has been updated, so the change method can be used in the migration to drop a column and the migration will successfully rollback. Please read the following warning for Rails 3 applications:
Rails 3 Warning
Please note that when you use this command:
rails generate migration RemoveFieldNameFromTableName field_name:datatype
The generated migration will look something like this:
def up
remove_column :table_name, :field_name
end
def down
add_column :table_name, :field_name, :datatype
end
Make sure to not use the change method when removing columns from a database table (example of what you don’t want in the migration file in Rails 3 apps):
def change
remove_column :table_name, :field_name
end
The change method in Rails 3 is not smart when it comes to remove_column, so you will not be able to rollback this migration.
5
@Powers – brilliant and clear answer – would you be able to elaborate on the following: “The change method in Rails 3 is not smart when it comes to remove_column, so you will not be able to rollback this migration.”
– BenKoshy@BKSpurgeon – In Rails 3, if you use the
change
method, then therake db:rollback
command will error out.rake db:rollback
is basically the opposite ofrake db:migrate
. This bug was fixed in Rails 4 🙂– PowersIn Rails 4, I tried to rollback a change drop column. It fails and states you must specify data_type (as in your down code in your answer)
Same problem occured to me as to @rmcsharry. My rails version is 4.2.2 and i used change method. when i tried to rollback, error occured that remove_column is only reversible if given a type.
– M. Habib
In a rails4 app it is possible to use the change method also for removing columns. The third param is the data_type and in the optional forth you can give options. It is a bit hidden in the section ‘Available transformations’ on the documentation .
class RemoveFieldFromTableName < ActiveRecord::Migration
def change
remove_column :table_name, :field_name, :data_type, {}
end
end
There are two good ways to do this:
remove_column
You can simply use remove_column, like so:
remove_column :users, :first_name
This is fine if you only need to make a single change to your schema.
change_table block
You can also do this using a change_table block, like so:
change_table :users do |t|
t.remove :first_name
end
I prefer this as I find it more legible, and you can make several changes at once.
Here’s the full list of supported change_table methods:
http://apidock.com/rails/ActiveRecord/ConnectionAdapters/SchemaStatements/change_table
Clear & Simple Instructions for Rails 5 & 6
- WARNING: You will lose data if you remove a column from your database. To proceed, see below:
- Warning: the below instructions are for trivial migrations. For complex migrations with e.g. millions and millions of rows, you will have to account for the possibility of failures, you will also have to think about how to optimise your migrations so that they run swiftly, and the possibility that users will use your app while the migration process is occurring. If you have multiple databases, or if anything is remotely complicated, then don’t blame me if anything goes wrong!
1. Create a migration
Run the following command in your terminal:
rails generate migration remove_fieldname_from_tablename fieldname:fieldtype
Note: the table name should be in plural form as per rails convention.
Example:
In my case I want to remove the accepted
column (a boolean value) from the quotes
table:
rails g migration RemoveAcceptedFromQuotes accepted:boolean
See the documentation re: a convention when adding/removing fields to a table:
There is a special syntactic shortcut to generate migrations that add
fields to a table.rails generate migration add_fieldname_to_tablename fieldname:fieldtype
2. Check the migration
# db/migrate/20190122035000_remove_accepted_from_quotes.rb
class RemoveAcceptedFromQuotes < ActiveRecord::Migration[5.2]
# with rails 5.2 you don't need to add a separate "up" and "down" method.
def change
remove_column :quotes, :accepted, :boolean
end
end
3. Run the migration
rake db:migrate
or rails db:migrate
(they’re both the same)
….And then you’re off to the races!
1
now migrations can also be run as
rails db:migrate
Generate a migration to remove a column such that if it is migrated (rake db:migrate
), it should drop the column. And it should add column back if this migration is rollbacked (rake db:rollback
).
The syntax:
remove_column :table_name, :column_name, :type
Removes column, also adds column back if migration is rollbacked.
Example:
remove_column :users, :last_name, :string
Note: If you skip the data_type, the migration will remove the column successfully but if you rollback the migration it will throw an error.
in rails 5 you can use this command in the terminal:
rails generate migration remove_COLUMNNAME_from_TABLENAME COLUMNNAME:DATATYPE
for example to remove the column access_level(string) from table users:
rails generate migration remove_access_level_from_users access_level:string
and then run:
rake db:migrate
0
Remove Columns For RAILS 5 App
rails g migration Remove<Anything>From<TableName> [columnName:type]
Command above generate a migration file inside db/migrate
directory. Snippet blow is one of remove column from table example generated by Rails generator,
class RemoveAgeFromUsers < ActiveRecord::Migration
def up
remove_column :users, :age
end
def down
add_column :users, :age, :integer
end
end
I also made a quick reference guide for Rails which can be found at here.
rails g migration RemoveXColumnFromY column_name:data_type
X = column name
Y = table name
EDIT
Changed RemoveXColumnToY
to RemoveXColumnFromY
as per comments – provides more clarity for what the migration is actually doing.
2
“Remove column to table” sounds strange, so from seems to be the better choice here.
@SebastianvomMeer yes I concur – the English reads much better with ‘from’
– BenKoshy
To remove the column from table you have to run following migration:
rails g migration remove_column_name_from_table_name column_name:data_type
Then run command:
rake db:migrate
Give below command it will add in migration file on its own
rails g migration RemoveColumnFromModel
After running above command you can check migration file remove_column code must be added there on its own
Then migrate the db
rake db:migrate
remove_column
in change
method will help you to delete the column from the table.
class RemoveColumn < ActiveRecord::Migration
def change
remove_column :table_name, :column_name, :data_type
end
end
Go on this link for complete reference : http://guides.rubyonrails.org/active_record_migrations.html
For removing column from table in just easy 3 steps as follows:
- write this command
rails g migration remove_column_from_table_name
after running this command in terminal one file created by this name and time stamp (remove_column from_table_name).
Then go to this file.
inside file you have to write
remove_column :table_name, :column_name
Finally go to the console and then do
rake db:migrate
Heres one more from rails console
ActiveRecord::Migration.remove_column(:table_name, :column_name)
Simply, You can remove column
remove_column :table_name, :column_name
For Example,
remove_column :posts, :comment
first try to create a migration file running the command:
rails g migration RemoveAgeFromUsers age:string
and then on the root directory of the project run the migration running the command:
rails db:migrate
Through
remove_column :table_name, :column_name
in a migration file
You can remove a column directly in a rails console by typing:
ActiveRecord::Base.remove_column :table_name, :column_name
Do like this;
rails g migration RemoveColumnNameFromTables column_name:type
I.e. rails g migration RemoveTitleFromPosts title:string
Anyway, Would be better to consider about downtime as well since the ActiveRecord caches database columns at runtime so if you drop a column, it might cause exceptions until your app reboots.
Ref: Strong migration
0
- Mark the column as ignored in the model
class MyModel < ApplicationRecord
self.ignored_columns = ["my_field"]
end
- Generate a migration
$ bin/rails g migration DropMyFieldFromMyModel
- Edit the migration
class DropMyFieldFromMyModel < ActiveRecord::Migration[6.1]
def change
safety_assured { remove_column :my_table, :my_field }
end
end
- Run the migration
$ bin/rails db:migrate
Step 1: Create a migration
rails g migration remove_column_name_from_table
Step 2: Change code in file migration just created
rails version < 3
def change
remove_column :table_name, :column_name, :datatype
end
rails version >= 3
def change
remove_column :table_name, :column_name
end
Step 3: Migrate
rake db:migrate
1
Simple and clear
– fguillen
Just run this in the rails console
ActiveRecord::Base.connection.remove_column("table_name", :column_name, :its_data_type)
or
TableName.find_by_sql(“ALTER TABLE table_name DROP column_name”)
1
I’m from the future and this is a terrible way to interact with your database.