def mail(headers={}, &block)
# Add a display name to the From field if Setting.mail_from does not
# include it
- mail_from = Mail::Address.new(Setting.mail_from)
- if mail_from.display_name.blank? && mail_from.comments.blank?
- mail_from.display_name =
- @author&.logged? ? @author.name : Setting.app_title
+ begin
+ mail_from = Mail::Address.new(Setting.mail_from)
+ if mail_from.display_name.blank? && mail_from.comments.blank?
+ mail_from.display_name =
+ @author&.logged? ? @author.name : Setting.app_title
+ end
+ from = mail_from.format
+ list_id = "<#{mail_from.address.to_s.tr('@', '.')}>"
+ rescue Mail::Field::IncompleteParseError
+ # Use Setting.mail_from as it is if Mail::Address cannot parse it
+ # (probably the emission address is not RFC compliant)
+ from = Setting.mail_from.to_s
+ list_id = "<#{from.tr('@', '.')}>"
end
headers.reverse_merge! 'X-Mailer' => 'Redmine',
'X-Redmine-Site' => Setting.app_title,
'X-Auto-Response-Suppress' => 'All',
'Auto-Submitted' => 'auto-generated',
- 'From' => mail_from.format,
- 'List-Id' => "<#{mail_from.address.to_s.tr('@', '.')}>"
+ 'From' => from,
+ 'List-Id' => list_id
# Replaces users with their email addresses
[:to, :cc, :bcc].each do |key|
assert_equal 'Redmine app <redmine@example.net>', mail.header['From'].to_s
end
+ def test_from_header_with_rfc_non_compliant_phrase
+ # Send out the email instead of raising an exception
+ # no matter if the emission email address is not RFC compliant
+ assert_nothing_raised do
+ with_settings :mail_from => '[Redmine app] <redmine@example.net>' do
+ Mailer.deliver_test_email(User.find(1))
+ end
+ end
+ mail = last_email
+ assert_match /<redmine@example\.net>/, mail.from_addrs.first
+ assert_equal '[Redmine app] <redmine@example.net>', mail.header['From'].to_s
+ end
def test_from_header_with_author_name
# Use the author's name or Setting.app_title as a display name
# when Setting.mail_from does not include a display name