50

这可能更像是一个 ruby​​ 问题,而不是 rails 问题,但我很确定我能够在 vanilla ruby​​ 应用程序中做到这一点。

我定义了强大的参数。

def trip_params
  params.require(:trip).permit(:name, :date)
end

现在我在控制器方法中获取这些参数。我想做这个。

def save
  trip_params[:name] = 'Modifying name in place'
  #trip_params[:name] still equals original value passed
end

这永远行不通。 名字永不改变。顺便说一句:trip_params 的类型是 ActionController::Parameters

如果我做一个标准的 ruby​​ 脚本,它就可以工作。

test = {}    
test[:name] = "blah"    
test[:name] = "ok"    
puts test #{:name=>"ok"}
4

4 回答 4

70

permit返回一个包含这些键的新哈希,因此您不会修改真实params变量。您也没有保存对哈希 trip_params 返回的引用,因此每次调用save.

尝试这个:

def save
  tp = trip_params
  tp[:name] = 'Modifying name in place'
  # ... use tp later, it'll be in there
end

或者,如果您真的希望它像以前那样使用,请trip_params像这样修改:

def trip_params
  @trip_params ||= params.require(:trip).permit(:name, :date)
end

现在该散列被延迟缓存,并且在后续trip_params调用中返回相同的散列。

于 2013-08-22T01:21:47.780 回答
28

如果你真的想改变控制器中的参数,你可以这样做:

def save
  params[:trip][:name] = 'Modifying name in place'
  # Now trip_params[:name] is 'Modifying name in place'
end
于 2013-11-26T10:46:34.700 回答
5

你也可以做

def save
  data = trip_params.merge(name: 'new name')
  # use data later
end

如果一个新的散列被合并到一个旧的散列中并且如果有重复的键,那么新散列的键将覆盖旧散列的匹配键。

于 2016-09-22T03:41:41.557 回答
3

这是因为没有诸如trip_params[]=(arg, val).

我的意思是,当您调用 trip_params 时,您将返回 的值params.require(:trip).permit(:name, :date),因此每次调用时,trip_params您都会再次获取参数。

所以,如果我是你,我会定义 trip_params 方法如下:

def trip_params
  @trip_params ||= params.require(:trip).permit(:name, :date)
end

并且还会定义一个方法来改变trip_params

def trip_params[]= (key,val)
  trip_params # Ensure that trip_params is called once or you will get an error
  @trip_params[key] = val
end

所以现在当你打电话时,trip_params你实际上会返回@trip_params,如果@trip_params还没有设置,它会设置为params.require(:trip).permit(:name, :date)

然后当你调用trip_params[:name] = "Some name"它时,它将确保首先@trip_params通过调用trip_params and then it will set the :name param to“Some name”来初始化它`

希望我对你有所帮助

于 2013-08-22T02:14:15.887 回答