当我们只更新一个属性时,我们应该使用强params吗?

我正在开发一个Rails应用程序,我有几个操作(#delete_later,#ban_later等等),我只从请求参数中设置一个属性(具体来说,是执行该操作的reason字段)。

我想知道是否可以这样做:

 def ban_later @object.reason = params[:object][:reason] @object.save end 

或者即使在这种情况下使用强对数也是最佳做法?

 def ban_later @object.reason = object_params[:reason] @object.save end private def object_params params.require(:object).permit(:permitted_1, :permitted_2, :reason) end 

哪种解决方案最好? 如果没有,那么问题的最佳解决方案是什么?

后来编辑:

#ban_later,#delete_later操作确实可以设置标志列status但是可以在不从params散列中接收它的值的情况下完成。 由于您只为每个方法设置一个状态,因此当您在#delete_later时可以简单地设置状态“pending_delete”,当您在#ban_later时,可以设置“pending_ban”。

后来编辑

为什么直接使用#save而不是update_attributes ? 假设你需要一个if @object.save语句。 在false分支(对象未保存)上,您可能仍希望呈现使用该@object内容的视图。

第一个节省计算。

第二个检查是否存在:object sub-hash,我认为它对容错有好处。

我最初会选择第一名,但经过一番思考后我更喜欢第二名。

最简单的答案是,如果你只在params使用一个参数,并且没有将它传递给像model#create #create那样的多属性setter,那么你就不必使用strong_parameters来获得安全的解决方案。

但是,我预计整个控制器不太可能出现这种情况。 ban_later方法只需要一个参数,其他控制器方法需要更多。 在这种情况下,问题变成:“你想对ban_later以不同方式处理params以及如何将它用于其他控制器方法吗?”。

您也可以确定function不会改变,并且当您更改function时,您将记得更改params的处理方式。

因此,我会使用strong_parameters,因为它意味着:

  • 参数在控制器中的所有方法中一致地处理。
  • 随着function的变化,对方法的更改不太可能暴露漏洞。

如果要更新单个属性,为什么不使用update_attributes方法? ( update_attribute不调用validation)

 def ban_later @object.update_attributes reason: params(:reason) end private def params params params = %i(:permitted_1, :permitted_2, :permitted_3) unless params params.require(:object).permit params end 

根据ReggieB的评论,您还可以使用update选项:

 def ban_later @object.update reason: params(:reason) end 

如上所述,Reggie和其他答案解释了如何最好地工作的原理图(具有mass-assignment IE等)。 以上是您可以自由使用的可操作代码。


这里的底线是,如果你想保持你的应用程序多function(IE在任何你需要的地方具有最大的可扩展性),你需要坚持强大的params设置。

其他答案概述了该设置的工作原理,以及它的function如何根据您的需要而有所不同。

我已经包含了一个技巧,所以你只接受params方法中的特定参数。 我没有对它进行过广泛的测试,因此我们可能需要对其进行重构以获得所需的结果。

强参数检查后为什么不只是update对象? 它只是一个标准的工作流程。 (请告诉我,如果你的情况有任何理由不这样做)

 def ban_later @object.update(object_params) # dont forget validation check end private def object_params params.require(:object).permit(:permitted_1, :permitted_2, :reason) end 

在这种情况下,添加更多可更新字段会更容易。