Scow HTML Email Inliner & Bundler
raw JSON →Scow is an HTML email inliner and bundler designed to prepare modern HTML and CSS for consistent rendering across a diverse range of email clients. Historically, email clients exhibit inconsistent support for external stylesheets and `<style>` tags within the `<head>` of an HTML document, often stripping them entirely. This necessitates that CSS be applied directly as `style` attributes on individual HTML elements for reliable presentation. Scow automates this critical inlining process, abstracting away the complexities of email client rendering quirks. Additionally, it aims to bundle associated assets like images, potentially converting them to data URIs. Currently available as `4.0.0-alpha.5`, the package is undergoing active alpha development, meaning its API and feature set are subject to change without strict adherence to semantic versioning until a stable release. Its core value lies in streamlining the email development workflow, ensuring that visually rich emails display as intended, despite the varied and often outdated rendering engines used by different email services and applications.
Warnings
breaking Scow is currently in an alpha release phase (e.g., `4.0.0-alpha.5`). This means the API is not yet stable and is subject to frequent and significant breaking changes without prior notice. Use in production with extreme caution. ↓
gotcha Email clients vary greatly in their support for CSS properties, even when inlined. While scow handles the inlining mechanism, it does not guarantee that all CSS properties will be rendered correctly by every email client (e.g., Outlook's reliance on Word's rendering engine). ↓
gotcha Incorrect handling of external stylesheets or image paths can lead to broken assets in the final email. Scow aims to bundle assets, but relative paths or unresolvable URLs will result in missing content. ↓
deprecated Older versions of email inliners (and potentially early alpha versions of scow) might have defaulted to CommonJS `require()` syntax. As of recent Node.js versions and the general shift in the JavaScript ecosystem, ESM `import` is the preferred and often only supported module system for newer libraries. ↓
Install
npm install scow yarn add scow pnpm add scow Imports
- inline wrong
const scow = require('scow'); const inlinedHtml = scow.inline(...);correctimport { inline } from 'scow'; - ScowConfig
import type { ScowConfig } from 'scow'; - bundleAssets
import { bundleAssets } from 'scow';
Quickstart
import { inline } from 'scow';
import { readFileSync } from 'node:fs';
import { join } from 'node:path';
async function processEmailTemplate() {
const templatePath = join(process.cwd(), 'email-template.html');
const htmlContent = readFileSync(templatePath, 'utf-8');
// Assume email-template.html looks something like:
// <html><head><style>h1 { color: #1a73e8; }</style></head><body><h1>Hello, World!</h1></body></html>
try {
const inlinedHtml = await inline(htmlContent, {
// Optional configuration, e.g., to keep original style tags for media queries
// keepOriginalStyleTags: true,
// Optional: Specify base URL for resolving relative paths if bundling external assets
// baseUrl: 'https://example.com/assets/',
});
console.log('Successfully inlined HTML:\n', inlinedHtml);
} catch (error) {
console.error('Error inlining email:', error);
}
}
processEmailTemplate();
// To make this runnable, create a file named 'email-template.html' in the same directory:
// <!-- email-template.html -->
// <!DOCTYPE html>
// <html>
// <head>
// <meta charset="utf-8">
// <title>Styled Email</title>
// <style type="text/css">
// body { font-family: sans-serif; margin: 0; padding: 20px; background-color: #f6f6f6; }
// .container { max-width: 600px; margin: 0 auto; background-color: #ffffff; padding: 20px; border-radius: 8px; box-shadow: 0 4px 8px rgba(0,0,0,0.1); }
// h1 { color: #333333; font-size: 24px; margin-bottom: 15px; }
// p { color: #555555; font-size: 16px; line-height: 1.5; }
// .button { display: inline-block; padding: 10px 20px; margin-top: 20px; background-color: #1a73e8; color: #ffffff; text-decoration: none; border-radius: 5px; }
// @media only screen and (max-width: 620px) {
// .container { width: 100% !important; border-radius: 0; }
// body { padding: 0; }
// }
// </style>
// </head>
// <body>
// <div class="container">
// <h1>Welcome to Our Service!</h1>
// <p>Thank you for signing up. We're excited to have you on board.</p>
// <p>Explore our features and get started today.</p>
// <a href="#" class="button">Get Started</a>
// </div>
// </body>
// </html>