有没有更好的方法来检查子参数?
Is there a better way to check child params?
是否有比以下代码更好的检查 items_attributes 的方法?我必须先检查 params[:order],因为有时它可能不存在,但我讨厌长条件语句的外观。
if params[:order] and params[:order][:items_attributes]
UPDATE for ruby 2.3,现在你可以使用挖掘方法
params.dig(:order, :item_attributes)
如果您使用 andand gem:
if params[:order].andand[:items_attributes]
您也可以使用 try
。
您可以使用 try
,像这样:
params[:order].try(:[], :items_attributes)
try 方法 returns nil
如果接收方没有响应它,而不是引发异常。
希望对您有所帮助!
如果我有这样的问题,我会考虑用这样的东西扩展基本的 ruby class Hash
(这只是一个想法)
class Hash
def has_nested_values?(*args)
current_value = self.dup
args.each do |arg|
current_value = current_value[arg]
break unless current_value
end
!!current_value
end
end
结果是
h[:a] = {b: {c: {d: 1}}}
h.has_nested_values?(:a, :b, :c)
=> true
h.has_nested_values?(:a, :b, :cc)
=> false
PS 我不喜欢 dup
的实现,但它有效
您可以创建辅助方法以更轻松地处理嵌套哈希。在您的 lib 文件夹中创建 ruby_ext.rb 文件,并编写此函数:
module RubyExt
module SafeHashChain
def safe(*args)
if args.size == 0 then self # Called without args ...
elsif args.size == 1 then self[args[0]] # Reached end
elsif self[args[0]].is_a?(Hash) then self[args[0]].safe(*args[1..-1])
else nil end # Reached end-value too soon
end
end
end
class Hash; include RubyExt::SafeHashChain; end
在此之后,您可以像这样在嵌套哈希上调用安全方法:
params.safe(:order,:items_attributes)
它会 return 来自 items_attributes 的值。如果订单或 items_attributes 不存在,它将 return nil。
Params 实际上是ActionController::Parameters
的一个实例,并内置了白名单过滤功能。
这使得做这样的事情成为可能:
# White list for Order params
def order_params
params.require(:order).permit(:items_attributes)
end
// If :order is missing exception, and then filter only permitted.
valid_params = order_params()
// Also make these calls safe without risk for unwanted params
order = Order.new(order_params())
order.save!
您可能喜欢使用默认值获取?
order = params.fetch(:order, {})
if order[:item_attributes]
# ...
end
是否有比以下代码更好的检查 items_attributes 的方法?我必须先检查 params[:order],因为有时它可能不存在,但我讨厌长条件语句的外观。
if params[:order] and params[:order][:items_attributes]
UPDATE for ruby 2.3,现在你可以使用挖掘方法
params.dig(:order, :item_attributes)
如果您使用 andand gem:
if params[:order].andand[:items_attributes]
您也可以使用 try
。
您可以使用 try
,像这样:
params[:order].try(:[], :items_attributes)
try 方法 returns nil
如果接收方没有响应它,而不是引发异常。
希望对您有所帮助!
如果我有这样的问题,我会考虑用这样的东西扩展基本的 ruby class Hash
(这只是一个想法)
class Hash
def has_nested_values?(*args)
current_value = self.dup
args.each do |arg|
current_value = current_value[arg]
break unless current_value
end
!!current_value
end
end
结果是
h[:a] = {b: {c: {d: 1}}}
h.has_nested_values?(:a, :b, :c)
=> true
h.has_nested_values?(:a, :b, :cc)
=> false
PS 我不喜欢 dup
的实现,但它有效
您可以创建辅助方法以更轻松地处理嵌套哈希。在您的 lib 文件夹中创建 ruby_ext.rb 文件,并编写此函数:
module RubyExt
module SafeHashChain
def safe(*args)
if args.size == 0 then self # Called without args ...
elsif args.size == 1 then self[args[0]] # Reached end
elsif self[args[0]].is_a?(Hash) then self[args[0]].safe(*args[1..-1])
else nil end # Reached end-value too soon
end
end
end
class Hash; include RubyExt::SafeHashChain; end
在此之后,您可以像这样在嵌套哈希上调用安全方法:
params.safe(:order,:items_attributes)
它会 return 来自 items_attributes 的值。如果订单或 items_attributes 不存在,它将 return nil。
Params 实际上是ActionController::Parameters
的一个实例,并内置了白名单过滤功能。
这使得做这样的事情成为可能:
# White list for Order params
def order_params
params.require(:order).permit(:items_attributes)
end
// If :order is missing exception, and then filter only permitted.
valid_params = order_params()
// Also make these calls safe without risk for unwanted params
order = Order.new(order_params())
order.save!
您可能喜欢使用默认值获取?
order = params.fetch(:order, {})
if order[:item_attributes]
# ...
end