Cloudmailin получает 500 от Heroku при доставке электронной почты
Я использую аддон Cloudmailin для получения электронной почты из моего приложения Heroku. Тем не менее, Cloudmailin не смог доставить - или, скорее, он получает 500 от Heroku каждый раз (поэтому адрес правильный).
Ошибка в журналах Heroku
Started POST "/incoming_mails" for 109.107.35.53 at 2013-02-27 08:54:22 +0000
2013-02-27T08:54:23+00:00 app[web.1]: Entering the controller! Controlling the e-mail!
2013-02-27T08:54:23+00:00 app[web.1]:
2013-02-27T08:54:23+00:00 app[web.1]: NoMethodError (undefined method `[]' for nil:NilClass):
2013-02-27T08:54:23+00:00 app[web.1]: app/controllers/incoming_mails_controller.rb:7:in `create'
Мой маршрут правильный; "Вход в контроллер! Управление электронной почтой!" происходит от путов в начале класса, поэтому класс определенно поступает.
# routes.rb
post '/incoming_mails' => 'incoming_mails#create'
Сам файл выглядит так:
# /app/controllers/incoming_mails_controller.rb
class IncomingMailsController < ApplicationController
skip_before_filter :verify_authenticity_token
def create
puts "Entering the controller! Controlling the e-mail!"
Rails.logger.info params[:headers][:subject]
Rails.logger.info params[:plain]
Rails.logger.info params[:html]
if User.all.map(&:email).include? params[:envelope][:from] # check if user is registered
@thought = Thought.new
@thought.body = params[:plain].split("\n").first
@thought.user = User.where(:email => params[:envelope][:from])
@thought.date = DateTime.now
if @thought.save
render :text => 'Success', :status => 200
else
render :text => 'Internal failure', :status => 501
end
else
render :text => 'Unknown user', :status => 404 # 404 would reject the mail
end
end
end
Пользователь и мысль - это ресурсы базы данных, используемые в других местах без проблем. Процедура сохранения та же, что и в контроллере Thought, созданном скаффолдингами. params
а также Rails.logger
Логика, которую я скопировал из примера Cloudmailin Rails 3.
Я действительно смущен - где я иду не так? Буду очень признателен за любые указатели.
1 ответ
Оказывается, именно поэтому вы не должны кодировать, будучи лишенным сна. Проблема была проста: нет такой вещи как params[:envelope][:from]
, есть только params[:from])
, Мое предположение, что :from
будет подэлементом :envelope
вероятно был сформирован путем просмотра шаблона во втором примере "Cloudmailin in Rails on Heroku", где код, используемый для записи темы Rails.logger.log params[:envelope][:subject]
,
Я понял, что это ошибка после прочтения документации API для "оригинального" формата Cloudmailin. Это было исключительно глупо с моей стороны не найти / искать этот ресурс в первую очередь.
После исправления этого код все еще не работал, потому что User.where(:email => params[:from])
только вернул Relation
объект, в то время как User
объект был ожидаем. Ошибка в журналах Heroku была следующей:
ActiveRecord::AssociationTypeMismatch (User(#29025160) expected,
got ActiveRecord::Relation(#12334440)):
Поскольку с каким-либо адресом электронной почты может быть только один пользователь, исправление User.where(:email => params[:from]).first
не имеет побочных эффектов и приводит к правильному поведению.