Настройки ActionMailer, неправильно отличающиеся между разработкой и производством - PullRequest
9 голосов
/ 09 августа 2011

Ошибка

Я установил ActionMailer и отлично работаю в разработке.Я могу позвонить UserMailer.welcome(user).deliver, и электронная почта достигнет пункта назначения.Однако, когда я запускаю свой код в производство и вызываю тот же самый метод deliver, внезапно я получаю сообщение об ошибке:

Errno::ECONNREFUSED: Connection refused - connect(2)
    from /usr/local/rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/net/smtp.rb:546:in `initialize'
    from /usr/local/rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/net/smtp.rb:546:in `open'
    from /usr/local/rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/net/smtp.rb:546:in `tcp_socket'
    from /usr/local/rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/net/smtp.rb:555:in `block in do_start'
    from /usr/local/rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/timeout.rb:58:in `timeout'
    from /usr/local/rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/timeout.rb:89:in `timeout'
    from /usr/local/rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/net/smtp.rb:555:in `do_start'
    from /usr/local/rvm/rubies/ruby-1.9.2-p290/lib/ruby/1.9.1/net/smtp.rb:525:in `start'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/gems/mail-2.3.0/lib/mail/network/delivery_methods/smtp.rb:128:in `deliver!'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/gems/mail-2.3.0/lib/mail/message.rb:1989:in `do_delivery'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/gems/mail-2.3.0/lib/mail/message.rb:230:in `block in deliver'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/bundler/gems/rails-5680a51dcbaf/actionmailer/lib/action_mailer/base.rb:414:in `block in deliver_mail'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/bundler/gems/rails-5680a51dcbaf/activesupport/lib/active_support/notifications.rb:55:in `block in instrument'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/bundler/gems/rails-5680a51dcbaf/activesupport/lib/active_support/notifications/instrumenter.rb:20:in `instrument'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/bundler/gems/rails-5680a51dcbaf/activesupport/lib/active_support/notifications.rb:55:in `instrument'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/bundler/gems/rails-5680a51dcbaf/actionmailer/lib/action_mailer/base.rb:412:in `deliver_mail'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/gems/mail-2.3.0/lib/mail/message.rb:230:in `deliver'
    from (irb):10
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/bundler/gems/rails-5680a51dcbaf/railties/lib/rails/commands/console.rb:45:in `start'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/bundler/gems/rails-5680a51dcbaf/railties/lib/rails/commands/console.rb:8:in `start'
    from /webapps/myapp/production/shared/bundle/ruby/1.9.1/bundler/gems/rails-5680a51dcbaf/railties/lib/rails/commands.rb:40:in `<top (required)>'
    from script/rails:6:in `require'
    from script/rails:6:in `<main>'

Проблема на данный момент

Вероятно, самая ценная информация, которую я могупредложение заключается в том, что фактические данные delivery_method на объекте Message являются неверными в производстве.В процессе разработки, когда я вызываю UserMailer.welcome(user).delivery_method, выводится (отформатированный):

#<Mail::SMTP:0x000001042c4a20 @settings={
  :address=>"smtp.gmail.com",
  :port=>587,
  :domain=>"foobar.com",
  :user_name=>"example@foobar.com",
  :password=>"MY_PASSWORD",
  :authentication=>"plain",
  :enable_starttls_auto=>true,
  :openssl_verify_mode=>nil}>

Это явно соответствует настройкам, которые я определил в mailers.yml.В производственном процессе, когда я делаю тот же вызов, выводом будет:

#<Mail::SMTP:0xbfb2c18 @settings={
  :address=>"localhost",
  :port=>25,
  :domain=>"localhost.localdomain",
  :user_name=>nil,
  :password=>nil,
  :authentication=>nil,
  :enable_starttls_auto=>true,
  :openssl_verify_mode=>nil}>

Это просто значения по умолчанию, определенные в строке 22 ActionMailer :: DeliveryMethods вместо моего собственногонастройки из mailers.yml.

Соответствующий код

Насколько я могу судить, в моих средах должна быть одинаковая настройка ActionMailer.

config / environment.rb:

Myapp::Application.config.action_mailer.delivery_method = :smtp
Myapp::Application.config.action_mailer.smtp_settings = YAML.load_file(
    Rails.root.join('config', 'mailers.yml'))[Rails.env].to_options

config / mailers.yml:

default: &default
  address:              smtp.gmail.com
  port:                 587
  domain:               foobar.com
  user_name:            example@foobar.com
  password:             MY_PASSWORD
  authentication:       plain
  enable_starttls_auto: true

development:
  <<: *default

production:
  <<: *default

config / environment / development.rb:

Myapp::Application.configure do
  # ...
  config.action_mailer.raise_delivery_errors = false
  config.action_mailer.default_url_options = { :host => 'localhost:3000' }
  config.action_mailer.interceptors = ['MailInterceptor']
  # ...
end

config / environment / production.rb:

Myapp::Application.configure do
  # ...
  config.action_mailer.default_url_options = { :host => 'foobar.com' }
  # ...
end

Обратите внимание, что я также пытался закомментировать две дополнительные строки в development.rb (и пыталсядобавив их в production.rb) без изменений - я по-прежнему получаю ту же ошибку при производстве, но не при разработке.

Кроме того, хотя я не думаю, что это уместно, я включу MailIntercepter, чтоЯ ссылаюсь на файл development.rb (он просто перенаправляет всю почту на мой адрес электронной почты вместо адресов электронной почты тестовых пользователей):

class MailInterceptor
  def self.delivering_email(message)
    message.subject = "[#{message.to}] #{message.subject}"
    message.to = "example+catcher@foobar.com"
  end
end

Ответы [ 2 ]

7 голосов
/ 10 августа 2011

Разобрался, хотя, похоже, он идет вразрез с тем, что я считал стандартным подходом к конфигурации Rails 3.1.

Изменена эта строка:

Myapp::Application.config.action_mailer.smtp_settings = YAML.load_file(
    Rails.root.join('config', 'mailers.yml'))[Rails.env].try(:to_options)

К этому:

ActionMailer::Base.smtp_settings = YAML.load_file(
    Rails.root.join('config', 'mailers.yml'))[Rails.env].try(:to_options)

До сих пор не уверен, почему первый работает в разработке, а не в производстве, но последний теперь работает для меня в производстве, так что сейчас я собираюсь.

2 голосов
/ 29 июня 2012

Случайно у вас есть environment.rb, настроенный как:

Myapp::Application.initialize!
Myapp::Application.configure do { }

Если это так, поменяйте местами эти две строки.У меня была почти такая же проблема (конфиг почтовой программы работал в dev, а не в других средах), и это была проблема.

...