Ruby 2.3 - 不可理解的ArgumentError异常

时间:2016-02-05 11:22:20

标签: ruby keyword-argument

我目前正在将项目从ruby 1.9.3升级到ruby 2.3.0,有一件事我无法解决关于关键字参数的问题。

我有一个类似的方法定义:

def icon(icon_name, opts = {})
  # ...
end

我这样称呼这个方法:

icon(:info, class: 'info-popup', data: { content: 'content', variation: 'inverted' })

并获得异常

unknown keywords: class, data

所以我查看了ruby 2.3中调用方法的文档并阅读了关键字参数并尝试了以下内容:

def icon(icon_name, opts: {}); end
icon(:info, opts: { class: 'info-popup', data: { content: object.description, variation: 'inverted' } }
#=> unknown keyword: opts

def icon(icon_name, *+args); end
icon(:info, class: 'info-popup', data: { content: 'content', variation: 'inverted' })
#=> unknown keywords: class, data

def icon(icon_name, *opts, **_); end
icon(:info, class: 'info-popup', data: { content: 'content', variation: 'inverted' })
#=> unknown keywords: class, data

def icon(icon_name, class: nil, data: nil); end
icon(:info, class: 'info-popup', data: { content: 'content', variation: 'inverted' })
#=> unknown keywords: class, data

我在这里缺少什么?

另外,为了给出一点透视:我想以多种不同方式调用该图标方法,因为在下面可以使用许多选项,如size: :smalldisabled: true等。根据CSS类。因此,调用该方法的最小方法是icon(:name_of_icon),这意味着设置一百个关键字参数nil作为默认值对我来说似乎不太实用...

更新

这是rails项目的一部分,该方法在SemanticHelper模块中定义。方法内部如下所示:

def icon(icon_name, opts = {})
  additional_classes = ''

  # STATES
  additional_classes << 'disabled ' if !!opts.delete(:disabled)

  # VARIATIONS
  additional_classes << 'circular '   if !!opts.delete(:circular)
  additional_classes << 'square '     if !!opts.delete(:square)
  additional_classes << 'inverted '   if !!opts.delete(:inverted)
  additional_classes << 'basic '      if !!opts.delete(:basic)
  additional_classes << 'link icon '  if !!opts.delete(:link)

  additional_classes << "#{opts.delete(:color)} " if opts[:color]

  size = opts.delete(:size)
  additional_classes << "#{size} " if !!size

  flipped_direction = opts.delete(:flipped)
  additional_classes << "#{flipped_direction} flipped" if !!flipped_direction

  rotated_direction = opts.delete(:rotated)
  additional_classes << "#{rotated_direction} rotated" if !!rotated_direction

  opts[:class] = "#{opts[:class]} #{additional_classes} #{icon_name} icon"

  content_tag(:i, '', opts)
end

2 个答案:

答案 0 :(得分:0)

使用原始方法定义,只需尝试用大括号包装选项哈希:

icon(:info, {class: 'info-popup', data: { content: 'content', variation: 'inverted' }})

答案 1 :(得分:0)

你在第二种方法中有一个错字。命名参数应使用双splat声明,而不是*+

 ▶ def icon(icon_name, **opts) ; puts opts.inspect ; end
 #⇒ :icon
 ▶ icon :info, class: 'info-popup', 
               data: { content: 'content', variation: 'inverted' })
 #⇒ {:class=>"info-popup", 
 #⇒  :data=>{:content=>"content", :variation=>"inverted"}}