ruby-on-railsactionviewhelper

Rails 5 tag helper with tag name in variable


I am converting some older code which uses content_tag like this:

wrap_tag = 'p'
....
content_tag(wrap_tag, class: 'etc') do
  'some content'
end

which generates the expected

<p class="etc">
Some content
</div>

I'd now like to update to use the tag syntax, but I am having troubles with this:

wrap_tag = 'p'
...
tag wrap_tag, class: 'etc' do
  'some content'
end

Trying: tag.wrap_tag gives "<wrap-tag>some content</wrap-tag>"

Not unexpected, except that the underscore has become a hyphen.

Other variations:

Note: all the examples above included the do..content..end block shown initially.

Is there a way to have the tag name in a variable and include content?

Thanks


Trying the suggestion from jvillian to use send I find that

wrap_tag = 'p'
content = 'some text'
helper.tag.send(wrap_tag, content)

returns "some text", and generally returns the second and subsequent arguments.


It does seem, looking at actionview/helpers/tag_helper.rb, that the content_tag method checks for block_given? and tag doesn't.

But whyyyyyyyyy (not) I will have to read through the PR again to find out.


Solution

  • I find that if I do:

    @arg = :div
    tag.send @arg, class: 'etc' do 
      'some content'
    end
    

    ...then I get:

    <div class="etc">some content</div>
    

    Similarly, if I do:

    @arg = :section
    tag.send @arg, class: 'etc' do 
      'some content'
    end
    

    ...then I get:

    <section class="etc">some content</section>
    

    If, however, I do:

    @arg = :p
    tag.send @arg, class: 'etc' do 
      'some content'
    end
    

    ...then I get:

    {:class=>"etc"}
    

    Which, obviously, is not what one expects. And, seems straight-up peculiar, because:

    tag.p class: 'etc' do 
      'some content'
    end
    

    ...gives:

    <p class="etc">some content</p>
    

    ...which is all sunshine and lolipops.

    Gremlins? One can only wonder.