Is your Handlebars code not working as expected? This article walks through a few of the most common issues and how to fix them.
# In this article
# Tips and best practices
To avoid potential issues with Handlebars in your message templates, there are a few tips and best practices you should be aware of. Knowing how the Handlebars language and Iterable's settings work can help you prevent issues before they start.
# How Iterable prioritizes data sources
If a merge tag references a field that exists in both a user's profile and the campaign's triggering event, Iterable uses the value from the event to render the merge tag at send time.
When the Merge the data feed and user contexts{{}})
instead of double square brackets ([[]]) to pull values from a data feed. You
can still use double curly braces to reference data from user profiles, but if
the same field exists in both the user's profile and the data feed, Iterable
uses the value from the user's profile. This way, your merge tags prioritize
values from user profiles but can fall back on values from a data feed if
necessary.
# Don't name fields with periods
Avoid using periods when naming user and event fields in your Iterable projects.
Since the Handlebars language uses periods to reference fields within objects{{objectName.fieldName}}), field names that contain periods can
cause errors.
To learn more about avoiding errors due to naming convention issues, see Best Practices for Field Names and Event Names.
# Using Handlebars in the WYSIWYG editor
When building a template in Iterable's WYSIWYG editor, there are two ways to add
Handlebars code: you can insert the code into the template's design, or click the
<> button to view and edit the template's HTML source.
When editing the HTML source, it's a good idea to comment out any lines of Handlebars code that don't output a value. In rare circumstances, the WYSIWYG editor can get confused by the presence of Handlebars in the HTML source, which can lead to errors. The WYSIWYG editor ignores comments in the HTML source, so commenting out these lines of Handlebars code can resolve this issue.
Before:
After:
IMPORTANT
Only comment out lines of Handlebars code that don't directly output a value
(like conditionals, looping statements, and closing statements). Don't comment
out lines that output a value (like {{email}} or <div> text). If you do,
these lines will be ignored in the template's HTML and won't render in the
message at send time.
# Removing whitespace
It's important to be aware that whitespace characters such as spaces, tabs, and newlines are preserved by default in Iterable's template editors. This can cause formatting issues, especially in use cases involving URLs, deep links, or code fragments, where extra characters can break the rendered output (for example, when using Handlebars to generate a deep link for the Open URL input box of a push notification template).
To avoid this, add a tilde character (~) before and/or after each merge tag in
your Handlebars code to trim unwanted whitespace from the rendered output:
| Action | Syntax |
|---|---|
| Remove leading whitespace before a merge tag | {{~tag}} |
| Remove trailing whitespace after a merge tag | {{tag~}} |
| Remove both trailing and leading whitespace from a merge tag | {{~tag~}} |
The following example demonstrates how to correctly trim whitespace to prevent rendering issues:
# Use single quotes inside quoted HTML and JSON
When a Handlebars expression appears inside an HTML attribute or JSON value that is already wrapped in double quotes, use single quotes for any string literals inside the Handlebars expression. Otherwise, the inner quotes can break the surrounding syntax.
This commonly affects values used in src="...", href="...", title="...",
data-*="...", and JSON payloads.
Example:
To learn more, see Quotes Inside HTML and JSON.
# Common issues
Running into issues with Handlebars in a message template? Here are some of the most common issues and their solutions.
# Can't save a template due to a Handlebars error
Handlebars blocks (which contain multiple lines of code) require both an opening statement and a closing statement. Each time you add an opening Handlebars statement, you must also include a corresponding closing statement. If one of your Handlebars blocks isn't rendering correctly, it might be missing one of these closing statements.
For example, the following block has two opening #if statements, but only one
closing /if statement:
In this example, you'd need to add another line containing a closing /if
statement after the <div> line. The above code should look like this:
# Handlebars code renders as HTML
Sometimes, Iterable's template editor may render Handlebars code as HTML. To
prevent this, comment out any lines of your Handlebars code that don't directly
render content. To comment out a line of Handlebars code, add <!-- to the
beginning of the line and --> to the end.
# Example
<!--{{#if [First Name]}}--> Hi, {{[First Name]}}! <!--{{/if}}-->
The comments surrounding the first and last line of code tell the template
editor to ignore the #if block when generating the template's HTML. The code
still functions (checking to see if the user's First Name field is set), but
the comment tells Iterable it shouldn't be part of the rendered HTML at send
time.
Since the second line hasn't been commented out, its content is eligible to be
displayed in the rendered HTML at send time. If the user's First Name field
is set, the content will be displayed.
# Unexpected characters in rendered content
Iterable renders certain characters with their HTML encoding. For example,
apostrophes (') are rendered with the following: '
Let's say you're using the merge tag {{productName}} in an Iterable template.
If any of your product names contain apostrophes, the names will render with the
' character encoding.
# Example
| Code | Example productName value | Output |
|---|---|---|
| Jenna's Elixir | Jenna's Elixir |
To prevent this from happening, use triple curly braces in your merge tag like this:
# Data feed in Handlebars code doesn't render
To reference a data feed in Handlebars code, you can use either square brackets
([]) or curly braces ({}) — which one you should use depends on the
template's settings.
Once data feeds have been enabled for the template, you'll see an additional
option called Merge the Data Feed and User Contexts. When this option is
enabled, you can use either curly braces or square brackets to reference values
from a data feed in Handlebars code. At send time, Iterable pulls data from both
the user profile and the data feed to populate the dynamic content in the final
template. If there are any conflicts (for example, if a firstName field
exists in both the user profile and the data feed), Iterable prioritizes values
from the user profile.
When the Merge the Data Feed and User Contexts option is disabled, you must
use square brackets ([]) to reference a value from a data feed in a Handlebars
block. For example:
# Blank or missing values in rendered content
If one of your referenced values isn't rendering in a template, it might be due
to a formatting issue with its field name. If any of your field names contain
spaces, you'll need to surround them with square brackets ([]) when you
include them in a merge tag.
# Example
| Code | Example First Name value | Output |
|---|---|---|
| Marishka | Hi, Marishka! |
NOTE
To learn more about when to use each kind of enclosing character, see Handlebars Syntax.
# Want to learn more?
For more information about some of the topics in this article, check out these resources. Iterable Academy is open to everyone — you don't need to be an Iterable customer!
Iterable Academy
Support docs