| name | foundation-emails |
| description | Build responsive HTML emails using Foundation for Emails (ZURB) — Inky markup, Sass theming, Gulp build. Use when the user has chosen Foundation as their email framework, or is working in an existing Foundation for Emails project. |
Foundation for Emails Workflow
Foundation for Emails (https://github.com/foundation/foundation-emails) is ZURB's responsive email framework. Uses Inky (semantic tags → tables), Sass for theming, and Gulp for build/inline.
Scaffolding a new project
git clone https://github.com/foundation/foundation-emails-template.git my-emails
cd my-emails
rm -rf .git
npm install
git init && git add -A && git commit -m "Initial scaffold"
npm start
The ZURB template is legacy — node-sass often needs rebuilding. Prefer Node 14–16 if available; on Node 18+ try npm install --legacy-peer-deps and fall back to npm rebuild node-sass if needed.
Project layout
src/
├── assets/
│ ├── img/
│ └── scss/
│ ├── _settings.scss # Foundation variables (palette, typography, spacing, buttons)
│ └── app.scss # Custom styles
├── layouts/
│ └── default.html # Panini wrapper
├── pages/
│ └── *.html # Templates (Inky markup)
└── partials/
└── *.html # Reusable fragments (header, footer)
dist/ # Compiled, inlined output
Core Inky tags
| Tag | Compiles to | Use for |
|---|
<container> | 580px outer wrapper table | Wrap the email body |
<row> | 12-col grid row | Group columns horizontally |
<columns small="12" large="6"> | Responsive column | Columns in a row must sum to 12 |
<button href="..."> | Bulletproof VML button | Primary/secondary CTAs |
<callout> | Padded/coloured panel | Highlights, tips, warnings |
<menu><item href="">X</item></menu> | Horizontal nav | Header links, footer nav |
<spacer size="16"> | Vertical spacing row | Replaces margin/padding hacks |
<wrapper> | Full-width bleed section | Coloured bands outside container |
<center> | Centers block children | Hero images, buttons |
<h-line> | Horizontal rule | Dividers |
Template skeleton
---
subject: "Your subject line"
---
<span class="preheader" style="display:none !important;visibility:hidden;mso-hide:all;font-size:1px;color:#ffffff;line-height:1px;max-height:0;max-width:0;opacity:0;overflow:hidden;">
Preview text — 80–90 chars
</span>
<container>
<row class="header">
<columns small="12">
<center><img src="{{root}}assets/img/logo.png" alt="Company" width="140"></center>
</columns>
</row>
<row>
<columns small="12">
<h1>Headline</h1>
<p>Body copy.</p>
<center>
<button href="https://example.com" class="expand">Call to action</button>
Unsubscribe
Preferences
Theming
Edit src/assets/scss/_settings.scss:
$primary-color: #2c3e50;
$secondary-color: #e74c3c;
$global-width: 580px;
$body-background: #f3f3f3;
$container-background: #ffffff;
$global-font-family: 'Helvetica Neue', Helvetica, Arial, sans-serif;
$header-color: #0a0a0a;
$button-background: $primary-color;
$button-color: #ffffff;
$button-padding: 8px 16px 8px 16px;
$button-radius: 3px;
Custom component styles go in app.scss — remember styles must be inlinable (avoid complex selectors, pseudo-classes beyond :hover).
Build commands
npm start
npm run build
After npm run build, dist/*.html contains the final inlined HTML ready to paste into an ESP or send via API.
Known pitfalls
- Columns not summing to 12 → Inky silently produces broken layout. Always check math.
{{root}} paths breaking in dist/ → Panini context not set; check panini task in gulpfile.
- node-sass errors on modern Node →
npm rebuild node-sass or switch to a version manager (nvm) and use Node 16.
- Styles not inlined → confirm
inliner task ran (npm run build, not npm start).
- Button styles lost →
_settings.scss variables must be set before @import 'foundation-emails'.
Hand off to email-client-gotchas for cross-client quirks and inline-and-test for preview/send workflow.