LoginSignup
21
17

More than 5 years have passed since last update.

RailsでFoundation for Emails 2.0を使ってレスポンシブなHTMLメールを送る

Posted at

 この記事はトレタ Advent Calendar 2016の24日目の記事になります。メリークリスマス!

 今時のメールは大体HTMLメールなのですが、これが結構な曲者です。HTMLメールはブラウザ以上に互換性が低く、色々な罠があります。

 RailsではActionMailerがHTMLメールをサポートしていますが、あまり深いところは助けてくれません。そこでいくつかのツールを合わせて解決して見ます。

HTMLメールの罠

  • CSSの挙動がブラウザと異なる場合がある
  • メール用のResponsive CSSを用意する必要がある
  • CSSはclassではなく、styleでインライン展開する
  • Asset pipelineを使うにはちょっと細工が必要
  • HTMLメールを作るにあたって知っておきたいことにまとまっています

メール用CSSフレームワーク

ブラウザではbootstrapFoundationなど、レスポンシブCSSフレームワークが流行しています。HTMLメール向けもブラウザ向けほど数は多くありませんが、同じようなフレームワークがリリースされています。

 HTMLメールはそれほど表現力は高くないので、ブラウザのCSSフレームワークに比べて能力の差は大きくありません。

Foundation for Emails 2.0

 今回はFoundation for Emailを使って見ます。前はZurb Inkと呼ばれていました。

 Foundation for EmailはSCSSで構築されているので、sass-railsを使いましょう。CSSよりSCSSの方がカスタマイズしやすいのでオススメです。

Railsに導入する

 Foundation for EmailのGemはないので、sass-railsだけをGemfileに追加します

gem 'sass-rails', '~> 5.0'

 続いてFoundation for Emailをダウンロードします。
https://github.com/zurb/foundation-emails/releases から最新版をダウンロードして適当なフォルダに展開します。使うのはSCSSディレクトリだけなので、これをassetsの下に移動します。

mkdir $(RAILS_ROOT)/assets/stylesheets/mailer
mv $(解凍したディレクトリ)/scss $(RAILS_ROOT)/assets/stylesheets/mailer/foundation

次にMailerで使うSCSSファイルを作ります。

$(RAILS_ROOT)/assets/stylesheets/mailer/common.scss
@import "_foundation-custom";
@import "foundation/foundation-emails";

// 以下に好きなSCSSを書いてね & 例
.footer {
  hr {
    width: 94%;
    margin: 40px auto 10px auto;
    height: 2px;
    background-color: #dddddd !important;
    border: 0 !important;
  }
  p, a {
    font-size: 12px;
    color: #cccccc !important;
  }
}
$(RAILS_ROOT)/assets/stylesheets/mailer/_foundation-custom.scss

// _global.scssを参考にFoundationをカスタマイズ
$primary-color: #ff0000;

 最後にlayoutファイルを準備します。公式にテンプレートを参考にしました

app/views/layouts/mailer.html.erb
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml" lang="en" xml:lang="en">
  <head>
    <%= stylesheet_link_tag "mailer/common", media: "all" %>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
    <meta name="viewport" content="width=device-width">
    <title><%= yield :title %></title>
  </head>
  <body>
    <%= yield %>
    <!-- prevent Gmail on iOS font size manipulation -->
    <div style="display:none; white-space:nowrap; font:15px courier; line-height:0;"> &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; </div>
  </body>
</html>

 これで、あとはFoundation for Emailのマニュアルに沿ってHTMLを書いて行ってください。

 HTMLメールでは未だにレイアウトのために<table>タグを使います。気持ち悪いですがそういうものだと思うしかないみたいです。

HTMLの最適化

 HTMLメールの問題は、HTMLの問題とCSSの問題があります。CSSの側の問題はCSSフレームワークで解決できますが、HTMLの書き方の問題が残っています。

 一番大きな問題はgmailがclassをサポートしないため、全てのタグにstyleで指定する必要があることでしょう。

 Railsではこの問題を解決するために premailer-railsを使います。
このGemではstyleへの展開以外に不必要なアトリビュートの削除などを行ってくれます。

画像の扱い

 HTMLメールの扱いの面倒な事の一つに画像の扱いがあります。添付ファイルにして<img src="cid:.."/>で指定する方法と、BASE64でエンコードして<img src="data:image/jpeg;base64.."/>という風にHTMLに含めてしまう方法があります。
 後者の方が楽なのですがOutlookでは表示されないため、前者を使う方が再現性が高いようです。

 その場合は下記のようにして、Mailerの方でattachments[]に表示したい画像ファイルを追加し、.html.erbの方ではattachments[n].urlを使って指定します。

foo_mailer.rb
class FooMailer < ActionMailer::Base
  def email
    attachments['banner.png'] = File.read(Rails.root.join('app/assets/images/banner.png'))
  end
end
email.html.erb
<%= image_tag attachments['banner.png'].url, class: 'banner' %>

メールの確認

 HTMLメールが正しく表示されているのか、各種クライアントで確認するのは大変です。そこでメールのレンダリングを一覧で確認できるWebサービスを使います。

 一番有名なのはLitmusだと思いますが、$99/mo〜(2016/12末現在)とちょっとお高めです。無料や低価格の同種のサービスはないようです。

21
17
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
21
17