Migration --- creating database tables
READ ruby guide on migrations here
migrations = way in RoR to alter database schema over time
i.e. in RubyMine: Tools-> Run Rails Generator -> model
>>> give it the name User (in this example)
it will generate a file under app/models/model_name.rb AND also a db/migrate/****_model_name.rb file
Here is example when name of model is User
SUPPOSE you have created a model called User it will create the following file for you. Edit it as shown in red to add code to create the corresponding database table.
db/migrate/20090215220309_create_students.rb:
class CreateUsers < ActiveRecord::Migration
def change
create_table :students do |t|
t.column :first_name, :string
t.column :last_name, :string
end
end
end
HERE IS A DIFFERENT example for a Model Student
db/migrate/20090215220309_create_students.rb:
class CreateStudents < ActiveRecord::Migration
def change
create_table :students do |t|
t.column :name, :string
t.column :birth, :date
t.column :gpa, :float
t.column :grad, :integer
end
end
end
OPTIONAL!!!!! Here there is a file load_data.rb that contains some initial data you want to load
COMMAND LINE: rails generate migration load_data
RubyMine IDE: Tools-> Run Rails Generator -> migration (then give the name load_data)
Example of a load_data.rb file
class LoadData < ActiveRecord::Migration def up # Create initial users. down jb = User.new(:first_name => "Justin", :last_name => "Bieber") jb.save(:validate => false) ph = User.new(:first_name => "Paris", :last_name => "Hilton") ph.save(:validate => false) mc = User.new(:first_name => "Miley", :last_name => "Cyrus") mc.save(:validate => false) bo = User.new(:first_name => "Barack", :last_name => "Obama") bo.save(:validate => false) sc = User.new(:first_name => "Santa", :last_name => "Claus") sc.save(:validate => false) jo = User.new(:first_name => "John", :last_name => "Ousterhout") jo.save(:validate => false)
end
def down User.delete_all end end
|
COMMAND LINE: rake db:migrate RubyMine IDE: Tools->Run Rake Task -> db:migrate
Following our example of ---this generates the following database table named:
users
primary key |
string |
string |
By default, create_table will create a primary key called id.
You can change the name of the primary key with the :primary_key option (don't forget to update the corresponding model)
If we had done the optional load_data file seen above this would be the contents of the users database
1 |
Justin |
Bieber |
2 |
Paris |
Hilton |
3 |
Miley |
Cyrus |
4 |
Barack |
Obama |
5 |
Santa |
Claus |
6 |
John |
Ousterhout |
SPECIAL WORD About the schema that is ALSO GENERATED when you perform migrations
From RoR guide:
What are Schema Files for? (YOU DONT EDIT THEM!!!!!)
Migrations, mighty as they may be, are not the authoritative source for your database schema. That role falls to either db/schema.rb or an SQL file which Active Record generates by examining the database. They are not designed to be edited, they just represent the current state of the database.
There is no need (and it is error prone) to deploy a new instance of an app by replaying the entire migration history. It is much simpler and faster to just load into the database a description of the current schema.
For example, this is how the test database is created: the current development database is dumped (either to db/schema.rb or db/structure.sql) and then loaded into the test database.
Schema files are also useful if you want a quick look at what attributes an Active Record object has. This information is not in the model's code and is frequently spread across several migrations, but the information is nicely summed up in the schema file. The annotate_models gem automatically adds and updates comments at the top of each model summarizing the schema if you desire that functionality.
Because schema dumps are the authoritative source for your database schema, it is strongly recommended that you check them into source control.
db/schema.rb contains the current version number of the database. This ensures conflicts are going to happen in the case of a merge where both branches touched the schema. When that happens, solve conflicts manually, keeping the highest version number of the two.
|
Example schema.rb file created from above
ActiveRecord::Schema.define(version: 20150105235326) do
create_table "users", force: :cascade do |t| t.string "first_name" t.string "last_name" end
end
|
SPECIAL WORD About Changing Migration file and rerunning---create a new one instead
"You should always create a new migration file when adding/changing something in the database. This is the purpose of migrations."
From RoR guide:
Occasionally you will make a mistake when writing a migration. If you have already run the migration then you cannot just edit the migration and run the migration again: Rails thinks it has already run the migration and so will do nothing when you run rake db:migrate. You must rollback the migration (for example with rake db:rollback), edit your migration and then run rake db:migrate to run the corrected version.
In general, editing existing migrations is not a good idea. You will be creating extra work for yourself and your co-workers and cause major headaches if the existing version of the migration has already been run on production machines. Instead, you should write a new migration that performs the changes you require. Editing a freshly generated migration that has not yet been committed to source control (or, more generally, which has not been propagated beyond your development machine) is relatively harmless.
The revert method can be helpful when writing a new migration to undo previous migrations in whole or in part (see Reverting Previous Migrations above).
|
NOT a suggestion but on the command line there is a
db:migrate:redo
and
rake db:schema:dump
|
Quickly generate new migrations file to add say a new column in a table
rails generate migration add_columnname_to_tablename
example
rails generate migration add_gpa_to_students |
edit the generated database migration file autogenerated for you in step 1 to add code to create table but ADD the timestamp
The timestamps macro adds two columns, created_at and updated_at.
- Both will be of the data type datetime.
- These special columns are automatically managed by Active Record if they exist. Ofcourse editing by hand requires input
|
SUPPOSE you have created a model called Student it will create the following file for you. Edit it as shown in red to add code to create the corresponding database table.
db/migrate/20090215220309_create_students.rb:
class CreateStudents < ActiveRecord::Migration
def change
create_table :students do |t|
t.column :name, :string
t.column :birth, :date
t.column :gpa, :float
t.column :grad, :integer
t.timestamps null: false
end
end
end
This generates the following database table named:
students
primary key |
string |
date |
float |
integer |
datetime
(e.g. 2015-01-06 00:52:29.375922) |
datetime |
|