import dateFormat from 'dateformat'; import fs from 'fs-extra'; import Handlebars from 'handlebars'; import mjml2html from 'mjml'; import path from 'path'; import { EmailGenerator, EmailPluginDevModeOptions, EmailPluginOptions } from './types'; /** * Uses Handlebars (https://handlebarsjs.com/) to output MJML (https://mjml.io) which is then * compiled down to responsive email HTML. */ export class HandlebarsMjmlGenerator implements EmailGenerator { onInit(options: EmailPluginOptions | EmailPluginDevModeOptions) { const partialsPath = path.join(options.templatePath, 'partials'); this.registerPartials(partialsPath); this.registerHelpers(); } generate( subject: string, template: string, templateVars: any, ) { const compiledSubject = Handlebars.compile(subject); const compiledTemplate = Handlebars.compile(template); const subjectResult = compiledSubject(templateVars); const mjml = compiledTemplate(templateVars); const body = mjml2html(mjml).html; return { subject: subjectResult, body }; } private registerPartials(partialsPath: string) { const partialsFiles = fs.readdirSync(partialsPath); for (const partialFile of partialsFiles) { const partialContent = fs.readFileSync(path.join(partialsPath, partialFile), 'utf-8'); Handlebars.registerPartial(path.basename(partialFile, '.hbs'), partialContent); } } private registerHelpers() { Handlebars.registerHelper('formatDate', (date: Date, format: string | object) => { if (typeof format !== 'string') { format = 'default'; } return dateFormat(date, format); }); Handlebars.registerHelper('formatMoney', (amount: number) => { return (amount / 100).toFixed(2); }); } }