简体   繁体   中英

EOFError error trying to use Amazon SES via SMTP with Rails 3.1.3

I have a Rails app configured to use Amazon SES via SMTP. When I try and send email, though, it appears to timeout after a minute, and I get an EOFError. It smells like a configuration issue--the email seems to be constructed fine, and I can send myself test emails from the AWS SES console. This is in sandbox mode, and the app is running in development mode, but both the sending and receiving emails have been verified with SES, and development.rb is set up with this:

config.action_mailer.raise_delivery_errors = true
config.action_mailer.delivery_method = :smtp

I've tried a million config variations; this is starting to drive me bananas. Any help or guidance would be very, very appreciated. More details:

The smtp config, which I have in an initializer:

ActionMailer::Base.smtp_settings = {
  :address        => "email-smtp.us-east-1.amazonaws.com",
  :port           => "465",
  :authentication => :plain,
  :enable_starttls_auto => true,
  :user_name      => "1234",
  :password       => "abcde"
 }

The logs with the error, a bit truncated for brevity:

Sent mail to john@phu.com (59929ms)
Date: Tue, 20 Dec 2011 03:08:37 -0800
From: contact@phu.com
To: john@phu.com
Message-ID: <4ef06cb5ed3c_d73c3fc604c34d4491943@Johns-MacBook-Pro.local.mail>
Subject: Your invitation to Phu
Mime-Version: 1.0
Content-Type: text/html;
 charset=UTF-8
Content-Transfer-Encoding: 7bit

<!DOCTYPE html>
....

Completed 500 Internal Server Error in 60564ms

EOFError (end of file reached):
  app/controllers/admin_controller.rb:61:in `block in send_invite'
  app/controllers/admin_controller.rb:46:in `send_invite'

There is also a solution without the monkey-patch solution from Mihir (which, according to AWS SES documentation, http://docs.amazonwebservices.com/ses/latest/DeveloperGuide/SMTP.Connecting.html , is the TLS wrapper solution), by using port 587 and :enable_starttls_auto option (the STARTTLS solution). So the modified config is such:

config.action_mailer.default_url_options = { host: “<example.com>” }
config.action_mailer.raise_delivery_errors = true
config.action_mailer.delivery_method = :smtp
config.action_mailer.smtp_settings = {
    :address: “email-smtp.us-east-1.amazonaws.com”,
    :port: 587,
    :domain: “<example.com>”,
    :authentication: :login,
    :user_name: “<your aws smtp username>”,
    :password: “<your aws smtp password>”,
    :enable_starttls_auto => true
}

Here is a solution in case you want to use SMTP (and not the AWS-SES gem)

http://blog.readypulse.com/2012/01/06/amazon-ses-smtp-emails-using-rails-3-1-in-three-easy-steps/

Things to note

AWS SMTP only works on TLS AWS SMTP does NOT support STARTTLS ActionMailer's configuration does not have an easy TLS switch. Steps to follow

Enable SMTP support on your AWS Console – See instructions here. Create an initializer under your config/initializers directory. I am calling it amazon_ses.rb and add following code to money patch ActionMailer's SMTP settings.

module Net
    class SMTP
        def tls?
            true
        end
    end
end

Add following code in your development.rb and production.rb files. Modify the settings to match your environment.

config.action_mailer.default_url_options = { host: “<example.com>” }
config.action_mailer.raise_delivery_errors = true
config.action_mailer.delivery_method = :smtp
config.action_mailer.smtp_settings = {
    address: “email-smtp.us-east-1.amazonaws.com”,
    port: 465,
    domain: “<example.com>”,
    authentication: :login,
    user_name: “<your aws smtp username>”,
    password: “<your aws smtp password>”
}

SES requires a SSL session before the EHLO command is sent.

I know System.Net.Mail doesn't work with SES, because System.Net.Mail initiates the TLS after the SMTP session has started.

I ran into this same issue using Rails 2.3, with Ruby 1.8.7, in dev mode with a sandboxed SES account, sending to/from verified senders.

I worked around it by adding in the unofficial aws-ses gem . Stick it in your Gemfile, and then replace the smtp settings with these 5 lines:

  # Configure mail sending options: Use AWS-SES for all environments
  config.after_initialize do
    ActionMailer::Base.delivery_method = :amazon_ses
    ActionMailer::Base.custom_amazon_ses_mailer = AWS::SES::Base.new(:secret_access_key => 'asfd/1234', :access_key_id => 'ABCD')
  end

Sending then worked as expected…which tells me the emails themselves were getting set up correctly.

I've done a lot of googling, and haven't seen any confirmation that SES-SMTP is compatible with Rails 2.3 + Ruby 1.8.7. Nor have I found anything that explicitly denies it either, beyond your & my experience.

Let us know if you find a solution!

I got this working on Rails 3.2.12 adding require 'net/smtp' to the initializer file with the module change like:

require 'net/smtp'

  module Net
    class SMTP
      def tls?
        true
      end
    end
 end

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM