Sending with attachments
You can attach files when sending with a template API or sending without a template API by adding an array of attachment objects to the attachments property of the API call. Each object includes:
| Property | Description |
|---|---|
| name | The filename shown to the receiver. eg. invoice-352.pdf |
| contentBlob | Base64-encoded string of the file content. Most languages have built-in tools for this (Ruby, .NET, Java, PHP). |
| attachmentId | Waypoint Attachment ID when attaching large files. |
| contentType | MIME Type for the file attachment. eg. application/pdf |
| cid | A Content ID turns the attachment into an inline attachment. The CID is the reference used to embed it in the email body. |
Using standard attachments
Section titled “Using standard attachments”Standard attachments are files sent alongside an email — not embedded in the body. PDFs and spreadsheets are typical examples; recipients have to open or download them separately.
To attach files, add an attachments array to your API call.
Emails using standard attachments must stay under 5 MB total (including the email body). See how to attach larger files.
Code example
Section titled “Code example”const fs = require('fs');
// Read and encode the file to base64const filePath = './order-receipt.pdf';const fileContent = fs.readFileSync(filePath);const base64Content = fileContent.toString('base64');
// Send the email with attachmentconst authHeader = 'Basic ' + Buffer.from(`${API_KEY_USERNAME}:${API_KEY_PASSWORD}`).toString('base64');
const options = { method: 'POST', headers: { 'Content-Type': 'application/json', Authorization: authHeader, }, body: JSON.stringify({ templateId: 'wptemplate_ABc123XYZ', to: 'jordan@usewaypoint.com', variables: { user: { displayName: 'Jordan', }, product: { title: 'Beechers Mac & Cheese', id: '02934203942', }, }, attachments: [ { name: 'order-receipt.pdf', contentBlob: base64Content, contentType: 'application/pdf', }, ], }),};
fetch('https://live.waypointapi.com/v1/email_messages', options) .then((res) => res.json()) .then((res) => console.log(res)) .catch((err) => console.error(err));Using large attachments
Section titled “Using large attachments”The 5 MB cap on standard attachments can be tight for files like custom reports, presentations, detailed invoices, or other high-quality assets.
For files over 5 MB, use the large attachment flow below instead. Growth plans support up to 10 MB, Pro plans up to 20 MB.
How it works:
POSTto v1/attachments API to create an attachment record. The response includes anuploadUrland anid.PUTyour file to theuploadUrl.POSTto v1/email_messages API to send your email, referencing theidin theattachmentsarray.
See the code example below.
Code example
Section titled “Code example”import fs from 'fs';
// File to uploadconst FILE_PATH = './reports/report-00000001.pdf';
async function executeUpload() { const file = fs.createReadStream(FILE_PATH); const stats = fs.statSync(FILE_PATH);
const authHeader = 'Basic ' + Buffer.from(`${API_KEY_USERNAME}:${API_KEY_PASSWORD}`).toString('base64');
// Create attachment URL const createRes = await fetch('https://live.waypointapi.com/v1/attachments', { method: 'POST', headers: { 'Content-Type': 'application/json', Authorization: authHeader, }, }); const createJson = await createRes.json();
const presignedUrl = createJson.data.uploadUrl; const attachmentId = createJson.data.id; console.log('Attachment created:', { attachmentId, presignedUrl });
// Upload file to the upload URL with file content type and file size await fetch(presignedUrl, { method: 'PUT', headers: { 'Content-Type': 'application/pdf', 'Content-Length': stats.size.toString(), Authorization: authHeader, }, body: file, duplex: 'half', });
// Send email with attachment ID, name, and file content type const emailMessageRes = await fetch('https://live.waypointapi.com/v1/email_messages', { method: 'POST', headers: { 'Content-Type': 'application/json', Authorization: authHeader, }, body: JSON.stringify({ to: 'jordan@usewaypoint.com', from: 'support@usewaypoint.com', bodyHtml: '<p>Your report is attached.</p>', subject: 'Your Report', attachments: [ { attachmentId: attachmentId, name: 'report-00000001.pdf', contentType: 'application/pdf', }, ], }), }); const emailData = await emailMessageRes.json(); console.log('Email message created:', emailData);}
executeUpload();Limitations
Section titled “Limitations”Large attachments require a Growth or Pro plan.
File size limits by plan:
- Free and Starter: Unavailable
- Growth: 10 MB
- Pro: 20 MB
Using inline attachments
Section titled “Using inline attachments”Inline attachments, usually images, are embedded directly in the email body so they render as part of the message.
The setup is the same as a standard attachment, with one addition: each attachment includes a cid (Content-ID), which you reference from the bodyHtml to embed it.
In the example below, note "cid": "emoji" referenced by <img src=\"cid:emoji\" />.
Code example
Section titled “Code example”const authHeader = 'Basic ' + Buffer.from(`${API_KEY_USERNAME}:${API_KEY_PASSWORD}`).toString('base64');
const options = { method: 'POST', headers: { 'Content-Type': 'application/json', Authorization: authHeader, }, body: JSON.stringify({ to: 'Jordan Tester <jordan@usewaypoint.com>', from: 'Waypoint Support <support@usewaypoint.com>', bodyHtml: '<h1>Hello from Waypoint <img src="cid:emoji" /></h1>', subject: 'Hello from Waypoint', attachments: [ { name: 'emoji.png', cid: 'emoji', contentType: 'image/png', contentBlob: 'iVBORw0KGgoAAAANSUhEUgAAABgAAAAYCAYAAADgdz34AAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAAApgAAAKYB3X3/OAAAABl0RVh0U29mdHdhcmUAd3d3Lmlua3NjYXBlLm9yZ5vuPBoAAANCSURBVEiJtZZPbBtFFMZ/M7ubXdtdb1xSFyeilBapySVU8h8OoFaooFSqiihIVIpQBKci6KEg9Q6H9kovIHoCIVQJJCKE1ENFjnAgcaSGC6rEnxBwA04Tx43t2FnvDAfjkNibxgHxnWb2e/u992bee7tCa00YFsffekFY+nUzFtjW0LrvjRXrCDIAaPLlW0nHL0SsZtVoaF98mLrx3pdhOqLtYPHChahZcYYO7KvPFxvRl5XPp1sN3adWiD1ZAqD6XYK1b/dvE5IWryTt2udLFedwc1+9kLp+vbbpoDh+6TklxBeAi9TL0taeWpdmZzQDry0AcO+jQ12RyohqqoYoo8RDwJrU+qXkjWtfi8Xxt58BdQuwQs9qC/afLwCw8tnQbqYAPsgxE1S6F3EAIXux2oQFKm0ihMsOF71dHYx+f3NND68ghCu1YIoePPQN1pGRABkJ6Bus96CutRZMydTl+TvuiRW1m3n0eDl0vRPcEysqdXn+jsQPsrHMquGeXEaY4Yk4wxWcY5V/9scqOMOVUFthatyTy8QyqwZ+kDURKoMWxNKr2EeqVKcTNOajqKoBgOE28U4tdQl5p5bwCw7BWquaZSzAPlwjlithJtp3pTImSqQRrb2Z8PHGigD4RZuNX6JYj6wj7O4TFLbCO/Mn/m8R+h6rYSUb3ekokRY6f/YukArN979jcW+V/S8g0eT/N3VN3kTqWbQ428m9/8k0P/1aIhF36PccEl6EhOcAUCrXKZXXWS3XKd2vc/TRBG9O5ELC17MmWubD2nKhUKZa26Ba2+D3P+4/MNCFwg59oWVeYhkzgN/JDR8deKBoD7Y+ljEjGZ0sosXVTvbc6RHirr2reNy1OXd6pJsQ+gqjk8VWFYmHrwBzW/n+uMPFiRwHB2I7ih8ciHFxIkd/3Omk5tCDV1t+2nNu5sxxpDFNx+huNhVT3/zMDz8usXC3ddaHBj1GHj/As08fwTS7Kt1HBTmyN29vdwAw+/wbwLVOJ3uAD1wi/dUH7Qei66PfyuRj4Ik9is+hglfbkbfR3cnZm7chlUWLdwmprtCohX4HUtlOcQjLYCu+fzGJH2QRKvP3UNz8bWk1qMxjGTOMThZ3kvgLI5AzFfo379UAAAAASUVORK5CYII=', }, ], }),});Activity logs
Section titled “Activity logs”On a message log in your Activity, any attachments on that send show up as filenames beneath the message preview.
Logs only show filenames (even for inline attachments) — Waypoint doesn’t store the file contents.

Limitations
Section titled “Limitations”- Total message size is capped per plan: 2 MB on Free and Starter, 5 MB on Growth and Pro, including attachments.
- Attachments aren’t currently supported for batch sending.
- The following file extensions aren’t supported and will block the email from being sent: .ade, .adp, .app, .asp, .bas, .bat, .cer, .chm, .cmd, .com, .cpl, .crt, .csh, .der, .exe, .fxp, .gadget, .hlp, .hta, .inf, .ins, .isp, .its, .js, .jse, .ksh, .lib, .lnk, .mad, .maf, .mag, .mam, .maq, .mar, .mas, .mat, .mau, .mav, .maw, .mda, .mdb, .mde, .mdt, .mdw, .mdz, .msc, .msh, .msh1, .msh2, .mshxml, .msh1xml, .msh2xml, .msi, .msp, .mst, .ops, .pcd, .pif, .plg, .prf, .prg, .reg, .scf, .scr, .sct, .shb, .shs, .sys, .ps1, .ps1xml, .ps2, .ps2xml, .psc1, .psc2, .tmp, .url, .vb, .vbe, .vbs, .vps, .vsmacros, .vss, .vst, .vsw, .vxd, .ws, .wsc, .wsf, .wsh, .xnk.