Advanced Rails - Building Industrial-Strength Web Apps in Record Time

(Tuis.) #1
What Is REST? | 201

DELETE /carts/4) are traditionally routed through the same controller. The third type,
line items, will be routed through a controller nested under the first controller.


First, we write the models corresponding to the newly createdCartandLineItem
resource types. Following Rails conventions, we will store these in the database using
ActiveRecord:


app/models/cart.rb
class Cart < ActiveRecord::Base


delete line items on cart destroy


has_many :line_items, :dependent => :destroy


def add_product(product_id, quantity)
quantity ||= 1
li = line_items.find_or_create_by_product_id(product_id.to_i)
# Increment the line item's quantity by the provided number.
LineItem.update_counters li.id, :quantity => quantity
end

def update_quantity(product_id, quantity)
li = line_items.find_by_product_id(product_id.to_i)
li.update_attributes! :quantity => quantity
end
end

TheActiveRecord::Base.update_countersmethod generates one SQL
query to update an integer field with the provided delta (positive or
negative). This avoids two SQL queries (findandupdate) in favor of
more expressive code like this:
LineItem.update_counters 3, :quantity => -1
>> UPDATE line_items SET quantity = quantity – 1 WHERE id = 3

app/models/line_item.rb
class LineItem < ActiveRecord::Base
belongs_to :cart
belongs_to :product


# Fields:
# cart_id integer
# product_id integer
# quantity integer default(0)
end

The structure of the ActiveRecord models parallels our resource architecture. We define
two instance methods onCart,add_product(which addsquantitycopies of the product
to the cart) andupdate_quantity(which sets the quantity of the existing product in the
cart to the providedquantity). The cart is emptied by deleting theCartobject (which
destroys it and its dependentLineItems, thanks to the:dependent => :destroydirective
onhas_many). Similarly, an item is removed from the cart simply by destroying its corre-
spondingLineItem.

Free download pdf