最近テストが不安定になって、その修正をしていっていたらActiveJobが絡むあたりがまた不安定になったので原因を探ろうとしたのだけれど、ActiveJobのテストの設定周りなんて久々すぎて忘れまくっていたのでここで一旦整理しておく。
テストでActiveJobを同期的に扱う
ActiveJobのqueue_adapterの設定は、environmentsの各ファイルで行うべき、だそう。コメントでそう書いてあった。
# Use a real queuing backend for Active Job (and separate queues per environment)
production.rbなど
# Use a real queuing backend for Active Job (and separate queues per environment) config.active_job.queue_adapter = :resque config.active_job.queue_name_prefix = "project_#{Rails.env}"
test.rb
テストでは、queue_adapterを:async
に設定する。以前は:inline
だったらしい。
# Use a real queuing backend for Active Job (and separate queues per environment) config.active_job.queue_adapter = :async config.active_job.queue_name_prefix = "project_#{Rails.env}"
こうするとキューに入ったと同時に実行されるっぽい。
テストでもResqueを使いたい!
あんまりこだわることはないのかもしれないが、テストでもqueue_adapterに:resque
を使いたい場合は、:resque
を指定した上で、Resqueの設定をinlineにすればよかった。
Resqueの設定は、config/initializers/resque.rb
で行なっていたのでそこに追記した。
Resque.redis = Redis.new(host: "localhost", port: ENV.fetch("REDIS_PORT", 6379) Resque.inline = true if Rails.env.test?
こうすると、Resqueもキューに入ったと同時にジョブを実行してくれる。
ActiveJob::TestHelperを使う
もう一つ方法がある。それは、ActiveJob::TestHelperを使う方法だ。spec/rails_helper.rbなどで読み込む。
config.include ActiveJob::TestHelper
実はすでにこちらを使っていた。しかし、なぜかジョブが実行されなかったようだったので、上記の設定を色々といじったりしていたのだが、何も変わらなかった。
しかしそれは当然で、ActiveJob::TestHelper
を読み込むと、queue_adapterがconfig/environments.test.rb
に設定したものではなく、TestAdapter
になってしまうのだ。
以下はpryの結果。
pry > ActiveJob::Base.queue_adapter => #<ActiveJob::QueueAdapters::TestAdapter:0x00007fa7646755d0 @enqueued_jobs=, @filter=nil, @perform_enqueued_at_jobs=true, @perform_enqueued_jobs=true, @performed_jobs=, @reject=nil>
どれだけconfig/environments/test.rb
のほうでqueue_adapterの設定をいじり回そうと、意味がなかったのだが、これにハマってしまっていた…。
とりあえず、コードの修正によってActiveJobが突如動かなくなった理由はまだわかっていないのだが、ActiveJobをテストで動かすときの設定については理解できたのでよかった。
まとめ
- キューイングのテストが不要でActiveJobの結果をすぐに反映してテストをしたい場合は、ActiveJob::TestHelperを読み込まずに、config/environments/test.rbで
config.active_job.queue_adapter = :async
と読み込めばよい。 - ActiveJobのキューイングや実行タイミングを自分で制御したい場合はActiveJob::TestHelperを読み込む。その場合は、config/environments/test.rbで
config.active_job.queue_adapter
を設定しても意味はない。
あとは昔に自分がqiitaに書いていたやつの通りにやれば問題なかった。