Recently I needed to write a rails helper to generate some html code with quite a bit of nested html. I quickly found this can be quite tricky and I discovered I wasn’t alone with a quick google of terms like ‘nesting content_tag’, ‘content_tag conact’, ‘content_tag table’.
So wrote a rails test and helper to play around with the outputs to get a better understanding. The best way to do this is was to try coding up a table.
I first tried writing the block with do and found the content_tag’s weren’t joining:
In this example notice the output is missing <thead><tr><th>HeaderCol 1</th></tr></thead>. What’s happening is th, tr and thead is generated and then tbody is generated after them but they aren’t being joined so what get’s outputted is only tbody within table as tbody is the last output in the block. I found some people using concat to get around this but when you start nesting more it becomes tricky.
An easier way than using concat is to write the block with () and use + to join the blocks together like so:
While this is easier to write it can become a little hard to read when you start adding options like classes or id’s to your content_tag as this goes after the nested content. So I found myself writing the blocks using a combination of do and ().
Here’s an example of a deeply nested content_tag I wrote. It iterates over a hash using map so requires the use of join and ‘html_safe’, and it also includes some conditionals.
And this is what the end result looked like with some pretty styling.
Later I put some more thought into this and think it’s better to break down the nested content_tags into methods or variables and then concatenate them together. Here’s an example using both methods and variables to concatenate the results together.
I think this result could end up being a lot more tidy and readable. As always more playing and more learning to be done.