0

I'm trying to create dynamic XMLs based on data stored in a javascript object. The problem is that the source data for certain attributes may contain null, which will result in Handlebars rendering the attribute with an empty string, while I would like Handlebars to just ignore it, and not render it at all. I suppose I could make a template with a helper like this:

<item {{if id}}id={{id}}{{/if}}></item>

But it just seems like a lot of work, and makes the whole thing unreadable. Is there a nicer way of getting the same results? Or would it perhaps be a better idea to traverse the whole XML after rendering and deleting attributes having empty strings?

robertpaulsen
  • 209
  • 4
  • 9

1 Answers1

1

I would recommend creating a very simple Handlebars helper. It could take a key and a value as parameters, but only return formatted attribute if value is 0 or truthy. For example:

Handlebars.registerHelper('attr', function (key, value) {
    if (!Handlebars.Utils.isEmpty(value)) {
        return new Handlebars.SafeString(key + '="' + Handlebars.escapeExpression(value) + '"');
    }
});

Your template would invoke the helper in the following manner:

<item {{attr 'id' id}}></item>

Note: I have added the HTML escaping of value just in case it contains a quote character.

Also, if your are able to use ES6, a Template Literal would be prettier:

return new Handlebars.SafeString(`${key}="${Handlebars.escapeExpression(value)}"`);

I have created a fiddle for your reference.

76484
  • 8,498
  • 3
  • 19
  • 30
  • Thank you, this appears to be a tidy and simple solution. – robertpaulsen Nov 02 '17 at 11:21
  • I've tested this solution, and while it works on the fiddle you made, it doesn't work on my site. I wonder if it can be related to me pre-compiling the templates, because inside my template.js file, the attribute, in this case "id" is part of a string which is returned regardless of the exclusion made by the helper it seems. Do you think it matters if it's precompiled? – robertpaulsen Nov 13 '17 at 16:03
  • @robertpaulsen: I can't image that precompiling would have any affect on this. What do you mean by "...is part of a string which is returned regardless..."? – 76484 Nov 14 '17 at 01:45
  • Indeed, you are right. I haven't properly analyzed what happened yet, but there was a typo in my template, which resulted in quite a different pre-compiled template. What I meant about the "returned string", was the value which is returned inside the precompiled template. In the original precompiled template, all attributes where "hardcoded" in the string, so they would not be excluded, even though the passed value to them were null. Well, seems to be working now, thanks for your time! – robertpaulsen Nov 14 '17 at 13:05