rails migration is not reflecting while migration is successful - ruby-on-rails

I have created 2 tables (categories and products) and I did has_many association like Category has_many :products and Product belongs_to :category.
When I do a migration like:
rails generate migration add_product_id_to_categories product_id:integer
then migration is running but not seeing product_id in Category.
I've tried multiple ways like
add_product_id_to_category product_id:integer
but still facing the same problem.

You only generated a migration file (rails generate migration add_product_id_to_categories product_id:integer). You have to run the migration with rake db:migrate.

Generating a migration is a different thing than actually running it. You just generated it, and in order to execute what you have written, you need to run it, and you can do so by invoking the following command:
rake db:migrate
Not sure that either you have run the migration or not, run the following command, and it will tell you the statues of all the migrations. If the status is up, the migration has been run, and for down, a migration couldn't be run.
rake db:migrate:status
When you run a migration, and you would like to get notified in terminal that it has been successfully run, you can add a puts statement in there like following:
class AddColumnToCategories < ActiveRecord::Migration
def change
add_column :categories, :product_id, :integer, index: true
puts "product_id column has been added into categories."
end
end

Have you tried rails generate migration AddProductIdToCategories product_id:integer?
When you have created the migration if you look inside the migration file you can see if any code has been generated in the change method before you run the migration. If it has not generated any content you can manually add it:
def change
add_column :categories, :product_id, :integer
end

Related

rake:db rollback does not delete the migration?

I have entrees and snapshots. An entree has_many snapshots. I forgot to add the foreign key to snapshots. So I later added migration:
$ rails generate migration add_snapshot_ref_to_entrees snapshot:references
Migration file looked like this:
class AddSnapshotRefToEntrees < ActiveRecord::Migration[5.0]
def change
add_reference :entrees, :snapshot, foreign_key: true
end
end
This did not do what I want. It added an snapshot_id to entrees, rather than adding an entree_id to snapshots.
So I run the rollback:
bundle exec rake db:rollback
It correctly moves the following from schema.rb:
add_foreign_key "entrees", "snapshots"
And also correctly rolls back the database itself. But the migration file remains in db/migrate. Am I suppose to remove this myself or did not complete its job?
Yes, you need to remove this file manually. Regarding your association, it should be as below:
class AddSnapshotRefToEntrees < ActiveRecord::Migration[5.0]
def change
add_reference :snapshots, :entree, foreign_key: true
end
end
It's not supposed to.
rails destroy migration add_snapshot_ref_to_entrees
In order to rollback a specific migration use:
rake db:migrate:down VERSION=YOUR_MIGRATION_VERSION
For Example:
rake db:migrate:down VERSION=20100905201547
To find the version of all migrations, you can use this command:
rake db:migrate:status
rake db:migrate:down and rollback worked on database label it's not removing file from db/migrate.
You need to remove direct from db/migrate folder.

Fixing migration error

