Reputation: 181
I'm trying to make a simple Ruby on Rails plugin. When the redcarpetable function is called with a hash for render_opts, I get "ArgumentError: unknown keyword: render_opts." The code for the function:
def redcarpetable(*fields, renderer: :default, as: [nil], prefix: "rendered", render_opts: {})
fields.each do |field|
if fields.count > 1
define_method "#{prefix}_#{field}" do
Carpet::Rendering.render(read_attribute(field), renderer_opts: render_opts, rc_renderer: renderer).html_safe
end # End defining the method dynamically.
else
if as[0]
as.each do |method_name|
define_method "#{method_name}" do
Carpet::Rendering.render(read_attribute(field), render_opts: render_opts, rc_renderer: renderer).html_safe
end # End defining the method dynamically.
end
else
define_method "rendered_#{field}" do
Carpet::Rendering.render(read_attribute(field), render_opts: render_opts, rc_renderer: renderer).html_safe
end # End defining the method dynamically.
end
end
end # End the fields loop.
end # End the redcarpet method.
How the function is called:
redcarpetable :name, renderer: :simple_parser, as: [:cool_name, :rendered_name], render_opts: {:generate_toc_data: true}
In order to allow for a hash of render options, what must be done to the function declaration? The full code (not documented well or refactored yet) is here.
Upvotes: 4
Views: 14283
Reputation: 26758
I think your issue might be caused by putting the *fields
splat before the other arguments.
Though I'm not specifically sure what's causing your error, you can get an options hash using the following approach:
def redcarpetable(options={}, *fields)
defaults = {
foo: "bar",
bar: "foo"
}
options= defaults.merge(options)
puts options[:foo] # => "bar"
end
This way you can set defaults and override them when you call the method.
In your method body, you're going to have to reference the variables via the options hash, i.e. options[:foo]
and not just foo
.
When you call the method, unless your passing nothing to *fields
you're going to have to include the braces in your options argument.
For example:
redcarpetable({foo: bar}, ["field1" "field2"])
And not:
redcarpetable(foo: bar, ["field1", "field2"])
Also, if you're passing any fields but not passing any options, you'll have to include empty braces.
For example:
redcarpetable({}, ["field1", "field2"])
Upvotes: 2
Reputation: 106782
You call the Carpet::Rendering
like this:
Carpet::Rendering.render(read_attribute(field),
render_opts: render_opts, rc_renderer: renderer
).html_safe
But the option is actually called renderer_opts
. Just change it to:
Carpet::Rendering.render(read_attribute(field),
renderer_opts: render_opts, rc_renderer: renderer
).html_safe
You might also want to change it in the methods' signature too.
Upvotes: 2