LCL Engineers' Blog

バス比較なび・格安移動・バスとりっぷを運営する LCLの開発者ブログです。

JOBのログ出力をちょっと便利にした話

Webエンジニアの横塚です。

LCLでは、JOB管理にクックパッド社のKuroko2を利用しています。 Webの管理画面でJOBのスケジューリングやリトライ、ログを監視できる便利なツールです。 詳しくは以下の記事をご覧ください。

techblog.lclco.com

課題

Kuroko2では、JOB内で標準出力したログは、管理コンソール上で確認ができます。ただし、リアルタイムではなくJOBが完了後に初めて確認できます。また、ログが多いと途中までしか表示されません。 JOBの処理内容によっては、それなりの量の情報をログに出しておきたいものもあります。そういったJOBがエラーになったとき、管理コンソール上でエラー終了していることはわかるのに肝心なエラーログが途切れてしまって見えない、なんてことが起きる可能性がありました。

解決

いざと言うときに困る前に、対策を打つことにしました。 やりたかった事は以下です。

  • ログが多い時やエラー発生時でもリアルタイムにログを追えるようにしたい
    • 各JOB専用のログファイルに出力するようにすれば良さそう
  • 今まで通り標準出力には出したい
    • Kurokoには拾って欲しいし、開発中も標準出力があったほうが便利

ActiveSupport::Logger.broadcastメソッドを使えば、Loggerのログファイルと標準出力の両方にログを出力できる事ができることがわかりました。

各JOBの親クラスで、標準出力と専用ログの両方に出力するようにカスタムしたLoggerでRails.loggerをオーバーライドすることで、既存の各JOBには手を加えずに実装することができました。

base_job.rb

# 専用のログファイルに出力する設定. dailyでローテートさせる
logger = Logger.new(Rails.root.join("log/batch/#{job_name}.log"), "daily")
# 'STDOUT'を指定して標準出力に出す設定
std_logger = Logger.new(STDOUT)
# broadcastメソッドで複数のログを出力するmoduleを生成してextendする
logger.extend ActiveSupport::Logger.broadcast(std_logger)
# Rails.loggerをオーバーライド
Rails.logger = logger

hoge_job.rb

def execute
  Rails.loger.info 'どっちにも出てくれー!'
end

コンソール

$ bundle exec rails runner "JobTask.execute('hoge_job')"
[2018-12-26 12:29:46.369 #39775 logger.rb:434]  INFO -- : どっちにも出てくれー!

hoge_job.log

$ tail -f log/batch/hoge_job.log
[2018-12-26 12:29:46.369 #39775 logger.rb:434]  INFO -- : どっちにも出てくれー!

標準出力と専用のログファイルに出力することができました!

参考

railsで、複数の出力先にlogを出力する · Yuichi Takada

まとめ

JOBの親クラスをちょっと改造するだけでログのチェックを便利にすることができました。 これだけだと、過去ログがたまり続けてしまうので、後は古くなったログを自動で圧縮、お掃除する仕組みを入れればディスク容量の心配も無くなりそうです。

LCLではエンジニア・インターン募集中です。 サービス開発はもちろん、開発プロセス改善も積極的に推進しています。 少しでも興味がある方は、ご連絡お願い致します。

https://www.lclco.com/recruit/