{"id":17942,"library":"scow","title":"Scow HTML Email Inliner & Bundler","description":"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.","status":"active","version":"4.0.0-alpha.5","language":"javascript","source_language":"en","source_url":"https://github.com/gakimball/scow","tags":["javascript","scow","email","inline","bundle","zip","assets"],"install":[{"cmd":"npm install scow","lang":"bash","label":"npm"},{"cmd":"yarn add scow","lang":"bash","label":"yarn"},{"cmd":"pnpm add scow","lang":"bash","label":"pnpm"}],"dependencies":[],"imports":[{"note":"The primary `inline` function for processing HTML is typically a named export. While CJS `require` might work in some contexts, modern Node.js and bundler setups prefer ESM `import`.","wrong":"const scow = require('scow');\nconst inlinedHtml = scow.inline(...);","symbol":"inline","correct":"import { inline } from 'scow';"},{"note":"For TypeScript users, import the configuration interface to ensure type safety when defining options.","symbol":"ScowConfig","correct":"import type { ScowConfig } from 'scow';"},{"note":"This function is expected to handle asset bundling (e.g., converting images to data URIs or local paths) and might be a separate utility within the library.","symbol":"bundleAssets","correct":"import { bundleAssets } from 'scow';"}],"quickstart":{"code":"import { inline } from 'scow';\nimport { readFileSync } from 'node:fs';\nimport { join } from 'node:path';\n\nasync function processEmailTemplate() {\n  const templatePath = join(process.cwd(), 'email-template.html');\n  const htmlContent = readFileSync(templatePath, 'utf-8');\n\n  // Assume email-template.html looks something like:\n  // <html><head><style>h1 { color: #1a73e8; }</style></head><body><h1>Hello, World!</h1></body></html>\n\n  try {\n    const inlinedHtml = await inline(htmlContent, {\n      // Optional configuration, e.g., to keep original style tags for media queries\n      // keepOriginalStyleTags: true,\n      // Optional: Specify base URL for resolving relative paths if bundling external assets\n      // baseUrl: 'https://example.com/assets/',\n    });\n    console.log('Successfully inlined HTML:\\n', inlinedHtml);\n  } catch (error) {\n    console.error('Error inlining email:', error);\n  }\n}\n\nprocessEmailTemplate();\n\n// To make this runnable, create a file named 'email-template.html' in the same directory:\n// <!-- email-template.html -->\n// <!DOCTYPE html>\n// <html>\n// <head>\n//   <meta charset=\"utf-8\">\n//   <title>Styled Email</title>\n//   <style type=\"text/css\">\n//     body { font-family: sans-serif; margin: 0; padding: 20px; background-color: #f6f6f6; }\n//     .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); }\n//     h1 { color: #333333; font-size: 24px; margin-bottom: 15px; }\n//     p { color: #555555; font-size: 16px; line-height: 1.5; }\n//     .button { display: inline-block; padding: 10px 20px; margin-top: 20px; background-color: #1a73e8; color: #ffffff; text-decoration: none; border-radius: 5px; }\n//     @media only screen and (max-width: 620px) {\n//       .container { width: 100% !important; border-radius: 0; }\n//       body { padding: 0; }\n//     }\n//   </style>\n// </head>\n// <body>\n//   <div class=\"container\">\n//     <h1>Welcome to Our Service!</h1>\n//     <p>Thank you for signing up. We're excited to have you on board.</p>\n//     <p>Explore our features and get started today.</p>\n//     <a href=\"#\" class=\"button\">Get Started</a>\n//   </div>\n// </body>\n// </html>","lang":"typescript","description":"This quickstart demonstrates how to use `scow` to inline CSS styles from a `<style>` block in an HTML email template directly into the HTML elements' `style` attributes, preparing it for various email clients. It also shows basic error handling."},"warnings":[{"fix":"Always pin to an exact alpha version (e.g., `\"scow\": \"4.0.0-alpha.5\"`) and regularly check the project's GitHub repository for API updates and migration guides before upgrading.","message":"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.","severity":"breaking","affected_versions":">=4.0.0-alpha.0"},{"fix":"Thoroughly test all inlined email templates across multiple email clients and devices (e.g., using Litmus or Email on Acid) to ensure consistent rendering. Design emails with a 'lowest common denominator' approach, favoring widely supported CSS properties.","message":"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).","severity":"gotcha","affected_versions":">=4.0.0-alpha.0"},{"fix":"Ensure all external assets (images, fonts, etc.) are hosted on publicly accessible URLs. Use the `baseUrl` configuration option if your HTML template uses relative paths that need to be resolved against a specific base URL for asset bundling.","message":"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.","severity":"gotcha","affected_versions":">=4.0.0-alpha.0"},{"fix":"Always use `import { ... } from 'scow';` for module loading. If encountering issues in a CommonJS environment, ensure your project is configured for dual ESM/CJS support or use dynamic `import()` for ESM-only packages.","message":"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.","severity":"deprecated","affected_versions":"<4.0.0"}],"env_vars":null,"last_verified":"2026-04-23T00:00:00.000Z","next_check":"2026-07-22T00:00:00.000Z","problems":[],"ecosystem":"npm","meta_description":null,"install_score":null,"install_tag":null,"quickstart_score":null,"quickstart_tag":null}