Rails 4.1 Nested Attributes and Fields For Getting Unpermitted Parameters and Not Saving

笑着哭i 提交于 2019-12-24 00:55:44

问题


Research: Rails 4.0 beta, fields_for not accepting pluralized model_name in one-to-many association, Rails 4 Nested Attributes with fields_for Don't Save to Database

First, let's get the most common problem out of the way: incorrectly named attributes parameters for strong parameters. Mine is correctly plural.

class AdultsController < ApplicationController
...
  def update
    authorize @user
    respond_to do |format|
      if @user.update_attributes(user_params)
        format.html { redirect_to unit_adult_path(@unit, @user), notice: "#{@user.full_name} was successfully updated." }
      else
        format.html { render action: 'edit' }
      end
    end
  end

  def user_params
    params.require(:adult).permit(:first_name, :last_name, phones_attributes: [])
  end
end

And my models are setup correctly

class User < ActiveRecord::Base
  has_many :phones, dependent: :destroy
  accepts_nested_attributes_for :phones, allow_destroy: true, reject_if: proc { |a| a["number"].blank? }
end

class Phone < ActiveRecord::Base
  belongs_to :user, touch: true
end

And the view

# adult/_form.html.haml
= bootstrap_form_for [@unit, @user] do |f|
  = f.text_field :first_name, control_col: 'col-md-4'
  = f.text_field :last_name, control_col: 'col-md-4'

  = f.fields_for :phones do |f_phone|
    = f_phone.form_group do
      = f_phone.select :kind, options_for_phones, hide_label: true, layout: :default
      = f_phone.phone_field :number, hide_label: true, layout: :default
      = f_phone.check_box :_destroy, label: 'remove'

But, when I submit the User form to save

Started PATCH "/units/2/adults/1" for 127.0.0.1 at 2014-07-11 15:20:17 -0700
Processing by AdultsController#update as HTML
  Parameters: {"utf8"=>"✓", "authenticity_token"=>"pDjDVSiEs5qqHLqnbxQMeGWDOUGvhXPPvgyRGmitmps=", "adult"=>{"first_name"=>"Karl", "last_name"=>"Smith", "phones_attributes"=>{"0"=>{"kind"=>"other", "number"=>"888.1212", "_destroy"=>"0", "id"=>"173"}, "1"=>{"kind"=>"mobile", "number"=>"888.1212", "_destroy"=>"0", "id"=>"174"}} }, "commit"=>"Update Adult", "unit_id"=>"2", "id"=>"1"}

Unpermitted parameters: phones_attributes

I don't understand why the nested data is being rejected by the strong parameter evaluation. It looks correct to me.

The one thing I do notice is that the params data for "phones_attributes" value is a HASH not an ARRAY. In the user_params, phones_attributes: [] looks like it expecting an ARRAY. So I changed it to a HASH.

  def user_params
    params.require(:adult).permit(:first_name, :last_name, phones_attributes: {})
  end

But now I get the following error.

Unpermitted parameters: 0, 1

So I tried specifying the field names in the "phones_attributes" array.

def user_params
    params.require(:adult).permit(:first_name, :last_name, phones_attributes: [:id, :kind, :number])
end

And I still get.

Unpermitted parameters: phones_attributes

I know I must be missing something small, but I can't find my error.

EDIT: all my nested attributes forms do not work. Not 100% sure when they stopped, but ones that worked previously no longer work and have not been modified.


回答1:


Figured this out. I was using javascript to copy the phone fields (kind, number) to make a new set of inputs available for entry. The script was adding non numeric characters to part of the field id, and this was causing rails to ignore all the submitted phone_attributes.

For the next person that comes along...

When fields_for renders out the fields, it will index each input name for uniqueness when the submitted post data is converted to params. In the example below, this number field

<input id="adult_phones_attributes_0_number" name="adult[phones_attributes][0][number]" type="tel" value="7773331111">

will look something like this when converted to params

"phones_attributes"=>{"0"=>{"number"=>"7773331111"}}

The hash key of "0" comes from the index created by fields_for. It's the "[0]" portion of the name.

In versions of rails past, if that nested attributes params hash key was not a number, the k/v pair was just ignored. Well now with strong parameters (I'm guessing the culprit), it will reject the entire "phones_attributes" hash.

My script was copying the input field, doing a regex on the html to change the "[0]" index to a random number. But sometimes it would replace it will non-digit characters. And this was causing the problem.



来源:https://stackoverflow.com/questions/24707953/rails-4-1-nested-attributes-and-fields-for-getting-unpermitted-parameters-and-no

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!