Skip to main content
Pre-release

This release is a pre-release and may not be stable for production use.

imio.recipe.emailkit

A zc.buildout recipe that gives every imio.emailkit consumer three scripts: bin/compile-emails, bin/check-emails and bin/preview-emails.

Usage

[buildout]
parts = ... emails

[emails]
recipe = imio.recipe.emailkit
eggs = ${instance:eggs}
# compile-on-install = false   (default)
# kit-mode = path | copy       (default: path)
# node-bin = node              (resolution: PATH by default)

The part scans eggs for distributions whose ZCML registers <emailkit:templates>, records each one's emails//templates/ paths, and writes the three scripts using the design kit from imio.emailkit.

A plain buildout run invokes no Node, touches no emails/ directory, and imports no consumer code. compile-on-install opts in to compiling at install time; default false.

Options

Option Default What it does
eggs required distributions to scan; normally ${instance:eggs}.
kit-mode path how the design kit wires into a consumer's Maizzle build.
node-bin node the Node executable; npm/npx sit beside it.
compile-on-install false run compile-emails as an install step. Opt-in.

Every option is also a script flag (--kit-mode copy).

The scripts

bin/compile-emails [--package NAME] [--watch] [--new NAME]

Steps: wire the kit, npm ci if node_modules is stale, npx maizzle build, then copy the plaintext twins back in, since maizzle build empties its output directory. Exits non-zero on failure.

--watch delegates to Maizzle's dev server, which shows build-time output: raw ${item/title}, unexpanded tal:repeat. Use preview-emails --watch for a real preview.

--new NAME scaffolds the four files a template needs: a .vue skeleton, a fixture, a golden placeholder, and a registration stub. It refuses to overwrite files without --force; the skeleton follows every authoring rule.

bin/check-emails [--package NAME]

The CI check. Two checks:

  1. Staleness. Snapshot the committed .pt files, build in place, diff, restore. Exit 1 with a per-file diff. Covers every .pt under the package, not just templates/.
  2. The authoring lint: python -m imio.emailkit.lint <paths>. A missing lint module fails this check. --no-lint skips it explicitly.

--lint-only runs the authoring lint alone; no Node needed.

bin/preview-emails [--package NAME] [--watch]

Compiles and renders every template through render() with its fixture, serving it with a language switcher and live reload.

It needs no ZODB and no zope.conf: a minimal ZCML load gives real placeholder substitution and real FR/NL/DE translations. Two things stay fake: portal_url is empty, and theme tokens use the kit's defaults (override with --theme token=value). For real site branding, use @@emailkit-preview.

--no-compile renders the committed .pt files as-is.

What a consumer addon has to do

Three things, once.

1. Lay the addon out as follows. emails/ sits inside the package or at the checkout root; both work.

src/acme/notifications/
├── emails/                     # dev only; prune it from the sdist
│   ├── package.json
│   ├── maizzle.config.js
│   ├── .kit/                   # generated; ignores itself
│   ├── twins/                  # hand-authored *.txt.pt, if any
│   └── src/templates/*.vue
└── templates/*.pt              # committed build output

2. Write emails/maizzle.config.js against ./.kit/. Three imports and one override. recipe/tests/consumer is a working example.

import { defineConfig } from '@maizzle/framework'
import { fileURLToPath } from 'node:url'
import { dirname, resolve } from 'node:path'

import { kitBaseConfig } from './.kit/maizzle.config.base.js'

const here = dirname(fileURLToPath(import.meta.url))
const kit = kitBaseConfig()

export default defineConfig({
  ...kit,
  output: { ...kit.output, path: resolve(here, '..', 'templates') },
})

compile-emails materializes emails/.kit/ before every build, identical in both modes, so a consumer's config never mentions which one. path mode re-exports the kit from the installed egg (zero-copy); copy mode holds the kit itself. Consumers never vendor kit files.

Do not add "type": "module" to emails/package.json: jiti must transpile the kit file's ESM syntax, since in path mode it lives outside any npm tree.

3. Register in ZCML and run the checks in CI:

<configure
    xmlns="http://namespaces.zope.org/zope"
    xmlns:emailkit="http://namespaces.imio.be/emailkit"
    i18n_domain="acme.notifications"
    >
  <include package="imio.emailkit" file="meta.zcml" />
  <emailkit:templates>
    <emailkit:template name="welcome" subject="[email_subject_welcome] Welcome" />
  </emailkit:templates>
</configure>
bin/check-emails --package acme.notifications

kit-mode: which one?

Use path unless something forces you off it: zero-copy, and it cannot go stale. copy is a verified, byte-identical fallback, for when Maizzle or packaging stops resolving files outside the npm tree.

Development

This distribution is a sibling directory in the imio.emailkit repository, released separately. Its tests run in two environments: no single one has both buildout and the Plone runtime.

make recipe-test      # both runs; the union covers every test
make buildout-test    # the full buildout acceptance test, end to end
make buildout-clean   # remove everything that writes

test-buildout.cfg at the repository root is the harness. test-buildout-pypi.cfg is the same thing resolving from PyPI — the literal "git clone && buildout".

Metadata

Release files for imio.recipe.emailkit 1.0.0b5

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for imio.recipe.emailkit 1.0.0b5
File Size Uploaded
imio_recipe_emailkit-1.0.0b5.tar.gz 55.7 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for imio.recipe.emailkit 1.0.0b5
File Interpreter ABI Platform
imio_recipe_emailkit-1.0.0b5-py3-none-any.whl Python 3 none any Details

Total release size: 101.0 kB

Release files / imio_recipe_emailkit-1.0.0b5.tar.gz

Download URL imio_recipe_emailkit-1.0.0b5.tar.gz
Size 55.7 kB
Tags Source
SHA-256 checksum
How to use checksums
3d1d1d66c5a2a99cfa8f7150d1bb08d3237ca3728943c064b999007cc7082fae
BLAKE2b-256 checksum
How to use checksums
074e673aee4304841720be4202bffca1fe51fd0130375af0e1afeda390c8b5c8
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.12.8

Release files / imio_recipe_emailkit-1.0.0b5-py3-none-any.whl

Download URL imio_recipe_emailkit-1.0.0b5-py3-none-any.whl
Size 45.2 kB
Tags Python 3
SHA-256 checksum
How to use checksums
2a9f2fffab7327476f5277cfda011bc3598fb98cb3e1a564d52b9608ad8b7635
BLAKE2b-256 checksum
How to use checksums
8f7d439a372ae4d1eced42b8504314c51605131fded0fd0683ec30b9737ec3bb
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/7.0.0 CPython/3.12.8
Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page