Rails ActionMailer - format sender and recipient name/email address

Ruby on-RailsActionmailer

Ruby on-Rails Problem Overview


Is there a way to specify email AND name for sender and recipient info when using ActionMailer?

Typically you'd do:

@recipients   = "#{user.email}"
@from         = "[email protected]"
@subject      = "Hi"
@content_type = "text/html"

But, I want to specify name as well-- MyCompany <[email protected]>, John Doe <john.doe@mycompany>.

Is there a way to do that?

Ruby on-Rails Solutions


Solution 1 - Ruby on-Rails

If you are taking user input for name and email, then unless you very carefully validate or escape the name and email, you can end up with an invalid From header by simply concatenating strings. Here is a safe way:

require 'mail'
address = Mail::Address.new email # ex: "[email protected]"
address.display_name = name.dup   # ex: "John Doe"
# Set the From or Reply-To header to the following:
address.format # returns "John Doe <[email protected]>"

Solution 2 - Ruby on-Rails

@recipients   = "\"#{user.name}\" <#{user.email}>"
@from         = "\"MyCompany\" <[email protected]>"

Solution 3 - Ruby on-Rails

In rails3 I place the following in each environment. i.e. production.rb

ActionMailer::Base.default :from => "Company Name <[email protected]>"

Placing quotations around the company name did not work for me in Rails3.

Solution 4 - Ruby on-Rails

within Rails 2.3.3 a bug within the ActionMailer was introduced. You can see the ticket over here [Ticket #2340][1]. It's resolved in 2-3-stable and master so it will be fixed in 3.x and 2.3.6.

For fixing the problem within 2.3.* you can use the code provided within the ticket comments:

module ActionMailer
  class Base
    def perform_delivery_smtp(mail)
      destinations = mail.destinations
      mail.ready_to_send
      sender = (mail['return-path'] && mail['return-path'].spec) || Array(mail.from).first

      smtp = Net::SMTP.new(smtp_settings[:address], smtp_settings[:port])
      smtp.enable_starttls_auto if smtp_settings[:enable_starttls_auto] && smtp.respond_to?(:enable_starttls_auto)
      smtp.start(smtp_settings[:domain], smtp_settings[:user_name], smtp_settings[:password],
                 smtp_settings[:authentication]) do |smtp|
        smtp.sendmail(mail.encoded, sender, destinations)
      end
    end
  end
end

[1]: https://rails.lighthouseapp.com/projects/8994/tickets/2340 "Ticket 2340"

Solution 5 - Ruby on-Rails

The version I like to use of this is

%`"#{account.full_name}" <#{account.email}>`

` << are backticks.

Update

You could also change that to

%|"#{account.full_name}" <#{account.email}>|
%\"#{account.full_name}" <#{account.email}>\
%^"#{account.full_name}" <#{account.email}>^
%["#{account.full_name}" <#{account.email}>]

Read more about string literals.

Solution 6 - Ruby on-Rails

Another irritating aspect, at least with the new AR format, is to remember that 'default' is called on the class level. Referencing routines that are instance-only causes it to silently fail and give when you try to use it:

 NoMethodError: undefined method `new_post' for Notifier:Class

Here's what I ended up using:

def self.named_email(name,email) "\"#{name}\" <#{email}>" end
default :from => named_email(user.name, user.email)

Solution 7 - Ruby on-Rails

Since Rails 6.1 there is a new convenient helper method on ActionMailer::Base:

ActionMailer::Base.email_address_with_name("[email protected]", "John Test with Quotes <'")
=> "\"John Test with Quotes <'\" <[email protected]>"

Inside a Mailer, it is accessible without the class-name:

mail to: email_address_with_name(user.email, user.name), ...

Under the hood it uses the Mail::Address like in the top answer.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionGrnbeagleView Question on Stackoverflow
Solution 1 - Ruby on-RailsJames McKinneyView Answer on Stackoverflow
Solution 2 - Ruby on-RailsEduardo ScozView Answer on Stackoverflow
Solution 3 - Ruby on-RailsastjohnView Answer on Stackoverflow
Solution 4 - Ruby on-RailsankaView Answer on Stackoverflow
Solution 5 - Ruby on-RailsMarcView Answer on Stackoverflow
Solution 6 - Ruby on-RailsKevinView Answer on Stackoverflow
Solution 7 - Ruby on-RailsstwienertView Answer on Stackoverflow