1

I have a migration file called [timestamp]_create_posts.rb. I found that I made the column with a wrong data type. I need to make t.text :content instead of t.string :content.

I include the code from the above file:

class CreatePosts < ActiveRecord::Migration
  def change
    create_table :posts do |t|
      t.string :title
      t.string :content

      t.timestamps null: false
    end
  end
end

I kinda know that I should not directly change the file but rollback migration and change the schema and do the migration again. But I wasn't sure whether that's a right way to do it. It would be really nice if someone can guide me through this. I'm not really familiar with Rails.

3 Answers 3

5

You should not rollback anything. You should create a new migration, that will change a column with following content:

class UpdatePostsChangeContentColumn < ActiveRecord::Migration
  def change
    change_column :posts, :content, :text, limit: 60000 # or whatever
  end
end

or, even better, to supply the reasonable rollback of this migration:

class UpdatePostsChangeContentColumn < ActiveRecord::Migration
  def up
    change_column :posts, :content, :text, limit: 60000 # or whatever
  end
  # back to previous version
  def down
    change_column :posts, :content, :string
  end
end
Sign up to request clarification or add additional context in comments.

4 Comments

wait, I'm confused. Do I get rid of " create_table :posts do |t|" and replace with your method then?
Nope. The old migration remains untouched. This is a brand new migration, that is to be run subsequently after the legacy one. The main idea of migrations is that they are to be run in a sequence, producing the expected result after all of them are run. The legacy migration will produce a table with string column, this one will change the type of column to text.
Is this Rails convention? I am thinking most natural way is just replace my wrong code. Is there a reason why we kinda override by adding new migration after the old one?
Yes, this is Rails convention. While you are in the very beginning of the application creation, you might just rewrite the migration. But in general, when there are 900 migrations already in the database, there is db/schema.rb file, describing the database, there are different environments, many branches etc—this solution is bullet-proof: the database state is consistent on any migration step. This is a matter of doing things rails-way and it’s good to have this habit from the very beginning.
-1

The other option if you are just in the development is just to Drop you database and recreate it. Then you can modify that file, but THIS IS NOT ADVISED. I have done this again in development where i didn't care about recreating my database

rake db:drop
rake db:create
rake db:migrate

4 Comments

If you have a production DB, will you do this? No!
@Alexandr If you read fully, I said "If you are just in development"... and I even explain it will DROP the Database.. And I even said its not advised... Sounds like you didn't read before you copy and pasted
@Alexandr This post was just another method that I use from time to time. It is not my job to know the readers skill level... Again, I even said "its not advised"... Who ever reads it should do their own research before copy and pasting.
Kahsn asked about - "How to change the table". This is another type of question.
-2

There are two ways to change the column in table:

  1. You can use rake db:rollback VERSION=file_version and then after that you can change datatype manually.

  2. Generate another migration file. e.g rails g migration RemoveColumnToPost and the you can add following codes:

    def up
     change_column :posts, :content, :text
    end
    
    def down
     change_column :posts, :content, :string        
    end 
    

    And then use rake db:migrate

2 Comments

You remove the column and because of that all data is lost in it. The new column is empty. That could produce invalid records as well.
Now this is a shallow copy of my answer, that was given 4 minutes earlier.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.