Search code examples
javascripthtmlhandlebars.jsexpress-handlebars

How do I use an handlebars #each call for an object with arrays of objects?


So I have an object that's structured like this:

menu = {
  classic: [
    {p1: ..., p2: ...}, {p1: ..., p2: ...}
  ],
  classic2: : [
    {p1: ..., p2: ...}, {p1: ..., p2: ...}
  ]
}

An object where each value is an array of objects. How do I use an handlebars #each call to get to menu.classic[0].p1, for example? Can I nest multiple #each calls to iterate over every array index in every object value?


Solution

  • Use nested {{#each}} blocks.

    Here you will see both classic and classic2 rendered into <ul>s with corresponding p1 properties rendered into <li>s using this approach.

    The first example builds the menus imagining p1 holds a URL and p2 holds the text for the link. That each goes into an <a> tag with in the <li>.

    let menu = {
      classic: [
        {p1: 'URL1', p2: 'classic link1'}, {p1: 'URL2', p2: 'classic link2'}
      ],
      classic2:  [
        {p1: 'URL3', p2: 'classic2 link1'}, {p1: 'URL4', p2: 'classic2 link2'}
      ]
    };
    
    const ul = `
    <div>
      {{#each this}}
      <ul class="menu">
        {{#each this}}
        <li><a href="{{this.p1}}">{{this.p2}}</a></li>
        {{/each}}
      </ul>
      {{/each}}
    </div>`;
    
    let template = Handlebars.compile(ul);
    console.log(template(menu));
    <script src="https://cdn.jsdelivr.net/npm/handlebars@latest/dist/handlebars.js"></script>

    In a table:

    let menu = {
      classic: [
        {p1: 'classic test', p2: 'classic test'}, {p1: 'classic test', p2: 'classic test'}
      ],
      classic2:  [
        {p1: 'classic2 test', p2: 'classic2 test'}, {p1: 'classic2 test', p2: 'classic2 test'}
      ]
    };
    
    const table = `
      {{#each this}}
    <table>
      {{#each this}}
      <tr>
        {{#each this}}
        <td>{{this}}</td>
        {{/each}}
      </tr>
      {{/each}}
    </table>
    {{/each}}`;
    
    let template = Handlebars.compile(table);
    console.log(template(menu));
    <script src="https://cdn.jsdelivr.net/npm/handlebars@latest/dist/handlebars.js"></script>