4

パスワードをリセットするためにユーザーに電子メールを送信しようとすると、実行タイムアウト エラーが発生し続けます。他のメーラー機能は動作するので、構成設定が正しいことはわかっています。ヘッダーは次のとおりです。「Timeout::Error in Password resetsController#create」

password_resets_controller は次のとおりです。

def create  
 @user = User.find_by_email(params[:email])  
 if @user  
  User.deliver_password_reset_instructions(@user.id)
  flash[:notice] = "Instructions to reset your password have been emailed to you. " +  
  "Please check your email."  
  redirect_to '/'  
 else  
  flash[:notice] = "No user was found with that email address"  
  render :action => :new
 end  
end

User.rb内のメソッドは次のとおりです

def self.deliver_password_reset_instructions(user_id)
 user = User.find(user_id)
 user.reset_perishable_token!  
 Emailer.deliver_password_reset_instructions(user)
end

最後に、emailer.rb 内の実際のメソッドを次に示します。

default_url_options[:host] = "http://0.0.0.0:3000"  #development
 def password_reset_instructions(user)  
    @subject                            = "Application Password Reset"  
    @from                               = 'Notice@myApp.com' 
    @recipients                         = user.email  
    @sent_on                            = Time.now  
    @body["edit_password_reset_url"]    =  edit_password_reset_url(user.perishable_token)  
    @headers["X-SMTPAPI"] = "{\"category\" : \"Password Recovery\"}"#send grid category header
  end

エラー メッセージの「Password」が原因で timeout::error と呼ばれるのはなぜですか

4

1 に答える 1

1

メイン コントローラーのリクエスト スレッドから電子メール (またはその他の実行時間の長いプロセス) を送信することはお勧めできません。電子メールの送信は、制御できないさまざまな理由 (送信電子メール配信サーバーのダウンなど) でタイムアウトになる可能性があり、そのためにアプリケーション サーバーとユーザーに損害を与えたくありません。

より良いアプローチは、Delayed Job (DJ) などのキューイング メカニズムを使用して、これらの電子メール タスクをキューに入れ、コントローラー スレッドの外部で処理することです。

https://github.com/collectiveidea/delayed_jobを参照してください

これ (または別のキュー システム) を Rails アプリに統合するのは非常に簡単です。また、Rails 4 にはキュー サービスが組み込まれていると言われています (私はまだ使用していません) http://blog.remarkablelabs.com/2012/12/asynchronous-action-mailer-rails-4-countdown-to-2013

たとえば、アプリで DJ を使用する場合、新しいコードは次のようになります。

def self.deliver_password_reset_instructions(user_id)
 user = User.find(user_id)
 user.reset_perishable_token!  
 # this is the only line that changes
 Emailer.delay.deliver_password_reset_instructions(user)
end

ジョブはデータベースに保存され、タイムアウトなどのエラーが発生したときに再試行されます。

DJ の詳細については、github ページを参照してください。

于 2013-10-05T07:34:04.247 に答える