我在将嵌套模型中的数据添加到数据库时遇到问题。
我有一个与Monster模型有以下关系的Photo模型。我能够为怪物添加和删除我的嵌套表单,但无法弄清楚如何在更新我的照片时实际添加新的Monster对象。这是基于http://railscasts.com/episodes/196-nested-model-form-revised示例中的1个嵌套级别表单,基本上是调查 - 问题关系。
class Photo < ActiveRecord::Base
attr_accessible :title, :monsters_attributes
has_and_belongs_to_many :monsters
accepts_nested_attributes_for :monsters, allow_destroy: true
end
class Monster < ActiveRecord::Base
attr_accessible :first_name, :last_name, :selected
has_and_belongs_to_many :photos
end
我确定问题出现在我的photos_controller中,而且我对如何使用更新照片表单时提交的参数的理解不足。在提交带有两个怪物的编辑照片表格时,我得到以下参数。第一个已经关联,第二个是我试图通过点击“添加怪物”链接,输入名字和姓氏,并提交表单来宣布。
“添加怪物”链接在我的_form.html.erb文件中为Photo定义,我使用partial来渲染字段。辅助函数在application_helper.rb中声明。
…
<!-- this uses the _monster_fields partial -->
<%= f.fields_for :monsters do |builder| %>
<%= render 'monster_fields', f: builder %>
<% end %>
</table>
<%= link_to_add_fields "Add Monster", f, :monsters %>
...
application_helper.rb
module ApplicationHelper
def link_to_add_fields(name, f, association)
new_object = f.object.send(association).klass.new # make instance of monster association record, Monster.new
id = new_object.object_id # get id of new monster object, id = Monster.new.object_id
fields = f.fields_for(association, new_object, child_index: id) do |builder|
render(association.to_s.singularize + "_fields", f: builder) # render partial _monster_fields.html.erb
end
link_to(name, "#", class: "add_fields", data: {id: id, fields: fields.gsub("\n", '
')}) # returns a link
end
end
{
"utf8"=>"✓",
"_method"=>"put",
"authenticity_token"=>"8dYkFrzdkulBv8YrZCHU2wfFh4v5LQc9q/JWPmsbDkc=",
"photo"=>{"title"=>"Family Gathering",
"monsters_attributes"=>{
"0"=>{"first_name"=>"Franken", "last_name"=>"Stein", "_destroy"=>"false", "id"=>"1"},
"1358291763102"=>{"first_name"=>"Ware", "last_name"=>"Wolf", "_destroy"=>"false"}
},
"monster_ids"=>"1"
},
"commit"=>"Update Photo",
"action"=>"update",
"controller"=>"photos",
"id"=>"1"
}
在我的applcation.js文件中,我定义了如何处理字段的添加和删除。在.add_fields中,该示例使用我新创建的对象的id,但是我没有看到如何在怪物表中保存我新创建的怪物。
$(document).ready(function() {
$('form').on('click', '.remove_fields', function(event) {
$(this).prev('input[type=hidden]').val('1');
$(this).closest('tr').hide();
event.preventDefault();
});
$('form').on('click', '.add_fields', function(event) {
time = new Date().getTime();
regexp = new RegExp($(this).data('id'), 'g');
$(this).before($(this).data('fields').replace(regexp, time))
event.preventDefault();
});
});
总的来说,这是一个非常简单的过程,但我不确定如何在我的照片编辑视图中实际保存一个新的Monster(创建一个新的活动记录对象)。
我可以使用多对多关系遇到问题吗?
来自railscasts的例子很好,但它并没有那么远。我很感激有人可能提供的帮助。
http://railscasts.com/episodes/196-nested-model-form-revised
ActiveModel :: MassAssignmentSecurity :: PhotosController中的错误#update
无法批量分配受保护的属性:monster_ids
app / controllers / photos_controller.rb:76:block in update'
app/controllers/photos_controller.rb:75:in
更新'
{"utf8"=>"✓",
"_method"=>"put",
"authenticity_token"=>"1l62Sged52hnEHQoj0WPf/asRjcIpIKBBzsb7gVDRm0=",
"photo"=>{"title"=>"Family Gathering",
"monsters_attributes"=>{"0"=>{"first_name"=>"Franken",
"last_name"=>"Stein",
"_destroy"=>"false",
"id"=>"1"},
"1358356969634"=>{"first_name"=>"Scary",
"last_name"=>"Frank",
"_destroy"=>"false"}},
"monster_ids"=>"1"},
"commit"=>"Update Photo",
"id"=>"1"}
答案 0 :(得分:0)
嵌套属性的美妙之处在于,对控制器代码的影响是不存在的。你可以继续做
photo.update_attributes params[:photo]
将根据需要更新和删除怪物:update_attributes将使用photo.monsters_attributes=
中的数据调用params[:photo][:monsters_attributes]
。调用accepts_nested_attributes_for
将(除其他外)创建一个合适的monsters_attributes=
方法