I tried to create a migration to add roles to my user tables but i accidentally typed AddRolesToUsers instead of AddRoleToUser. So i tried creating a new migration with the correct AddRoleToUsers but when i tried to run rake db:migrate i got an error :
SQLite3::SQLException: duplicate column name: role: ALTER TABLE "users" ADD "role" integer/Users/miguel/.rvm/gems/ruby-2.2.1/gems/sqlite3-1.3.11/lib/sqlite3/database.rb:91:in `initialize'
I tried rake db:migrate:down VERSION= do delete the one I had to type on but i keep getting the same error . PS: i deleted the migration file manually after running rake db:migrate:down VERSION=
rails g migration AddRoleToUsers role:integer
migration file :
class AddRoleToUsers < ActiveRecord::Migration
def change
add_column :users, :role, :integer
end
end
When you ran the first migration, the role column was added to the Users table. The error on the second migration tells you that much.
To clear the migration pending error, you need to comment out the add_column statement in the new migration.
i.e,
class AddRoleToUsers < ActiveRecord::Migration
def change
# add_column :users, :role, :integer
end
end
Then run the migration. This way, the new migration should run successfully.
You can now uncomment it and delete the previous migration, so that when you deploy, only the newer migration is run and the role column is added successfully.
In that case right click and delete both migration files and start again. The error exists because it thinks you want to add two columns both named role to your users table
UPDATE
In that case, if role already exists in your users table, a migration must've been successfully run and there is no need to run another. As long as the role column is there, trying to add another column called role will always give you an error. If you wanted to test that you are still able to add new columns you can always check by creating a test migration AddSomethingToUsers something:string and rake db:migrate to test, then rake db:rollback to undo..but it all seems like it's worked so I probably my wouldn't mess with it too much.

Create a field in a table using Command Prompt *Ruby on Rails

How do I create a new field in an existing table using the Ruby command prompt?
I created the model (and migrated it) but I forgot to add a field - how would I go about this?
Generate a new migration to add a new column to table.
rails g migration add_column_name_to_table_name column_name:type
This will create a migration class like below:
#config/migration/20150304121554_add_column_name_to_table_name.rb
class AddColumnNameToTableName < ActiveRecord::Migration
def change
add_column :table_name, :column_name, :type
end
end
Here, column_name, table_name and type should be your desired name and type. Than run rake db:migrate command.
There are two ways to make changes in your situation:
Roll back the last migration
Add the new field in a new migration
Undoing the last migration should only be done if you have not yet pushed the migration to a public server. Here's how to do it:
Run rake db:rollback
Add the new field to the same migration file you originally used
Run rake db:migrate
Option 2:
To add the field in a new migration:
rails g migration AddFieldNameToTableName
For example, if your field is name and your table is users, you would run:
rails g migration AddNameToUsers
This will create a new migration file whose name starts with today's date and ends with add_name_to_users.rb. Open the file and add the field using the add_column command, like this:
class AddNameToUsers < ActiveRecord::Migration
def change
add_column :users, :name, :string
end
end
Save the file, then run rake db:migrate.
I encourage you to read the Rails migrations guide to learn more.

Rake db:migrate not ignoring old migrations?

Running through Michael Hartl's well known Rails tutorial, hit this snag.
I have this in a migration file, created by rails generate model etc:
class CreateUsers < ActiveRecord::Migration
def change
create_table :users do |t|
t.string :name
t.string :email
t.timestamps
end
end
end
Later, I added this second migration file:
class AddIndexToUsersEmail < ActiveRecord::Migration
def change
add_index :users, :email, unique: true
end
end
To try and update the database to include the new one, I followed the instructions and ran rake db:migrate, but this gives me an error telling me I'm trying to create a table that already exists, which is to say I'm clearly missing something.
Am I...supposed to delete the first migration? That wouldn't make any sense. What to do?
(These are the only files under db/migrate)
if you realy want to see what migrations have been ran into the database, you can inspect your app database, there is a table called schema_migrations, in there you can see the unique id of each migration as a row for example is your migration is called: 20130402190449_add_flagand_table.rb, you should see the number 20130402190449 as a row of that table, hope i gave you some guidance
What you can do is rollback couple of migration and re-run.
You can rollback migration like this
#rake db:rollback STEP=2
and then run
#rake db:migrate
Hope it should work
My issues was my 2nd to last migration ran and it was trying to rerun that migration again after i added a new migration.
I ended up just commenting out the code inside the one it was trying to rerun, and then ran rake db:migrate then uncommented the migration code.
This way the schema does not break and it fixes whatever bug occurred.

Adding a column through the terminal

How do you add a column to a table using ActiveRecord through the terminal. I am trying to use add_column method but its not working. Any ideas please?
It is better to write a migration and a must if you are working with a team. When you make db changes, then every developer's environment has to be updated also. Otherwise, you will have some mad developers at you.
rails generate migration AddPartNumberToProducts part_number:string
will generate
class AddPartNumberToProducts < ActiveRecord::Migration
def change
add_column :products, :part_number, :string
end
end
Then you run the migration
rake db:migrate
http://guides.rubyonrails.org/migrations.html
Edit:
For a rails console command line check #tadman's answer or use what Bengala proposed like
ActiveRecord::Migration.add_column :products, :part_number, :string
You can run migrations directly in rails console rails c with ActiveRecord::Migration
For your purpose the next command will do what you ask:
> ActiveRecord::Migration.add_column :table_name, :field_name, :field_type
If you're just hacking around, it's usually easier to manipulate the database using a SQLite client of some sorts than through the Rails DB layer.
If you're doing this for a project, create a proper migration file and run it.
If you're determined to do this, the add_column method is available through the ActiveRecord::Base.connection driver object.

Resources