强参数:params.permit返回未允许的参数,尽管白名单

时间:2017-01-21 00:29:49

标签: ruby-on-rails ruby parameters ruby-on-rails-5 strong-parameters

UsersProfileController具有强大的参数,如下所示:

    def user_profile_params
      params.permit(:age, :relations)
      # yes, I am not requiring user_profile. Just permitting attributes I need. 
    end

create动作通过父(has-one和belongs-to association)

构建UserProfile
    def create
      parent = Parent.create_guest
      parent.build_user_profile(user_profile_params)
      if parent.save 
        # do something 
      else 
        # handle error
      end
    end

在UserProfiles中调用params返回:

    <ActionController::Parameters 
      {"age"=>"23", 
       "relations"=>"3", 
       "subdomain"=>"api", 
       "format"=>:json, 
       "controller"=>"api/v1/user_profiles", 
       "action"=>"create"} 
     permitted: false>

调用user_profile_params,返回:

    user_profile_params:
      Unpermitted parameters: subdomain, format
      <ActionController::Parameters 
       {"age"=>"23", 
       "relations"=>"3", } 
      permitted: true>

当发布帖子请求时,我希望能够使用user_profile_params中列入白名单的参数创建user_profile。相反,UserProfiles中的create操作失败,错误为:Unpermitted parameters: subdomain, format

这不是我的预期。我希望user_profile_params只包含允许的值并忽略所有其他值。

我可以将:format:subdomain添加到允许的属性列表中,但有些事情让人觉得有点不对劲。

有人可以解释发生了什么/我错过了什么?

1 个答案:

答案 0 :(得分:4)

此消息只是警告,而不是错误/异常。如果你的模型没有被持久化,那就是另一个原因。

来自strong parameters docs

  

处理未经许可的密钥

     

默认情况下,未明确允许的参数键将是   登录开发和测试环境。在其他环境中   这些参数将被过滤掉并被忽略。

     

此外,可以通过更改此更改   config.action_controller.action_on_unpermitted_pa​​rameters属性   你的环境文件。如果设置为:log将取消未经许可的属性   记录,如果设置为:将引发异常。

您可以在控制台中模拟它(rails c):

fake_params_hash = {
    "age"=>"23", 
    "relations"=>"3", 
    "subdomain"=>"api", 
    "format"=>:json, 
    "controller"=>"api/v1/user_profiles", 
    "action"=>"create"
} 

permited_params = ActionController::Parameters.new(fake_params_hash).permit(:age, :relations)
#=> Unpermitted parameters: subdomain, format <== warning logged to the console
#=> <ActionController::Parameters {"age"=>"23", "relations"=>"3"} permitted: true>


user = User.create(permited_params) #mass assigment with permited params

#check if there are errors
puts user.errors.messages if user.errors.any?

如您所见,User.create不会抛出此消息,但会调用.permit