所以我正在重新编写/升级使用基于此专业Railscast http://railscasts.com/episodes/403-dynamic-forms的动态字段的3.0应用程序。
加载动态字段的方式是通过以下代码:
<%= f.hidden_field :tour_type_id %>
<%= f.fields_for :options, OpenStruct.new(@trip.options) do |builder| %>
<% @trip.tour_type.type_fields.where(:variable => false).each do |field| %>
<%= render "type_fields", field: field, f: builder %>
<% end %>
<% end %>
这正确地渲染了html。
当我通过控制台执行创建时,我传入的哈希:选项正确保存。但是,当我通过表单提交值时,它会将哈希值保存为nil。
我在想这可能是因为我在控制器中有强烈的参数。
def trip_params
params.require(:trip).permit(:options => {:id => :value})
end
我也试过
def trip_params
params.require(:trip).permit(:options => {})
end
params在rails服务器日志中看起来没问题,但是在更新发生之前,选项的值被设置为nil
Processing by TripsController#update as HTML
Parameters: {"utf8"=>"✓", "authenticity_token"=>"...", "trip"=>{"options"=>{"1"=>"400"}}, "commit"=>"Update Trip", "id"=>"1"}
SQL (1.0ms) UPDATE "trips" SET "updated_at" = $1, "options" = $2 WHERE "trips"."id" = 1 [["updated_at", Mon, 26 Aug 2013 05:13:35 UTC +00:00], ["options", "--- !ruby/hash:ActionController::Parameters\n'1': \n"]]
我还将序列化操作添加到模型
class Trip < ActiveRecord::Base
serialize :options, Hash
end
我真的不知道为什么这个代码在Rails v 4,Ruby V 1.9.3中不起作用。
此代码以动态表单RailsCast为模型。
编辑:
我尝试了此处列出的解决方案http://guides.rubyonrails.org/action_controller_overview.html#outside-the-scope-of-strong-parameters
def trip_params
params.require(:trip).permit(
:admin_name,
:brochure_title,
:description,
:organized_by,
:start_date,
:end_date,
:tour_type_id,
:pay_by,
:extension
).tap do |whitelisted|
whitelisted[:options] = params[:trip][:options]
end
end
我现在得到一个未找到的参数:选项错误。
答案 0 :(得分:0)
似乎strong_parameters
不支持允许使用任意键进行哈希,我认为这是有充分理由的......
在rails github repo上建议了一个解决方案:https://github.com/rails/rails/issues/9454#issuecomment-14167664和 RailsGuides http://guides.rubyonrails.org/action_controller_overview.html#outside-the-scope-of-strong-parameters
对于你的情况,它会是这样的
params.require(:trip).permit(:foo, :bar, :baz).tap do |whitelisted|
whitelisted[:options] = params[:trip][:options]
end
如果options
是Trip
的唯一属性,那么就像
params.require(:trip).permit!