Search code examples
rubyyamlerbmiddleman

Outputting data with erb and middleman


I'm wanting to output some data and I'm not sure if it is possible or not without changing my data file. Basically I have a YAML file with the following structure

 items: 
   - category: red
     name: super fun times
     note: likes fun
   - category: red
     name: sunshine
     note: wear sunglasses
   - category: blue
     name: crazy face
     note: avoid.

What I'm doing is looping through like so

<% data.options.items.each do |q| %>
  <h2><%= q.category %></h2>
  <p><%= q.name %></p>
<% end %>

I'd like to be able to do is group items by category when it outputs so it would be something like the following.

<h2>red</h2>
<p>super fun times</p>
<p>sunshine</p>

<h2>blue</h2>
<p>crazy face</p>

I pretty much just want to output the category once, list out the items under that category and then when a new category comes up output that one and any relevant data, without having to repeat chunks of code.


Solution

  • An approach you can take is using group_to to cluster the items by their group, resulting in sets of arrays for each category:

    <% data.options.items.group_by(&:category).each do |group| %>
      <h2><%= group.first %></h2>
      <% group.last.each do |item| %>
        <p><%= item.name %></p>
      <% end %>
    <% end %>
    

    In this scenario, running group_by on the collection of items provides an object with the following format:

    {"red"=>[{"category"=>"red", "name"=>"super fun times", "note"=>"likes fun"}, 
    {"category"=>"red", "name"=>"sunshine", "note"=>"wear sunglasses"}],
    "blue"=>[{"category"=>"blue", "name"=>"crazy face", "note"=>"avoid."}]}
    

    This allows you to then iterate through the object, making it easier to keep the groups separate in the markup.

    Hope it helps!