3
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Rails4.2 でActiveJob & ActionMailerをそのプロセスでだけ一時的に止める

Last updated at Posted at 2015-06-23

導入 ( ぼくのRails開発環境事情 )

「ユーザー登録時にwelcomeメールを送る」みたいな機能があると、
ユーザーを生成するたびにメール送信処理が走ります。

app/models/user.rb
class User
  after_create :send_welcome

  ...

  private

  def send_welcome
    UserMailer.welcome(self).delivey_later # => ActiveJobが非同期にメールを送ってくれる
  end
end
rails-console
User.create!(...) # => Welcome メールが飛ぶ!

開発環境では、letter_opener を使っているので、実際にメールサーバーを叩いたりはしないようになっています。

Gemfile
gem 'letter_opener'
config/environments/development.rb
Rails.application.configure do
  ...
  # letter opener
  config.action_mailer.delivery_method = :letter_opener
  ...
end

が、代わりにブラウザに新しいタブが開くわけです。

rails-console
User.create!(...) # => ブラウザに新しいタブが開く

問題

そんな時、まとめてユーザーを1000人作ったりすると一斉にメールが開きます。

rails-console
1000.times { User.create!(...) } # => ブラウザに新しいタブが1000個開く

ブラウザに1000個タブが一気に開いたら普通に考えてメモリ食いつぶして死にます。
何とかしなければ。

解決方法

で、端的に解決方法。

ActionMailer::Base.perform_deliveries = false
ActiveJob::Base.queue_adapter = :inline

1000.times { User.create!(...) } # => メールが飛ばないやったー!

かいせつ

最初はActionMailer::Base.perform_deliveries = falseだけでいけるかと思ったのですがダメでした。

なんでかというと、バックグラウンドジョブ自体は、別プロセスで動いているので...

$ bin/rails c # => プロセス1

$ bin/rake jobs:work # => プロセス2

.deliver_laterしてしまうと、そちらに処理が飛ばされてしまい、ローカルで上書きした設定は反映されないのです。
(deliver_layerはActiveJobとActionMailerの連携したメソッドです)

なんとかして同じプロセス上でActiveJobが走らせればいいわけで、
それがActiveJob::Base.queue_adapter = :inlineになります。

ActiveJob::QueueAdapters::InlineAdapterは、そのプロセスで即時実行するキュー戦略なので、その場で処理が起動して、めでたく、上書きした設定で処理を進めてくれます。

書いてから思ったけど、完全に自分の環境依存の問題な気がした。

3
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?