Topic: I need help with routes.rb

I can't for the life of me figure this out, but because "i came down in the last shower" when it comes to programming its not suprising!

map.resources :orders do |map|
  map.resources :invoices
end

or

ActionController::Routing::Routes.draw do |map|
map.resources :orders, :invoices,

or anything i try, I will get this error;

undefined method `first' for :orders:Symbol

or this error;

undefined method `resources' for #<ActionController::Routing::RouteSet:0x32fce40>

I even downloaded the code for resful2 from the agile web development book and got the same error."undefined method `first' for :orders:Symbol"

Has anyone got some insight into this? Please!

Re: I need help with routes.rb

Did you install edge rails?

rake rails:freeze:edge

Also, you should pick a different name for the map in the block in your first code snippet. I think this will override the other map local variable. Something like:

map.resources :orders do |orders|
  orders.resources :invoices
end

Railscasts - Free Ruby on Rails Screencasts

Re: I need help with routes.rb

Ok thankyou.
I will try this.
edge rails? maybe the missing ingredient, i had no idea, thanks(:

Re: I need help with routes.rb

I recently switched to instant rails and it appears i dont have svn.


C:\InstantRails\rails_apps\track02>rake rails:freeze:edge
(in C:/InstantRails/rails_apps/track02)
C:/INSTAN~1/ruby/bin/rake.bat: No such file or directory - svn --version
ERROR: Must have subversion (svn) available in the PATH to lock this application
to Edge Rails
rake aborted!
exit
How do you install svn so that it's 'in the path'.

Re: I need help with routes.rb

I dont know RyanB. Everything i am reading on edge rails is a bit over my head at the moment.
I am learning how to program with ruby, most posts i have seen are people learning ruby who are already programmers.
All I am trying to acheive at the moment with my project is;

I have the relashionships right (i think). They work in the console.
such as i can create an object and then run say order.invoices << invoice  and the invoice then gets the order_id and order.invoices gives me the order, the customer, the invoice ect(brilliant-I love it!)
But,

How do i do this in the application, I want the user to be able to open an invoice and create lines for that particular invoice. The only way i know how to do this is with the select option in the view.

From my little experience i have found that the solution is usually simple but i havnt found it yet.  I thought the url should be something like invoice/1/invoice_lines/something and that is why i was on the routes.rb track but maybe i was on the wrong track.

Re: I need help with routes.rb

What you were attempting to do in the first post is called RESTful design. It is for creating special URLs and mapping certain actions to them. In other words, it only changes how the URLs are presented, not much more than that.

You don't need to use map.resources (which is only available in edge rails currently) to get the order.invoices << invoice ability. In fact, this doesn't have anything to do with the URL, it is all handled by ActiveRecord which is at a lower layer that doesn't even know what the URL of the page is.

If you have the has_many/belongs_to association set up for Invoice and InvoiceLine models then you are partly there. The next step is probably adding a controller action or two which adds the invoice line to an invoice. If you provide more details on how you want it to behave I may be able to provide some code.

Railscasts - Free Ruby on Rails Screencasts

Re: I need help with routes.rb

ok these are the models;
class Customer < ActiveRecord::Base
    has_many :invoices
    has_many :orders, :through => :invoices
   
    end

class Order < ActiveRecord::Base
    has_many :invoices
    has_many :customers, :through =>:invoices
   
      end
class Invoice < ActiveRecord::Base
    belongs_to :order
    belongs_to :customer
   
      has_many :invoice_items
      has_many :items, :through => :invoice_items
   
end
class InvoiceItem < ActiveRecord::Base
      belongs_to :item
      belongs_to :invoice
   end

class Item < ActiveRecord::Base
    has_many :invoice_items
    has_many :invoices, :through => :invoice_items
   
end

So for a_customer I would like to create an_order for a_customer and an_invoice. I think an_invoice would need to be saved regardless as invoice is the join model holding the id's of customer and order. Is this right?
But first things first I would like to know more simply how to create a new whatever @whatever.
So that for example when the user is at a_invoice and creates invoice_items they know they are for the invoice the user is at and the invoice_items inherit the id of the invoice.

Re: I need help with routes.rb

Thanks to your tutorial the app creates an associated invoice_item when an invoice is created.

I would like to create an order when a customer is created how do i do this with the :through =>association?

I would also like to know how to create a link to "create an order for this unique customer" .

Re: I need help with routes.rb

In order to create an order you will also need to create an invoice. Try this:

# in the view
<%= link_to 'create order', :action => 'create_order', :id => @customer %>

Assuming @customer is set, this will pass the customer's id to the action. You can use this to create an empty order/invoice and add it to the person. Like this:

def create_order
  @customer = Customer.find(params[:id])
  @invoice = @customer.invoices.create
  @invoice.order.create
  redirect_to #....
end

This will create an empty invoice and order for the given customer.

Last edited by ryanb (2006-11-06 13:01:05)

Railscasts - Free Ruby on Rails Screencasts

Re: I need help with routes.rb

Thankyou Ryan,
Im doing something wrong. The create_order action gives errors. If i create the invoice with the create customer action, that works but the the create_order link returns an error , undefined method "invoice". If i tell it to find the invoices it does but cant find the customer.
If i create a customer alone and then create_order i get the error, you have nil object when i didnt expect it well by now i usually do expect it! anyway 'nil.create' it told me.
The invoice table holds the id for customer and the order (the join model).
I tried various things but all with errors. So close yet so far!
Sorry for being such a spass!

Re: I need help with routes.rb

Did you try the code I gave above? What error do you get for that code? Make sure you are calling @customer.invoices.create (it needs to be plural).

Railscasts - Free Ruby on Rails Screencasts

Re: I need help with routes.rb

Yes,
def create_order
     @customer = Customer.find(params[:id])
     @invoice = @customer.invoices.create
     @invoice.order.create
     redirect_to :action => 'show', :id => @customer
end

the error for /customers/create_order/36
is nil object nil.create for the @invoice.order.create line.

Re: I need help with routes.rb

Oh, sorry, don't know what I was thinking. Try this:

@invoice.create_order

Railscasts - Free Ruby on Rails Screencasts

Re: I need help with routes.rb

Amazing, that does create an order and invoice but the order id doesnt populate the invoice join model.

Re: I need help with routes.rb

Oh, the invoice probably needs to be saved for the order_id column to be set:

@invoice = @customer.invoices.create
@invoice.create_order
@invoice.save

Actually this can all be done much simply with:

@customer.invoices.create!(:order => Order.create!)

Or if you are running Edge Rails (1.2):

@customer.orders << Order.create

I think that works anyway. Untested.

Railscasts - Free Ruby on Rails Screencasts

Re: I need help with routes.rb

Ryanb You are a ledgend!! Thankyou so much!
Now just one more question.
How do I show it all on one page??
I tried;

<% for invoice in @customer.invoices %>
<h1>This invoice is for <%= @customer.name %></h1>
<% end %>
and the error i get is nil object, nil.invoices
Thankyou I really appreciate all your help.

Re: I need help with routes.rb

You need to create the @customer instance variable in the controller action. For example, if you want it in the "show" action in your controller, you would do:

# in controller
def show
  @customer = Customer.find(params[:id])
end

# in show.rhtml
<% for invoice in @customer.invoices %>
  <h1>This invoice is for <%= @customer.name %></h1>
<% end %>

Railscasts - Free Ruby on Rails Screencasts

Re: I need help with routes.rb

yes i sort of new that but everything i tried didnt work. OMG im really hopeless at this.
The code you gave me i tried for the edit view as that is where i was sorry, should have said so.
I still got the same error of nil.invoices.
In the show veiw i got error couldnt find customer with id=88

Re: I need help with routes.rb

@invoices = @customer.invoices in the controller
Works! Yaaaah.
Thankyou so much!