form_for with RESTful route calling the wrong action

Hi,

I am using RESTFUL routes with the following setup with a form_for tag, but instead of calling the :create action my form is calling the :new action. I have read and re-read the resources documentation, and I am confident that I have the right combination of paths, and posting methods, please take a look at this setup and let me know if I'm doing something stupid or if this is an error w/rails routing.

,----[environment.rb]

# Specifies gem version of Rails to use when vendor/rails is not present RAILS_GEM_VERSION = '2.1.0' unless defined? RAILS_GEM_VERSION

`----

,----[processing_service_levels/new.html.erb]

    <% form_for(:processing_service_levels, @level,                 :url => processing_service_level_path(@level),                 :html => { :method => :post}) do |f| %>

`----

,----[routes.rb]

  map.resources :processing_service_levels

`----

,----[processing_service_levels_controller.rb]

  # POST /processing_service_levels   # POST /processing_service_levels.xml   def create     @level = ProcessingServiceLevel.new(params[:id])     @level.process_hours = (Integer(params[:months]) * 30 * 24) +       (Integer(params[:days]) * 24) + Integer(params[:hours])     respond_to do |format|       if @level.save         flash[:notice] = 'Service level was successfully created.' ...

`----

,----[rendered html]

    <form action="/processing_service_levels/" method="post">     ... form stuff ...     <input name="commit" type="submit" value="Create" />

`----

I've restarted with web-server since adding the map.resources line to my routes. I've tried specifying the path using the old style

:url => {:controller => :processing_service_levels, :action => :create, :id => @level}

but with no success. I've googled, and searched the archives of this list, but I have had no success in finding out what's going wrong.

Please help me out!

Thanks -- Eric

inline...

Hi,

I am using RESTFUL routes with the following setup with a form_for tag, but instead of calling the :create action my form is calling the :new action. I have read and re-read the resources documentation, and I am confident that I have the right combination of paths, and posting methods, please take a look at this setup and let me know if I'm doing something stupid or if this is an error w/rails routing.

,----[environment.rb] > # Specifies gem version of Rails to use when vendor/rails is not present > RAILS_GEM_VERSION = '2.1.0' unless defined? RAILS_GEM_VERSION `----

What code do you have in your controller? It should be something like this:

class ProcessingServiceLevelsController < ApplicationController

  def new     @processing_service_level = ProcessingServiceLevel.new   end

end

,----[processing_service_levels/new.html.erb] > <% form_for(:processing_service_levels, @level, > :url => processing_service_level_path(@level), > :html => { :method => :post}) do |f| %> `----

Given the above controller code, you can use this instead:

<% form_for @processing_service_level do |f| %>

That should create a POST action to /processing_service_levels, which should call your create action.

Last resort, try restarting your web server (mongrel or webrick or whatever).

Jeff

purpleworkshops.coom

inline...

Jeff <cohen.jeff@gmail.com> writes:

inline...

Hi,

I am using RESTFUL routes with the following setup with a form_for tag, but instead of calling the :create action my form is calling the :new action. I have read and re-read the resources documentation, and I am confident that I have the right combination of paths, and posting methods, please take a look at this setup and let me know if I'm doing something stupid or if this is an error w/rails routing.

,----[environment.rb] > # Specifies gem version of Rails to use when vendor/rails is not present > RAILS_GEM_VERSION = '2.1.0' unless defined? RAILS_GEM_VERSION `----

What code do you have in your controller? It should be something like this:

class ProcessingServiceLevelsController < ApplicationController

  def new     @processing_service_level = ProcessingServiceLevel.new   end

end

the relevant methods in my processing_service_levels_controller.rb are

  # GET /processing_service_levels/new   # GET /processing_service_levels/new.xml   def new     @processing_service_level = ProcessingServiceLevel.new     @version = ProcessingServiceVersion.find(params[:version])     @parent = @version.processing_service     respond_to do |format|       format.html # new.html.erb       format.xml { render :json => @level }     end   end

  # POST /processing_service_levels   # POST /processing_service_levels.xml   def create     @level = ProcessingServiceLevel.new(params[:id])     @level.process_hours = (Integer(params[:months]) * 30 * 24) +       (Integer(params[:days]) * 24) + Integer(params[:hours])     respond_to do |format|       if @level.save         flash[:notice] = 'Service level was successfully created.'         format.html { redirect_to(:controller => :processing_service_versions,                                   :action => :show,                                   :id => @version,                                   :parent => @parent,                                   :level => @level) }         format.xml { render :json => @service, :status => :created, :location => @level }       else         format.html { render(:action => "new",                              :version => @level.processing_service_version,                              :parent => @level.processing_service_version.processing_service) }         format.xml { render :json => @level.errors, :status => :unprocessable_entity }       end     end   end

not that the create method has ever successfully been called :wink:

