Skip to content

Instantly share code, notes, and snippets.

@thegedge
Created September 27, 2021 19:19
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save thegedge/b84733bab581670959cc81ab47a7b7e7 to your computer and use it in GitHub Desktop.
Save thegedge/b84733bab581670959cc81ab47a7b7e7 to your computer and use it in GitHub Desktop.
Benchmarking pure JS + top three templating engines on NPM
import { Event, Suite } from "benchmark";
import * as ejs from "ejs";
import * as handlebars from "handlebars";
import * as nunjucks from "nunjucks";
const DATA = {
greeting: "Hello",
things: [
{ name: "Test", color: "red" },
{ name: "Boat", color: "blue" },
{ name: "Car", color: "yellow" },
],
};
const NUNJUCKS_TEMPLATE = nunjucks.compile(`
{% for thing in things %}
{{ greeting }}, {{ thing.name }} 👋
Your color is: {{ thing.color }}
{% endfor %}
`);
const TEMPLATES = {
"js concat": (data: any) => {
let result = "\n";
for (const thing of data.things) {
result += `${data.greeting}, ${thing.name} 👋\n`;
result += `Your color is: ${thing.color};\n`;
}
return result;
},
"js join": (data: any) => {
const result = [];
for (const thing of data.things) {
result.push(`${data.greeting}, ${thing.name} 👋\n`);
result.push(`Your color is: ${thing.color};\n`);
}
return result.join("");
},
ejs: ejs.compile(`
<% for(const thing of things) { %>
<%- greeting %>, <%- thing.name %> 👋
Your color is: <%- thing.color %>
<% } %>
`),
handlebars: handlebars.compile(`
{{#each things}}
{{ @root.greeting }}, {{ this.name }} 👋
Your color is: {{ this.color }}
{{/each}}
`),
nunjucks: (data: any) => NUNJUCKS_TEMPLATE.render(data),
};
var suite = new Suite("template engines", { initCount: 1_000_000 });
for (const [name, template] of Object.entries(TEMPLATES)) {
console.info(`--- ${name} ---\n`, template(DATA));
suite.add(name, () => template(DATA));
}
console.info("Starting benchmark...");
suite
.on("cycle", (event: Event) => {
if (!event.target.stats) {
throw new Error(`no stats for ${event.target.name}`);
}
const toMicro = (x: number) => {
const v = (x * 1_000_000).toPrecision(2);
return `${v}μs`;
};
console.log(`${event.target.name}: ${toMicro(event.target.stats.mean)} ± ${toMicro(event.target.stats.deviation)}`);
})
.on("complete", function (this: Suite, _event: Event) {
console.log("\nFastest is " + this.filter("fastest").map("name"));
})
.run();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment