Rails - 在.create上传递其他变量

时间:2014-07-14 21:57:43

标签: ruby-on-rails ruby-on-rails-4

我试图使用瘦控制器和胖模型付诸实践,但是为了做到这一点,我发现自己需要将其他变量传递给.create方法。

所以例如我在哪里:

@app =  App.new(app_params)

def app_params
  params.require(:app).permit( :name,  :description)
end

现在我还想传递一个会话持有user_id,以及对权限组的引用。所以希望类似下面的伪代码:

@app = App.create(app_params, session[:user_id], app_permission_id)

user_id和app_permission_id不会被持久化但是可用我希望在模型中的after_create回调之类的地方,所以我可以做一些进一步的工作,例如创建创建的日志条目,与主叫用户相关联。

我不太热衷于将它们作为隐藏字段添加到表单中(以隐藏用户的实现)。我认为有一种可能的方法使用.merge?如果是这样的话,我猜我会用虚拟属性将它们拉出来。

非常感谢有关最佳/最干净方法的任何建议。我想我不得不以某种方式覆盖.create方法(但仅限于控制器端最干净的实现方式)。

3 个答案:

答案 0 :(得分:5)

如果您是app_params,则应始终包含user_id和app_permission_id

你应该这样做

def app_params
  params.require(:app).permit( :name,  :description).merge(user_id: session[:user_id], app_permission_id: app_permission_id)
end

否则,如果它不应该一直包含这个

你应该这样做

app_params.merge(user_id: session[:user_id], app_permission_id: app_permission_id) #as mentioned by Vapire in his answer

答案 1 :(得分:1)

是的,这可以通过merge

实现
def create
  @app = App.new(app_params.merge(user_id: session[:user_id], app_permission_id: app_permission_id))
end

当然,您的模型中需要虚拟属性user_idapp_permission_id

另见this answer

答案 2 :(得分:1)

描述.merge的两个答案是正确的;让我解释原因

-

<强> PARAMS

在控制器级别处理params并使用strong_params进行处理时,Rails基本上是&#34;通过&#34;将数据传递到您的模型,如下所示:

"params" => {
   "app" => {
      "name" => "data",
      "description" => "data",
    }
}

这是典型的form_for参数对象通过控制器发送的内容。当您通过strong_params方法获取数据时,您基本上只是&#34;允许&#34;要传递给模型的各种数据。

请注意,strong_params旨在帮助阻止mass_assignment,这意味着该方法旨在仅向您的模型发送特定的参数。

-

<强>修正

如果您想为每个模型请求附加额外数据,您必须使用merge

def app_params
   params.require(:app).permit(:name, :description).merge(user_id: session[:user_id], app_permission_id: app_permission_id) 
end