Techioz Blog

gitlab-rails で cron スクリプトを実行する方法

概要

私はgitlab-railsを持っています

Cron から gitlab-rails スクリプトを実行したいと考えています。 gitlab-rails ランナーは、ファイル引数を認識せず、代わりにスクリプトとして実行しようとして失敗するため、壊れているようです。そのため、gitlab-railsrunner -h で提案されているシバン行が機能したとしても (引数が分離されていないため、私のシステムでは機能しません)、gitlab-railsrunner はファイル パスが有効なスクリプトではないというエラーを出します。

Ruby スクリプトをシェル スクリプトに含めて、gitlab-rails にパイプすることもできますが、エディターでの .rb ファイルの構文ハイライトとインテリセンスが犠牲になります。

シェル スクリプト内から .rb スクリプトを gitlab-rails にパイプできます。これで前の問題は解決しますが、現在 2 つのスクリプトがあり、ライブラリ パスを明示的に指定しない限り、関連するスクリプトを参照する際にシェルが信頼できません。それは複雑なようです。

誰かが回避策を提案してくれました。これには、通常どおり Ruby を実行してから、rails (私の場合は gitlab-rails) を使用してスクリプトを再実行する必要があります。ファイル引数を Rails コマンドとして扱う gitlab-rails ランナーが壊れているため、これでもまだ失敗します…

解決策

Update 2024: バグは修正されたようです。シンプルに試してみてください:

#!/usr/bin/env -S gitlab-rails runner

# Do your GitLab work here. This is just a harmless trivial example.
Project.find_each do |project|
  puts "#{project.full_path}"
end

標準入力でスクリプトを gitlab-rails にパイプする回避策を拡張しましたが、これは機能します。

#!/usr/bin/env ruby

#
# List GitLab projects
#
# Run this script with sudo

if not defined?(Rails) then
  # Running in plain rubby, invoke rails runner and pipe the script into it, passing args
  exec("/usr/bin/gitlab-rails", "runner", "-", *ARGV, :in=>[File.expand_path(__FILE__)])
end

# Do your GitLab work here. This is just a harmless trivial example.
Project.find_each do |project|
  puts "#{project.full_path}"
end

このスクリプトを実行可能ファイル chown a+x にすると、これを cron ジョブに簡単に入れることができます。

00 * * * * root /path/to/my/script.rb