params[:fu] #4 ) Use the magical <association_name>_ids=([...array of ids]) association proxy method.
In the last blog entry, we looked at an example of having to build a new parent model and build its join models all in two lines of code. But if you are trying to just assign a list of has_many or has_and_belongs_to_many models, you don't have to use the fields_for and index trick. You can just use an association proxy method. Let's check it out:
class Reader < ActiveRecord::Base
has_and_belongs_to_many :blogs
end
<% form_for @reader do |f| %>
<%= f.text_field :name %>
<%= f.collection_select :blog_ids, Blog.find(:all), :id, :name, {}, :multiple => true %>
<%= f.submit 'Create' %>
<% end %>
generates:
<select id="reader_blog_ids" multiple="multiple" name="reader[blog_ids][]">
<option value="1">Martin Fowler</option>
<option value="2">Stephen Chu</option>
</select>
Processing ReadersController#create (for 127.0.0.1 at 2008-01-14 21:12:56) [POST]
Parameters: { "commit" => "Create",
"reader" => { "name" => "stephen chu"
"blog_ids" => ["1", "2"] },
"authenticity_token" => "238ba79b8282882ba01d840352616c2cc79280f0",
"action" => "create",
"controller" => "readers" }
And now, in my controller action, the creation of the reader only takes one line of code:
def create
@reader = Reader.new(params[:reader])
... thanks to the following has_many (or habtm) association assignment method:
@reader.blog_ids = [...many ids...]
So, stop doing any more params-munging code in your controller action like these:
def create
...
params[:blog_ids].each do |id|
@reader.blogs << Blog.find(id)
end
end
Get on the Rails bandwagon!
3 comments:
Just a note that this does not work if your association is a has_many :through type. At least, that is what the docs say.
Hi, first, thanks for all those great tips. However, I am trying to figure out how to solve a "similar" problem.
I want to create many entries in a join table by selecting multiple elements in a select helper.
I am stuck with at least 2 problems:
1)Only one type of value can be in the select helper, either one of the non-join tables ids
2)I am not even able to recuperate the ids which are clearly sent to the server formatted like this (Parameters: { "other stuff" ,"record"=>{"period_id"=>["996332878", "996332879"]}}
Any suggestions would be greatly appreciated.
thanks!
Thanks a lot for this blog post! I totally missed the "*_ids" assignment method and it's making things so easy now :)
Post a Comment