38 comments

[ 5.0 ms ] story [ 73.7 ms ] thread
Hi looks nice. I am in the process of building a email management system for a client with a small coaching base, and decided to go with Maily to integrate with the React and resend stack.

I hadn't heard of beefree or unlayer before this post. What would you say are the reasons we would want to use Templatical over our current integration or Beefree/unlayer?

Thanks.

does it store our data persistently on your server/system
What do you use for the onboarding guide?
This is really nice, thanks for building. I will use that heavily :)
I got you a gold star ;) Excited to use this, as I've been frustrated by vendor lock-in for this exact use case.
This is cool!

I looked for this in the past. This is the main reason we bothered with mailchimp/hubspot -- simply the ability for nontechnical marketing people to put together nice emails, and the trust that we won't need an engineer to troubleshoot email formatting on their behalf. I remember trying some OSS tools at the time (8 years ago?) and there were some templates we used but then when we wanted to modify them, the broken-ness of email html/css standards made it really hard to test.

I know the standards and practice around this are a moving target, though, so I hope you can find a model to sustain and expand this, without charging for delivery/contact list numbers like MailChimp or other incumbents.

I remember doing a MailChimp "clone" in Laravel some 12 years ago and implementing an email builder using their templates
Picking MJML as the output format instead of raw HTML is the move. That's the layer where the cross-client pain has already been solved by people more patient than any of us.

Two questions:

1. How extensible is the block system? Can consumers define their own block types with custom MJML output, or are you limited to the built-ins?

2. Any plans for a headless render path (JSON → MJML → HTML on a server) for transactional emails generated from templates at send time?

Either way, bookmarking. Been waiting for someone to do this without the SaaS tax.

Thanks — yes on both, and both already exist today.

1. Custom block extensibility: full. You define a custom block as a schema — typed fields displayed in the editor (text, textarea, image, color, number, select, boolean, repeatable that contains basic fields) plus a Liquid template that emits HTML using those field values. The editor auto-renders the form for marketers to fill in, then runs the Liquid against those values to show a live preview on the canvas — so consumers don't write a Vue component themselves. The renderer wraps that HTML in <mj-text>, so it still goes through MJML's table layer for cross-client rendering. Optional dataSource.onFetch lets the block hit your API at render time, so use user can fetch custom block contents from existing data source — instead of having to manually type values into every field. Check out the docs and playground for custom blocks usage.

2. Headless render path: that's exactly what @templatical/renderer is. Separate package, zero UI dependency, pure JSON -> MJML conversion. You store the JSON tree in your storage; on the backend you pass it to renderToMjml() and get MJML back. Since MJML has compiler libraries in almost every language, you compile MJML to HTML yourself whenever. Currently the renderer is TypeScript-only (browser + Node.js); porting to other languages as first-party packages is on the roadmap.

The whole shape — store JSON in your DB, render at send time on your server, send via your own provider — is the transactional flow you described.

Really cool work. Quick question: is this built on top of React Email?
This is great, i've been wanting someone to do this for a while, and was tempted to myself
This looks great! So glad the output is MJML. I will have to see how I can embed it in the project I am working on as I have been wanting to add the feature for clients to build out their own emails or customize some of the standard templates. It will at least be a big help in my own admin UI to start.
Looks good! Do you have an MCP or API in your roadmap? The reason: managing a lot of templates and their placeholders can get out of hand pretty quickly and agents can be a good way to deal with the complexity.

I'd love to try this with sendops.dev although I'm not sure how it's going to work with the git backed templating it has.

This is really awesome. I'm showing this to my marketing team - we were looking for something similar in the past too. I've had the pleasure of attempting to build fancy marketing emails and a signature and I never wanna look at a Word Table in my life again.
(comment deleted)
I was thinking this is so nice but too bad I can't use it because I'm so deep into Unlayer. Then I see the the migration page :)
(comment deleted)
The migration page is so good. Being stuck in Unlayer is a real thing, and seeing a clear path out makes this much more tempting to adopt.
As someone who built a similar open source project (grapesjs), this looks really good

Even with LLMs, generating raw HTML emails that render correctly across major email clients is still surprisingly hard, so great choice going with MJML.

Holy shit, it's you! Thank you, that genuinely means a lot coming from you!

GrapesJS is the forever OG that proved this whole space could be an embeddable SDK rather than a paywalled SaaS. It also standardized the palette/canvas/inspector layout that every serious visual builder now ships by default — including Templatical. I took direct inspiration from a few other patterns too: the block-as-first-class-citizen model, and the trait system, which maps almost 1:1 to how Templatical's custom blocks expose typed fields into the inspector.

And yeah — agreed on MJML. Building email layouts that work for most clients is notoriously hard. I think the people who built MJML absorbed an enormous amount of pain so the rest of us don't have to.

Huge respect for what you built.

This is great a great idea !! I starred it on github.
YES! This is so needed. Also very happy to see it's Vue + TipTap. Great choices.