JavaScript Template Literals & Tagged Templates
String formation from variables in JavaScript had been pain all the time. Not anymore; JavaScript Template Literals will save a lot of your time. Let's see the working & benefits of JavaScript Template Literals.
String formation from variables in JavaScript had been pain all the time. No more, JavaScript Template Literals and Tagged Templates will save a lot of your time. Let's see working and benefits of JavaScript Template Literals and Tagged Templates.
JavaScript Template literals
JavaScript Template literals are the Literals or Strings allowing Expression in between them. These are enclosed inside two back-ticks (`
) and the expressions start with $
sign and then are enclosed in curly braces {}
.
And the output of expression is placed at that position where the expression is embedded. For example:
let name = '';
console.log(`Hello ${name}!`);
name = 'World';
console.log(`Hello ${name}!`);
name = 'Pankaj';
console.log(`Hello ${name}!`);
generating the output like:
Hello !
Hello World!
Hello Pankaj!
So the template literal Hello ${name}!
is equal to 'Hello ' + name + '!'
.
That was the trivial usage of Template Literals. Going forward on advanced usage, the expressions can be anything which may return a String
. If not convertible to String, then it will try to convert it to string and may give output like [object Object]
.
For example if you give { place: 'World', name: 'Pankaj'] }
to the name
variable above, you will get Hello [object Object]!
And the strings can have newlines and any character in between. Following is a valid example of Template Literal. On usage, this will preserve the spaces and tabs in the output as well.
const template = (name, profileUrl, pictureUrl) => `
<div>
<p><a href="${profileUrl}">${name}</a></p>
<img src="${pictureUrl}" style="max-height: 200px" />
</div>
`
template('Pankaj', '//pankaj.pro', 'https://avatars0.githubusercontent.com/u/251937?s=200&v=4');
Which on executing will give following output:
"
<div>
<p><a href="//pankaj.pro">Pankaj</a></p>
<img src="https://avatars0.githubusercontent.com/u/251937?s=200&v=4" />
</div>
"
which now can be used in any way, like following:
let div = document.createElement('div');
div.id = 'profile';
div.innerHTML = template('Pankaj', '//pankaj.pro', 'https://avatars0.githubusercontent.com/u/251937?s=200&v=4');
div.setAttribute('style', 'display: block; width: 200px; height: 200px;');
document.body.appendChild(div);
Now lets see how to render a list of links for navigation menu. Example markup is from Nav in Bootstrap 4.
const topLevel = [
{ label: 'Home', url: '/home' },
{ label: 'Products', url: '/products' },
{ label: 'Services', url: '/services' },
{ label: 'About', url: '/about-us' },
{ label: 'Contact', url: '/contact-us' },
];
const social = [
{ label: '<i class="fa fa-facebook-square"></i>', url: 'https://facebook.com/time2hack' },
{ label: '<i class="fa fa-twitter-square"></i>', url: 'https://twitter.com/time2hack' },
{ label: '<i class="fa fa-google-plus-square"></i>', url: 'https://plus.google.com/+Time2hack' },
]
const menu = (menuData) => `
<ul class="nav">
${menuData.map(item => `
<li class="nav-item">
<a class="nav-link" href="${item.url}">${item.label}</a>
</li>
`)}
</ul>
`;
And considering that we have these menus on header and footer, on executing the above code in following way; we will add it to page.
document.querySelector('body > header').innerHTML += menu(topLevel);
document.querySelector('body > footer').innerHTML += menu(social);
Tagged Templates
Tagged Templates are the template literals which are tagged some another function for further processing.
For example:
const tag = (parts, name, url) => {
return `${parts[0]}__${name}__${parts[1]}__${url}__`;
}
const name = 'Pankaj';
const url = 'http://pankaj.pro';
console.log(tag`I am ${name} and you can reach me at ${url}`);
which will give following output:
I am __Pankaj__ and you can reach me at __http://pankaj.pro__
The expressions reaching as the parameters to the tagging function are already executed and hence you can do more of the text processing of the template parts.
With tagged templates, you can achieve more wide range of the templates' capabilities.
Let's take following example of unknown number of expressions and wrap all the expression parameters with code
HTML tag:
const tag = (parts, ...params) => {
const strParts = parts.slice();
const exprParts = params.slice();
const output = [];
while(strParts.length) {
output.push(strParts.shift());
exprParts.length && output.push(`<code>${exprParts.shift()}</code>`);
}
return output.join('');
}
const name = 'Pankaj';
const url = 'http://pankaj.pro';
console.log(tag`I am ${name} and you can reach me at ${url}`);
which will generate the following output:
I am <code>Pankaj</code> and you can reach me at <code>http://pankaj.pro</code>
Related
Conclusion
And with such power to JavaScript Template Literals we can easily remove the need of template engine if our needs/requirements are not too wide-range for templates.
Please let me know about your experiences and any problems you are facing with Template Literals through comments ? or on Twitter at @heypankaj_ and/or @time2hack
If you find this article helpful, please share it with others ?
Subscribe to the blog to receive new posts right to your inbox.