Ruby On Rails
Ruby On Rails
Part-1
✔
Migrations
✔
Active Record
Part -2
✔
Associations
✔
Validations
✔
Callbacks
Part -3
✔
Testing
Migrations
What is migration?
•
iteratively improving schema
•
keep things synchronized
Auto generated migrations
def self.down
drop_table :products
end
end
self.up / self.down
Creating a Standalone
Migration
def self.down
remove_column :products, :part_number
end
end
rake db:migrate
also invokes the db:schema:dump task
schema_migrations table
Other Transformations
Creating a table
def self.up
create_table :people do |t|
t.string :username, :null => false
t.string :fname,lname
t.text :notes
t.timestamps
end
end
def self.down
drop_table :people
end
More transformations
drop_table table_name
More...
rake db:rollback
mapping class names to table names.
pluralized table names.
integer primary keys.
classname_id as foreign keys.
Why Active Record
for simplicity and ease of use
hides low level implementation
The Basics
Select * from people where id='2'
class Person < ActiveRecord::Base
limit='1'
end
person=Person.find(2)
find method
Examples:
User.find(23)
User.find(:first)
User.find(:all, :offset => 10, :limit => 10)
User.find(:first).articles
Find :select
Why this ?
Find: Order By
person = Person.find_by_fname("mohit")
all_mohit = Person.find_all_by_fname("mohit")
person =
Person.find_by_fname_and_lname("mohit",”jain”)
Creating a new record
user = User.new
user.name = "David"
user.occupation = "Code Artist“
user.save
OR
OR
OR
person= Person.find(123)
person.name = "mohit”
person.save
OR
Person.delete(123)
OR
person = Person.find_by_name("Mohit")
person.destroy
Named and Anonymous Scopes
Named scope
Organization.active
Organization.active.people
Named scope example 2
orders = Orders.last_n_days(7)
orders = Orders.checks.last_n_days(7)
Anonymous scopes
in_house.checks.last_n_days(7)
Thank You.
Associations
Types of associations
➢
belongs_to
➢
has_one
➢
has_many
➢
has_many :through
➢
has_one :through
➢
has_and_belongs_to_many
Whats the need?
Comparison: without and with
class Customer < ActiveRecord::Base
end
OR
has_many :orders
and
has_one :order
has_many :through
has_and_belongs_to_many
has_and_belongs_to_many vs has_many :through
has_and_belongs_to_many
Stories can belong to many categories. Categories can have many stories.
Categories_Stories Table
story_id | category_id
Subscriptions Table
person_id | magazine_id | subscription_type |
subscription_length | subscription_date
Many to many
has_one :through
has_one:through*
continue...
When things get saved (continue)
order = Order.find(some_id)
an_invoice = Invoice.new(...)
order.invoice = an_invoice # invoice gets saved
continue...
When things get saved (continue)
order = Order.new(...)
an_invoice.order = order # Order will not be saved here
an_invoice.save # both the invoice and the order get saved
Validations
Validation Helpers
validates_acceptance_of
validates_confirmation_of
validates_length_of
validates_numericality_of
validates_presence_of
Example of validator helper
validates_uniqueness_of :name,
:on => :create,
:message => "is already used"
end
When Does Validation Happen?
new_record?
instance method
Method triggers validations
* create
* create!
* save
* save!
* update
* update_attributes
* update_attributes!
Method skips validations
* update_all
* update_attribute
* update_counters
* save(false)
valid? and invalid?
Validation Errors
errors.add_to_base
errors.add
errors.clear
errors.size
Displaying Validation Errors
error_messages
error_messages_for
Showing error message
1.Instance method
2.Handlers
callback as instance method
end
Callbacks as handlers
before_save:normalize_credit_card
protected
def normalize_credit_card
#......
end
end
Observers
●
Same as callbacks
●
It's about separation of concerns.
●
factor out code that doesn't really belong in
models
class OrderObserver < ActiveRecord::Observer
observe Order
end
Instantiating Observers
config.active_record.observers= :order_observer
( in environment.rb )
Thank you
Testing
Testing type
1. Unit
2. Functional
3. Integration
Unit testing?
What and why
rake db:test:prepare
copy the schema
rake test:units
1.copies the schema
2. runs all the tests in the test/unit
Test file?
require 'test_helper'
product.price = 0
assert !product.valid?
assert_equal "should be at least 0.01" , product.errors.on(:price)
product.price = 1
assert product.valid?
end
Fixtures
sample data
YAML fixtures
ruby_book:
title: Programming Ruby
description: Dummy description
price: 1234
image_url: ruby.png
rails_book:
title: Agile Web Development with Rails
description: Dummy description
price: 2345
image_url: rails.png
Naming convention & usage
fixtures :products
Mention this in the ProductTest class
:products => name of table and YML file
Fixture loading
➢
assert( boolean, [msg] )
➢
assert_equal( obj1, obj2, [msg] )
➢
assert_not_equal( obj1, obj2, [msg] )
➢
assert_same( obj1, obj2, [msg] )
➢
assert_instance_of( class, obj, [msg] )
Thank you
WEB v2.0