,----[processing_service_levels/new.html.erb] > <% form_for(:processing_service_levels, @level, > :url => processing_service_level_path(@level), > :html => { :method => :post}) do |f| %> `----

Given the above controller code, you can use this instead:

<% form_for @processing_service_level do |f| %>

I switched to the form_for argument you suggested, which renders to the following html

  <form action="/processing_service_levels" class="new_processing_service_level" id="new_processing_service_level" method="post">

> That should create a POST action to /processing_service_levels, which should call your create action.

Is there a way to inspect which method (put, post, get etc...) is being sent?

When I submit this form I am still directed to the processing_service_controllers/new action. I'm really not clear on what's going on, and why this one particular model has issues when all of my other models are working fine. Also the processing_service_levels/edit form is submitting to the edit actions instead of update.

Last resort, try restarting your web server (mongrel or webrick or whatever).

I've been restarting my web-server after almost every change.

Thanks for the advice, if you have any other ideas please let me know -- Eric

Are you sure it's just not being redirected? If the .save fails inside the create() action, it looks like the code will render the new form again - so perhaps it's been misleading?

Can you check the development.log, and see if the #create action is really ever getting called? At the end of the "Processing..." line in the log, you should see "[POST]" to confirm that the POST method is being used.

Sorry if you've already checked all this... just trying to think of what to try next.

Jeff

Jeff <cohen.jeff@gmail.com> writes:

Is there a way to inspect which method (put, post, get etc...) is being sent?

When I submit this form I am still directed to the processing_service_controllers/new action. I'm really not clear on what's going on, and why this one particular model has issues when all of my other models are working fine. Also the processing_service_levels/edit form is submitting to the edit actions instead of update.

Are you sure it's just not being redirected? If the .save fails inside the create() action, it looks like the code will render the new form again - so perhaps it's been misleading?

Can you check the development.log, and see if the #create action is really ever getting called? At the end of the "Processing..." line in the log, you should see "[POST]" to confirm that the POST method is being used.

Thank for the help Jeff,

I checked the logs, and immediately after rendering the processing_service_levels/new page, the next line is

Processing ProcessingServiceLevelsController#new (for 127.0.0.1 at 2008-10-07 13:55:32) [GET]

for more of the log see [1] below

which leads me to believe that the form is submitting directly to the new action using GET. I don't see how this could be the case given the raw html of the "new" page, unless maybe something is twisted inside of the rails routing...

I've also tried sticking error raising code in the from of the udpate action, but said code is never reached...

Thanks -- Eric

Sorry if you've already checked all this... just trying to think of what to try next.

Jeff

[1] ,----[development log]

Processing ProcessingServiceLevelsController#new (for 127.0.0.1 at 2008-10-07 13:55:25) [GET]   Session ID: f69ec3fdb850969c52d3e6173df8e72e   Parameters: {"action"=>"new", "version"=>"20", "controller"=>"processing_service_levels"}   User Columns (0.9ms) SHOW FIELDS FROM `users`   User Load (0.1ms) SELECT * FROM `users` WHERE (`users`.`id` = 5) LIMIT 1   ProcessingServiceLevel Columns (0.9ms) SHOW FIELDS FROM `processing_service_levels`   ProcessingServiceVersion Columns (0.8ms) SHOW FIELDS FROM `processing_service_versions`   ProcessingServiceVersion Load (0.1ms) SELECT * FROM `processing_service_versions` WHERE (`processing_service_versions`.`id` = 20)   ProcessingService Columns (0.8ms) SHOW FIELDS FROM `processing_services`   ProcessingService Load (0.1ms) SELECT * FROM `processing_services` WHERE (`processing_services`.`id` = 3) Rendering template within layouts/application Rendering processing_service_levels/new Rendered processing_services/_processing_service (3.7ms) Rendered processing_service_versions/_processing_service_version (3.7ms) Rendered processing_service_levels/_form (4.0ms) Rendered users/_user_bar (3.3ms) Completed in 130ms (View: 35, DB: 4) | 200 OK [http://localhost/processing_service_levels/new?version=20]

Processing ProcessingServiceLevelsController#new (for 127.0.0.1 at 2008-10-07 13:55:32) [GET]   Session ID: f69ec3fdb850969c52d3e6173df8e72e   Parameters: {"month"=>"0", "commit"=>"Create", "processing_service_level"=>{"name"=>"Nothing", "description"=>"Nothing", "processing_service_version_id"=>"20"}, "hour"=>"0", "authenticity_token"=>***, "action"=>"new", "day"=>"0", "controller"=>"processing_service_levels"}   User Columns (1.1ms) SHOW FIELDS FROM `users`   User Load (0.1ms) SELECT * FROM `users` WHERE (`users`.`id` = 5) LIMIT 1   ProcessingServiceLevel Columns (1.1ms) SHOW FIELDS FROM `processing_service_levels`

`----

Could your browser cache be screwing with you maybe? Any difference if you switch to a different browser?

My bad,

it looks like the creation form was nested inside of empty <form></form> tags. These surrounding tags, must have been what was breaking the submit action to GET rather than POST. I removed these tags and it appears to be working.

Thanks for the help! Sorry about the noise -- Eric

"Eric Schulte" <schulte.eric@gmail.com> writes: