Reputation: 14418
I'm working through Agile Web Development with Rails and having a problem with Task E and adding the payment types to a database. Within the orders table, there is a foreign key relating the column payment_type_id to the payment_types database (which holds columns id, label and value)
So, an order has a payment_type_id of 1, which corresponds to the entry in payment_types of "Credit Card", "cc"
class Order < ActiveRecord::Base
has_many :line_items
belongs_to :payment_types
class PaymentType < ActiveRecord::Base
has_one :order
Then within the Order controller
class OrdersController < ApplicationController
# GET /orders
# GET /orders.xml
def index
@orders = Order.all
And then in the index.html.erb view:
<% @orders.each do |order| %>
<tr>
<td><%=h order.name %></td>
<td><%=h order.payment_types.label %></td>
This gives the following error:
"You have a nil object when you didn't expect it! The error occurred while evaluating nil.label"
for the line order.payment_types.label
Do I have the relationships correct? The foreign key works elsewhere, when creating orders and everything. It's just in this view. Thanks so much for any help.
Upvotes: 0
Views: 195
Reputation: 9778
Side note: Your belongs_to :payment_types
should be belongs_to :payment_type
. You only have one payment type for any given order.
This will be because this specific order has no payment type (order.payment_types
is nil
).
To fix this, you can do:
<td><%=h order.payment_type.label if order.payment_type %></td>
or even
<td><%=h order.payment_type.try(:label) %></td>
which does much the same thing, but uses some rails kung-fu (some purists will whine about this as a code smell, but they can all stop whining and do something useful, like building a shed).
or you can set the payment type some how (possibly involving a more complex controller, and maybe a validates_presence_of :payment_type
in your Order
model.
Upvotes: 3