Stylizing ActionMailers with Maizzle

I’ve been using Tailwind CSS for all my new projects, and I’ve been migrating my other projects over slowly. With Tailwind’s Rails gem, it’s been incredibly easy to drop in Tailwind, include my old CSS, and then move pages over. Tailwind is incredibly deferential to other CSS frameworks because it has a unique utility system, rather than trying to redefine the .button class yet again. Maizzle is a tool, written in Javascript, that takes Tailwind styled HTML for a mailer, and generates hardcoded styles. It optimizes for inboxes, so it makes some default decisions, such as column width. If you have an existing theme in your app, you can easily customize all your mailers to match your website’s theme and design.

How I’m using it

I purchased one of the theme packs from the craftingemails as a great starting point. One nice thing about Maizzle is that you can bring your CSS, and it will add the styles so that it looks correct in as many email clients as possible. I added my theme colors to make the templates match my project.

Setting it up

If you’ve already set up Rails on your machine, with Tailwind CSS, you should have the correct version of node setup. You can follow the directions at https://maizzle.com/docs/introduction, but here’s what I did.

First, download the email template or the starter version from GitHub.

Then, install maizzle and the dependencies:

$ npm install

Then, start the development server, which watches the source folder, and builds them.

$ maizzle serve

The one change necessary is to change the baseURL in the config.production.js file. Set it to an empty string so that nothing is prepended for image tags or links.

module.exports = {
  baseURL: "",
  // ... other options
}

Designing the templates

Since Maizzle just uses CSS, we can take a basic HTML template, and make it look great. This means you’ll want to change the views/layouts/mailer.html.erb to get rid of all the boilerplate to just 1 line:

<%= yield %> 

All the header and HTML tags will be in each email template.

When designing the template in the maizzle folder, you’ll need to create dummy data to fill in. When you want to replace the data in the actual template that you’ll copy into your Rails app, you could manually add the ERB tags. You could also use Maizzle’s built-in preprocessors to use dummy data for development and actual ERB tags in the production build. For example, the Maizzle starter on GitHub has a transactional template that includes the logo. In Rails, we’ll want to use the asset_path to the icon instead of a local path.

Here is the icon:

 <img src="images/maizzle.png" width="70" alt="Maizzle" class="max-w-full align-middle [border:0]">

If we test the page.env value, we can select the right tags:

<if condition="page.env === 'production'">
     <img src="<%= asset_path('maizzle.png') %>" width="70" alt="Maizzle" class="max-w-full align-middle [border:0]">
</if>
<if condition="page.env !== 'production'">
     <img src="images/maizzle.png" width="70" alt="Maizzle" class="max-w-full align-middle [border:0]">
</if>

Now, you can see the image when you’re designing the template, but when it’s built for distribution, it includes the ERB tag, so you can copy and paste it into your mailer’s view, without have to tweak anything.

Occasionally, you don’t mind the ERB tags in the design, so you can just add them and know they’ll be converted on the Rails side.

Example of ERB tags in the output during design
Example of ERB tags in the output during design

Move Into Rails

Once you’ve got your design working, you should run the build command:

$ maizzle build production

This will optimize the CSS in the templates, and perform any switching we needed for the Rails side.

Look for the template in the dist folder. Copy all the HTML from the template, and the preview the email with your app’s Rails mailer previews.

Fancy Email Templates

Now, you have prettier looking email templates generated with your Tailwind theme. This should make all your transactional emails feel on brand when you correspond with your customers.

Leave a Reply