npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

payload-email-template

v1.2.1

Published

A plugin for Payload CMS to create email templates based on React Email

Readme

Payload Email Template Plugin 🚀

npm version npm downloads MIT License


A powerful, visual, and block-based email template builder plugin for Payload CMS — built on top of React Email. Design beautiful, dynamic, and localized email templates with ease! ✨


✨ Features

  • 🧩 Visual, block-based email template builder (no raw JSX required)
  • 🏗️ Custom blocks: Heading, Button, Container, Image, Row, Section, Text, and more
  • 🔧 Dynamic macros: Variables, functions, dates, conditions, loops, and config values
  • 👀 Preview: See your email as you build, with device and zoom controls
  • 🌍 Localization: Localize templates and content
  • 🔌 API endpoints: Generate both HTML and PlainText before sending your email

📦 Installation

pnpm add payload-email-template
# or
yarn add payload-email-template
# or
npm install payload-email-template

🚀 Getting Started

Add the plugin to your Payload config in the plugins array:

import { emailTemplatePlugin } from 'payload-email-template'

export default buildConfig({
  // ...other config
  plugins: [
    emailTemplatePlugin({
      enabled: true,
      imageCollectionSlug: 'media', // (optional) collection for image uploads
      previewBreakpoints: [
        // (optional) default breakpoints
        { name: 'mobile', label: 'Mobile', width: 375, height: 667 },
        { name: 'desktop', label: 'Desktop', width: 1440, height: 900 },
      ],
      disableStyle: false, // (optional) allow custom style overrides, default: false
      macros: {
        // (optional) dynamic content for variables, functions, and config
        variables: {
          companyName: 'Your Company',
          user: { firstName: 'John', lastName: 'Doe' },
        },
        functions: {
          greet: (name) => `Hello, ${name}!`,
          formatPrice: (price) => `$${price.toFixed(2)}`,
        },
        config: {
          appName: 'My App',
          version: '1.0.0',
        },
      },
      // ...other options
    }),
  ],
})

🖼️ Demo

Demo 1

Demo 2


⚙️ Plugin Options

| Option | Type | Default | Description | | --------------------- | ------- | ---------------------------------------- | --------------------------------------------------------------------------- | | enabled | boolean | true | Enable/disable the plugin | | imageCollectionSlug | string | 'media' | Collection slug for image uploads | | previewBreakpoints | array | see example | Device preview sizes for the preview tab | | disableStyle | boolean | false | Disable custom style overrides | | macros | object | {} | Dynamic content configuration (variables, functions, config) | | endpointAccess | Access | ({req}) => Boolean(req.user) | Default access control for the /api/email-templates/:id/generate endpoint | | collectionAccess | Access | { read: ({req}) => Boolean(req.user) } | Default access control for email-templates collection |


🛠️ Usage

🧱 Blocks

Configure blocks (Heading, Button, Container, etc.) to build your template. Each block has configurable fields (content, style, alignment, etc.). Blocks can be nested for complex layouts.

🌍 Localization

If you enable localization in your Payload config, the plugin will automatically make text-related template fields localizable.

👀 Preview

The template can be previewed in the Preview tab. You can also use the controls to toggle mode, device, and zoom.


🔌 API Endpoints

Generate Email Template

You can trigger rendering the email template by sending a POST request to the following endpoint:

POST /api/email-templates/:id/generate

You will receive both html and plainText versions of the template:

{
  "html": "<html>...</html>",
  "plainText": "..."
}

Then you can send it via your email provider.


⚙ Local Api

Generate Email Template

It's also possible to render the email template by calling renderEmailTemplate directly in the back-end, skipping the http request in that case.

import { renderEmailTemplate } from "payload-email-template"

// const emailTemplate = await req.payload.find({
//   collection: 'email-templates',
//   ...
// })

const html = await renderEmailTemplate({
  data: emailTemplate,
  locale: 'en',
  format: 'html',
  macroContext: {
    variables: { ... },
    functions: { ... },
    config: { ... }
  }
})

🔧 Macros

The plugin supports powerful dynamic content through macros that can be used in email subjects, headings, and text blocks.

Macro Types

1. Variables - {{variableName}}

Access data from your macro configuration:

{{companyName}} → "Acme Corporation"
{{user.firstName}} → "John"

2. Config Values - {{@config('key')}}

Access plugin configuration values:

{{@config('appName')}} → "My Awesome App"
{{@config('version')}} → "1.0.0"

3. Date Functions - {{@date('format')}}

Format current date and time:

{{@date('YYYY-MM-DD')}} → "2024-01-15"
{{@date('MMMM Do, YYYY')}} → "January 15th, 2024"

4. Functions (Server-side only)

Transform data with custom functions:

{{@uppercase('hello')}} → "HELLO"
{{@greet('John')}} → "Hello, John!" (if configured)

5. Conditional Content

Show content based on conditions:

  • Set up conditions in the macro block interface
  • Define content for true/false scenarios
  • Useful for personalized content

6. Loops

Repeat content for data collections:

  • Configure collection data source
  • Define template for each item
  • Great for product lists, etc.

Usage Locations

✅ Email Subjects: "Welcome to {{companyName}}, {{user.firstName}}!"

✅ Heading Blocks: Mix text, links, and macros in headings

✅ Text Blocks: Inline macros alongside regular text and links

✅ Macro Blocks: Dedicated blocks for complex conditions and loops

Runtime Context

You can also pass runtime macro context when generating emails:

// POST /api/email-templates/:id/generate
{
  "macroContext": {
    "variables": {
      "user": { "firstName": "Jane" },
      "orderTotal": "$99.99"
    }
  }
}

Runtime context takes precedence over plugin configuration.


🤝 Contributing

Contributions are welcome! Please open issues or pull requests for bug fixes, features, or documentation improvements.


📄 License

MIT