HerokuでRailsアプリケーションを運用しているのですが、Sidekiqを導入するときにredisを構築したり、sidekiqのプロセスを立ち上げたり、色々と調べることがあったので、そのあたりの内容をメモしておきます📝
pumaからhookしてsidekiqのプロセスをwebのdynoのインスタンス上で立ち上げる方法もあるようですが、今回はsidekiq用のプロセスタイプを別に定義して構築する方法を記述しています。
freeプランでもプロセスタイプ数は2つまで無料のようなので・・・!
Heroku Redisの導入
Sidekiqを利用するためにHeroku Redisを使ってRedisを構築します。
Heroku RedisはHobby Devであれば無料で構築できます。
導入は簡単で以下のコマンドを実行するかHerokuのダッシュボードから手動で構築することができます。
$ heroku addons:create heroku-redis:hobby-dev -a your-app-name --version your-redis-version
※デフォルトだと6.0系がインストールされるようです👀(2021/03/28時点)
構築は数分で終わって完了すると環境変数REDIS_URL
に構築したHeroku Redisへの接続情報が自動的に設定されます。(便利✨)
As of Redis version 6, Hobby plans support both TLS and unencrypted connections, while production plans require TLS connections.
https://devcenter.heroku.com/articles/heroku-redis#create-a-new-instance
redis 6以降のredisを構築すると、REDIS_TLS_URL
も同時に環境変数に定義され、こちらを利用するとTLSを活用した暗号化もサポートされているようです👀
sidekiqの導入
SidekiqのWiki等を参考にgemをインストールします。
gam 'sidekiq'
私は以下のような設定ファイルをconfig/sidekiq.yml
に置きましたが、このへんは好みなので設置せずに実行時に指定するなり、諸々対応します。
--- :concurrency: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %> :queues: - high - default - low development: :logfile: log/sidekiq.log :pidfile: tmp/pids/sidekiq.pid
あとはroutesにSidekiqの管理画面をmountして、initializerの中でベーシック認証を追加しておきます。
Rails.application.routes.draw do require 'sidekiq/web' mount Sidekiq::Web, at: '/sidekiq' end
require 'sidekiq/web' # NOTE: Sidekiqのwebuiにベーシック認証をかける Sidekiq::Web.use(Rack::Auth::Basic) do |user, password| [user, password] == [ENV['BASIC_AUTH_USER'], ENV['BASIC_AUTH_PASSWORD']] end
※ SidekiqはデフォルトでREDIS_URLを参照してくれるので接続情報等の設定はなくても大丈夫です。
You may also use the generic REDIS_URL which may be set to your own private Redis server. Using Redis · mperham/sidekiq Wiki · GitHub
Sidekiq用のプロセスタイプを定義
プロジェクトのルートに以下を記載したProcfile
を用意してSidekiq用のworkerのプロセスタイプを定義し、herokuにpushします。
web: bin/rails server -p ${PORT:-5000} -e $RAILS_ENV worker: bundle exec sidekiq
HerokuはこのProcfileに記載されたプロセスタイプごとにインスタンスを生成するようです。
sidekiq用のインスタンスを構築する。
以下のコマンドを実行し、HerokuにRailsアプリケーションが動作するweb
とSidekiqが動作するworker
のインスタンスを1つずつ立ち上げます。
$ heroku ps:scale web=1 worker=1
※ 前述の「 Sidekiq用のプロセスタイプを定義」を実施しないとコマンド実行時に以下のエラーが発生します。前述の通り。Herokuはプロセスタイプに従ってインスタンス化するようなので、事前にProcfileにプロセスタイプを定義する必要があるようです👀
$ heroku ps:scale web=1 worker=1 Scaling dynos... ! ▸ Couldn't find that process type (worker).
これでHerokuでRailsアプリケーションとSidekiqを起動することができました🙌
以下のようなコマンドを実行してJobをエンキューして無事に処理されることを確認できれば問題なさそうです。
$ heroku run bin/rails c -e production
$ MySampleJob.perform_later
おわりに
Herokuの無料プランでSidekiqまで動かせると思っていなかったのですが、ここまで出来るとは・・・!