GitHub - javan/whenever: Cron jobs in Ruby https://github.com/javan/whenever
以下のように普通にcrontab設定することにした。
* * * * cd /path/to/app && /path/to/docker-compose run web rails runner 'SomeClass.some_method' -e production >> log/cron.log
wheneverはconfig/schedule.rbにcrontabの設定を記述できる。
config/schedule.rb
every 3.hours do # 1.minute 1.day 1.week 1.month 1.year is also supported
# the following tasks are run in parallel (not in sequence)
runner "MyModel.some_process"
rake "my:rake:task"
command "/usr/bin/my_great_command"
end
every 1.day, at: '4:30 am' do
runner "MyModel.task_to_run_at_four_thirty_in_the_morning"
end
every 1.day, at: ['4:30 am', '6:00 pm'] do
runner "Mymodel.task_to_run_in_two_times_every_day"
end
every :hour do # Many shortcuts available: :hour, :day, :month, :year, :reboot
runner "SomeModel.ladeeda"
end
every :sunday, at: '12pm' do # Use any day of the week or :weekend, :weekday
runner "Task.do_something_great"
end
every '0 0 27-31 * *' do
command "echo 'you can use raw cron syntax too'"
end
# run this task only on servers with the :app role in Capistrano
# see Capistrano roles section below
every :day, at: '12:20am', roles: [:app] do
rake "app_server:task"
end
コードとしてgitに残るので履歴が追えるし、プロジェクトに新規アサインされたひとでも容易にcronの環境が構築できて便利。
ただ、docker-compose配下だといろいろ面倒でググるとその辺のトラブルシューティングの方法が出てくるんだけどヤックシェービング感は否めないし余計なレイヤーが挟まることで面倒が増えるなとおもって時間かけていろいろ実験してみたけど使うのを辞めた。
:environment, ENV['RAILS_ENV'] || 'development'
とかが本番でdevelopmentになってて動かなくてdotenv-railsが必要?dockerはcronはフォアグラウンドで動かさないダメなの?envがうまく読み込めないとかcron用のをdocker-composeに記載しないととかあれがダメこれがダメとかいろいろやってたけどそもそもwheneverじゃないと絶対実現できないことなのか?ホストのcrontabでできるんじゃないの?と取り組んでる問題が急にアホらしくなった。
dockerは何も考えずにubuntu上に環境を作るのとは若干勝手が違うのでいろいろハマりがち。
ruby、postgres、nginx、redisのバージョンを簡単に上げれるし、OSのバージョンもガンガン上げれるのでセキュリティ的にいい。
新しい機能をガンガン取り込むのにも積極的になれるけどGemによってはアンマッチな場合もあるのでその辺の勘所がほしい。
他にもcapistranoとかは実態はrsyncプラスアルファなんだけどハマりがち、docker-compose環境にはめちゃくちゃ相性が悪そうな気がするのでdeploy.shとかを自作してやるのが平和的に解決できそう。
wheneverはcronのコード化ができて便利だけどdocker-compose環境下での利用はGitHubのREADMEを見ても書いてないしIssueを見ても積極的に対応しようという空気感がないので素直にcrontab書くというのもアリだと思います。
自分のプロジェクトのREADME.mdにcrontabの設定はこうやるんだよって書いておけば新規アサインされたひともちゃんと見てくれるはず、というかwhenever使おうとしたけどいまいちだったから素のcrontabで対応したって口頭なりチャットなりで伝える。
developmentだとcron動いてなくても開発は問題なくできることも多そう。
なんでもGem使っていい感じに解決できればいいけどやってみて違和感を感じたら無理しないことも大事。
ツールに無理やり合わせてもどこかで不都合が生じてくるのでそれに気づいた時点で潔く使うのを諦めていい。
cronもwheneverも結果は同じ(wheneverはwhenever --update-crontabで最終的にcrontabに書き込んでる)なのに抱え込む問題と解決できる問題のバランスが取れてないみたいなことあるよなあという感じ。
技術ってそういうところがあって組み合わせとかでヤクシェービングになりそうなら早めに撤退したほうがいい。
そういう意味ではdockerも余計なレイヤーが挟まってメリットとデメリットのバランスが悪くなるシーンがありそうだから微妙かもしれないとは思い始めてる…
無理せずに学習して上手に扱うのが技術者の腕だけどそれって現実に合わせた問題解決の質としてどうなんだろうって捉え直したとしてもまだ価値があるといえるのであればやるべきだけど売上がすべてを癒すからそれとのギャップを埋めれるならいいんだけどその辺はほんとにセンス。
データベース設計におけるわかっててあえて非正規形にしてるなら全然アリみたいな話と似てる。
声の大きい有名人が記事で紹介してた技術だからどのプロジェクトでも盲目的に使えるって判断するのもあぶない話ではある。
自分のプロジェクトに適用してみて明確にいまいちな問題があるんなら解決するか諦めるか自分で考えて判断するのがいい、無理にツールに合わせても辛いばかり。