Rails 4嵌套表格不能通过参数中的嵌套属性
当我提交表单时,它在参数中传递{"utf8"=>"✓", "authenticity_token"=>"blah", "client"=>{"first_name"=>"jack", "last_name"=>"kool","complaints"=>{"symptom"=>"burnt"}
并且我得到Unpermitted Parameters: complaints
由于投诉嵌套在客户端中,因此它应该通过complaints_attributes
,就像我在其中设置的一样强烈的参数,我不明白为什么它不是。Rails 4嵌套表格不能通过参数中的嵌套属性
class ClientsController < ApplicationController
def new
@client = Client.new
end
def edit
@client = Client.find(params[:id])
end
def create
@client = Client.new(client_params)
if @client.save
redirect_to @client
else
render 'new'
end
end
def update
@client = Client.find(params[:id])
if @client.update(client_params)
redirect_to @client
else
render 'edit'
end
end
private
def client_params
params.require(:client).permit(:first_name, :last_name, complaints_attributes: [ :symptom, :id ])
end
end
客户端模式:
class Client < ActiveRecord::Base
has_many :complaints
has_one :personal_disease_history
has_one :family_disease_history
has_many :surgeries
has_many :hospitalizations
has_many :medications
has_many :allergies
validates :first_name, :last_name, presence: true
accepts_nested_attributes_for :complaints
end
投诉型号:
class Complaint < ActiveRecord::Base
belongs_to :client
end
形式:
<%= form_for :client, url: clients_path, html: { class: "form-inline" } do |f| %>
<div class="panel panel-success">
<div class="panel-heading">
<h3 class="panel-title">Health History Form</h3>
</div>
<div class="panel-body">
<div class="form-blocks"><legend>Name</legend>
<div class="form-group">
<%= f.label :first_name, class: "sr-only" %>
<%= f.text_field :first_name, class: "form-control", placeholder: "First Name" %>
</div>
<div class="form-group">
<%= f.label :last_name, class: "sr-only" %>
<%= f.text_field :last_name, class: "form-control", placeholder: "Last Name" %>
</div>
</div>
<div class="form-blocks"><legend>Complaints</legend>
<div class="form-group">
<%= f.fields_for :complaints do |builder| %>
<%= builder.label :symptom, class: "sr-only" %>
<%= builder.text_field :symptom, class: "form-control", placeholder: "Symptom" %>
<% end %>
</div>
</div>
<div>
<%= f.submit "Submit Form", class: "btn btn-primary btn-lg"%>
</div>
<% end %>
,试着说这里面的,如果@ client.save:
Complaint.create(symptom: params[
"client"]["complaints"]["symptom"], client_id: @client.id)
在未经许可的参数与嵌套的属性问题,但是这应该获得实际的记录保存。如果不这样做,请发布围绕提交的堆栈跟踪。
有一些其他的想法:但(1)你在被允许的params中有了complaint_attributes,但是你可以改变它到bc,这就是params中的内容。
这实际上是有效的,但正如你所说,它似乎hacky。由于params不在私有的'client_params'方法中,这种方法是否也会打开安全漏洞?任何想法使它不那么hacky?无论如何,感谢您的帮助。 – rymcmahon
@rymcmahon如果有效,请接受答案:)为了减少黑客行为,你可以尝试像嵌套属性一样使用它。你的form_for可能需要传递两个对象。很难解释,但像form_for [:client,:complaint]而不是form_for:client。 – toddmetheny
我发现了一个不太好用的解决方案。我改变了''to''并将'@ client.complaints.build'添加到客户端的新操作中。感谢领先。 – rymcmahon
您需要build
的客户端控制器内创建操作关联的模型以及
def new
@client = Client.new
@client.complaints.build
end
添加'@ client.complaints.build'不会改变行为。仍然得到'不允许的参考:投诉' – rymcmahon
在控制器中,尝试用'.build'建立你的Client模型,而不是调用'.new'。这应该将相关的投诉建立到客户端上。 –
如果这样做不起作用,那么临时解决办法就是在您的客户控制器内部创建一个Complaint.create(params [“complaints”])行为。 – toddmetheny
@harishsr添加'.build'代替'.new'会产生一个没有方法的错误 – rymcmahon