Controller Problem

I have this action in questions_controller.rb :

def arg
@questions = Question.find(:all)

respond_to do |format|
format.html
format.xml { render :xml => @questions }
end
end

Why this action doesn’t work ?
It is the same as index action, but this one doesn’t work.
The error is: “Couldn’t find Question with ID=arg”

The error is: “Couldn’t find Question with ID=arg”

What’s the url that is supposed to be invoking the arg action?

What do your routes look like?

rake routes >routes.lst

then browse that file to see the routes that are available

it seems that ‘arg’ is being interpreted as an id parameter for an
existing route…

if you want arg as an action for the whole collection, then I’d expect
to see something like

map.resources :questions, :collection => {:arg => :get}

in routes.rb to add that as a recognized route

If it’s for a specific question, then

map.resources :questions, :member => {:arg => :get}

What’s the url that is supposed to be invoking the arg action?

http://localhost:3000/questions/arg

if you want arg as an action for the whole collection, then I’d expect
to see something like

map.resources :questions, :collection => {:arg => :get}

That way it works. But can you explain me the reason ?
What’s the meaning of the parameter :collection => {:arg => :get} ?

Every time i create a new action, I have to update the routes.rb file ??

Davide S. wrote:

What’s the url that is supposed to be invoking the arg action?

http://localhost:3000/questions/arg

if you want arg as an action for the whole collection, then I’d expect
to see something like

map.resources :questions, :collection => {:arg => :get}

That way it works. But can you explain me the reason ?
What’s the meaning of the parameter :collection => {:arg => :get} ?

Every time i create a new action, I have to update the routes.rb file ??

That is true, yes. The RESTful design methodology requires you to define
custom actions in your routes file. That is because earlier when we used
map.connect ‘:controller/:action/:id’ we always used the GET method -
for the destroy, create and update actions.

Then someone found out that you could make the urls prettier (and
respect the RESTful design philosophy) by using other standard HTTP
methods like DELETE, POST and PUT. Therefore you have to actually tell
Rails what method you’ld like to use, it will not use GET by default.
That is actually good. Imagine having half of your custom actions being
using the GET method, the other half using the POST, PUT or DELETE
method. Then you’ld need to define what method to use for half of them
in your routes file (instead of all of them). What a mess… (:

That is true, yes. The RESTful design methodology requires you to define
custom actions in your routes file. That is because earlier when we used
map.connect ‘:controller/:action/:id’ we always used the GET method -
for the destroy, create and update actions.

Then someone found out that you could make the urls prettier (and
respect the RESTful design philosophy) by using other standard HTTP
methods like DELETE, POST and PUT. Therefore you have to actually tell
Rails what method you’ld like to use, it will not use GET by default.
That is actually good. Imagine having half of your custom actions being
using the GET method, the other half using the POST, PUT or DELETE
method. Then you’ld need to define what method to use for half of them
in your routes file (instead of all of them). What a mess… (:

So, if i don’t specify a method (as we did), the default one would be
POST ??
Or DELETE ??
Or PUT ??

Which one ??

Davide S. wrote:

That is true, yes.

So, if i don’t specify a method (as we did), the default one would be
POST ??
Or DELETE ??
Or PUT ??

Which one ??

Sorry for being a little unclear but this was my point: Rails will NOT
try to guess which method you want and there is no default. In other
words, since we don’t only use GET now, we have to tell Rails which one
to use (no matter if it’s GET, POST, PUT or DELETE).

map.resources :questions, :collection => {:arg => :get}

In the example above we pass an option called :collection that specifies
which custom actions that is going to affect a collection of (in your
case) questions. Then we define one custom action (“arg”) that is going
to use the GET method. See the point? :arg => :get

The collection option accepts a hash with action name as key and method
name (GET, POST, PUT, DELETE) as value, so there is no default. Also
remember that if you want to make an action that is only going to affect
one question you’ll want to use the :member option instead, like this:

map.resources :questions, :collection => {:arg => :get}, :member =>
{:affecting_one_question => :get}

Hope that helped. (:

That way it works. But can you explain me the reason ?
What’s the meaning of the parameter :collection => {:arg => :get} ?

Every time i create a new action, I have to update the routes.rb file ??

http://api.rubyonrails.org/classes/ActionController/Resources.html