HTTPS SSH

uSend

USend is a tool that joins together an email transporter (package that sends out emails) with a templating engine to allow easy email content and header templating.

No email transporter or templating engine is bundled with uSend, nor is either a dependency. However, in order for uSend to work, both packages need to be installed. The recommended set is Nodemailer and Nunjucks. You can install them like this:

npm install nodemailer nunjucks --save

Usage

USend comes with TypeScript typings, so it can be used in both JavaScript and TypeScript applications.

Instantiation

In order to use it, a USend object needs to be instantiated. Its constructor accepts a templating engine and an email transporter, both wrapped in a common interface, thus making them exchangeable for different implementations.

Example:

const USend = require("usend").USend;
const Nunjucks = require("usend").Nunjucks;
const Nodemailer = require("usend").Nodemailer;

const nunjucks = require("nunjucks");
const nodemailer = require("nodemailer");

const template = new Nunjucks(nunjucks);
const transport = new Nodemailer({
    host: "smtp.example.com",
    port: 465,
    secure: true,
    auth: {
        user: "john.doe@example.com",
        pass: "supersecretpassword"
    }
});

const usend = new USend(template, transport);
import {USend, Nunjucks, Nodemailer, TemplateEngine, Transport} from "usend";
import * as nunjucks from "nunjucks";
import * as nodemailer from "nodemailer";

const template: TemplateEngine = new Nunjucks(nunjucks);
const transport: Transport = new Nodemailer({
    host: "smtp.example.com",
    port: 465,
    secure: true,
    auth: {
        user: "john.doe@example.com",
        pass: "supersecretpassword"
    }
});

const usend: USend = new USend(template, transport);

Message configuration and templating

Once instantiated, the USend object is able to send out a single email or a whole series of emails. One simply needs to provide an email configuration (or an array thereof). The email configuration object is a plain JavaScript object containing the following fields:

  • Mandatory:
    • from (string|EmailAddressConfiguration|Array)
    • to (string|EmailAddressConfiguration|Array)
    • subject (string)
    • at least one of either:
      • html (string)
      • text (string)
  • Optional:
    • cc (string|EmailAddressConfiguration|Array)
    • bcc (string|EmailAddressConfiguration|Array)
    • replyTo (string|EmailAddressConfiguration|Array)

The EmailAddressConfiguration type is a simple object containing two string fields: name and email. Example:

{
    "name": "John Doe",
    "email": "john.doe@example.com"
}

All address fields (from, to, replyTo, cc and bcc) can accept multiple types:

  • a string (ex. "john.doe@example.com" or "John Doe <john.doe@example.com>")
  • an EmailAddressConfiguration (explained above)
  • an Array of the two (meaning you can mix strings and EmailAddressConfigurations)

All strings within the message configuration (including the fields of the EmailAddressConfiguration) can use inline templating:

{
    "to": ["{{siteAdminAddress}}", "{{officeAddress}}"],
    "from": "{{mailerAddress}}",
    "replyTo": {
        "name": "{{senderAddress}}",
        "email": "{{senderEmail}}"
    },
    "subject": "New mail with subject {{subject}}",
    "text": "Hey, someone sent you and email with the body: {{body}}",
}

Additionally, the text and html fields can use a template file:

{
    "to": ["{{siteAdminAddress}}", "{{officeAddress}}"],
    "from": "{{mailerAddress}}",
    "replyTo": {
        "name": "{{senderAddress}}",
        "email": "{{senderEmail}}"
    },
    "subject": "New mail with subject {{subject}}",
    "html": "contact.html",
}

Note that it's the templating engine wrapper's responsibility to determine whether a given string is a template file or not. The default Nunjucks wrapper will check if the input terminates with ".html", but this will vary from engne to engine. For example, Twig will use ".twig" extension. Also, template string delimiters ({{ and }} in this case) may also vary between temlpating engines. Use the ones that your temlpating engine recognises.

Also note that it's your responsibility to inform the templating engine of the temlpate files' whereabouts.

Sending messages

Once the email configuration object or objects are available, USend can proceed with email sending using one of the following methods:

usend.sendMail(messageConfig, data); // one message
usend.sendMails(messageConfigs, data); // multiple messages

Note the second argument, data. It's an object containing the data that will be used by the templating engine to replace the template placeholders.

Error handling

Both sendMail() and sendMails() return a Promise. If email sending fails, the Promise will be rejected. Therefore it's adviseable to handle the promise rejections. With this in mind, a special type of error has been created: MailTransportError. Its constructor can accept no arguments, a string message, an Error object or both message and causing error (in this order). You can therefor send mails like this:

const MailTransportError = require("usend").MailTransportError;

usend.sendMail(messageConfig, data)
    .catch(e => {
        // throw new MailTransportError();
        throw new MailTransportError(e);
        // throw new MailTransportError("oops");
        // throw new MailTransportError("oops", e);
    });