The mailer plugin allows your Roda
application to send emails easily.
class Mailer < Roda plugin :render plugin :mailer route do |r| r.on "albums", Integer do |album_id| @album = Album[album_id] r.mail "added" do from 'from@example.com' to 'to@example.com' cc 'cc@example.com' bcc 'bcc@example.com' subject 'Album Added' add_file "path/to/album_added_img.jpg" render(:albums_added_email) # body end end end end
The default method for sending a mail is sendmail
:
Mailer.sendmail("/albums/1/added")
If you want to return the Mail::Message
instance for further modification, you can just use the mail
method:
mail = Mailer.mail("/albums/1/added") mail.from 'from2@example.com' mail.deliver
The mailer plugin uses the mail gem, so if you want to configure how email is sent, you can use Mail.defaults
(see the mail gem documentation for more details):
Mail.defaults do delivery_method :smtp, address: 'smtp.example.com', port: 587 end
You can support multipart emails using text_part
and html_part
:
r.mail "added" do from 'from@example.com' to 'to@example.com' subject 'Album Added' text_part render('album_added.txt') # views/album_added.txt.erb html_part render('album_added.html') # views/album_added.html.erb end
In addition to allowing you to use Roda’s render plugin for rendering email bodies, you can use all of Roda’s usual routing tree features to DRY up your code:
r.on "albums", Integer do |album_id| @album = Album[album_id] from 'from@example.com' to 'to@example.com' r.mail "added" do subject 'Album Added' render(:albums_added_email) end r.mail "deleted" do subject 'Album Deleted' render(:albums_deleted_email) end end
When sending a mail via mail
or sendmail
, a RodaError
will be raised if the mail object does not have a body. This is similar to the 404 status that Roda
uses by default for web requests that don’t have a body. If you want to specifically send an email with an empty body, you can use the explicit empty string:
r.mail do from 'from@example.com' to 'to@example.com' subject 'No Body Here' "" end
If while preparing the email you figure out you don’t want to send an email, call no_mail!
:
r.mail 'welcome', Integer do |id| no_mail! unless user = User[id] # ... end
You can pass arguments when calling mail
or sendmail
, and they will be yielded as additional arguments to the appropriate r.mail
block:
Mailer.sendmail('/welcome/1', 'foo@example.com') r.mail 'welcome' do |user_id, mail_from| from mail_from to User[user_id].email # ... end
By default, the mailer uses text/plain as the Content-Type for emails. You can override the default by specifying a :content_type option when loading the plugin:
plugin :mailer, content_type: 'text/html'
For backwards compatibility reasons, the r.mail
method does not do a terminal match by default if provided arguments (unlike r.get
and r.post
). You can pass the :terminal option to make r.mail
enforce a terminal match if provided arguments.
The mailer plugin does support being used inside a Roda
application that is handling web requests, where the routing block for mails and web requests is shared. However, it’s recommended that you create a separate Roda
application for emails. This can be a subclass of your main Roda
application if you want your helper methods to automatically be available in your email views.
Classes and Modules
Public Class methods
Set the options for the mailer. Options:
:content_type |
The default content type for emails (default: text/plain) |
# File lib/roda/plugins/mailer.rb 136 def self.configure(app, opts=OPTS) 137 app.opts[:mailer] = (app.opts[:mailer]||OPTS).merge(opts).freeze 138 end