[Server & Network General] crontab: ruby スクリプトを実行する
rvm + zsh 環境で、設定してみます。
このあたりで復習しつつ、設定を進めます。
Contents
公式の手順に従う
後述の通り、いろいろ試してはまりました。
こちらのエントリに救われました。
- cron にはシェルスクリプトを登録する。
- シェルスクリプト内で、rvm 環境をロードする。
- シェルスクリプト内で、ruby スクリプトを実行する。
シェルスクリプトを用意する
まず、そのままの状態で何が呼ばれるのか確認してみました。
#!/usr/bin/zsh
#ruby $HOME/sbin/blog_mysql.rb
ruby -v
echo $PATH
$ chmod 700 sbin/blog_mysql.sh
cron を1分ごとに動かしながら確認します。
SHELL=/usr/bin/zsh
MAILTO='alert@exsample.com'
HOME='/home/****'
* * * * * $HOME/sbin/blog_mysql.sh
実行結果。rvm 環境は読み込まれていないことが分かります。
ruby 1.8.7 (2010-08-16 patchlevel 302) [x86_64-linux]
/usr/bin:/bin
シェルスクリプトに rvm 環境を読み込みむ
以下の2行を加えます。
# load rvm ruby
source $HOME/.rvm/environments/default
実行結果。成功です。
ruby 2.1.0p0 (2013-12-25 revision 44422) [x86_64-linux]
/home/****/.rvm/gems/ruby-2.1.0/bin:/home/****/.rvm/gems/ruby-2.1.0@global/bin:/home/****/.rvm/rubies/ruby-2.1.0/bin:/usr/bin:/bin
設定
実行したい ruby スクリプトを指定、crontab を修正して完了。
#!/usr/bin/zsh
# load rvm ruby
source $HOME/.rvm/environments/default
ruby $HOME/sbin/blog_mysql.rb
作ったスクリプトを設定してみます。
実行結果。
default: 0
osi: 0
gfm: 0
完了。
補遺
遭遇したエラーとか含め、ログとして残しておく。
cron から ruby への path を通してみる
レンタルサーバは rvm で ruby が入っているようで、crontab 内で path をどう指定するか分からない。
.rvm
以下を探って、ココをあててみることにする。
$ .rvm/rubies/default/bin/ruby -v
ruby 2.1.0p0 (2013-12-25 revision 44422) [x86_64-linux]
こちらを参考に cron から呼べるように調整します。
$ crontab -e
MAILTO='alert@exsample.com'
HOME='/home/****'
RUBY_PATH='.rvm/rubies/default/bin'
* * * * * $HOME/$RUBY_PATH/ruby -v >> $HOME/ruby_version
$ tail ruby_version -fruby 2.1.0p0 (2013-12-25 revision 44422) [x86_64-linux]
ruby 2.1.0p0 (2013-12-25 revision 44422) [x86_64-linux]
ruby 2.1.0p0 (2013-12-25 revision 44422) [x86_64-linux]
OKです。
gem が require できないとエラー
ということで、ココで作ったスクリプトを設定してみます。
と思ったら、cron deamon からエラーが出てました。
/home/****/.rvm/rubies/ruby-2.1.0/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:55:in `require': cannot load such file -- mysql (LoadError)
from /home/****/.rvm/rubies/ruby-2.1.0/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:55:in `require'
from /home/****/sbin/blog_mysql.rb:1:in `<main>'
gem の require でこけているようです。
path を追加すればできそうですが、rvm の知識がなさ過ぎてできませんでした。
crontab 内で cd してみる
気を取り直して調べ直してみました。
シェルスクリプトで、cd /foo && ruby bar
のようなことができるよう。
MAILTO='alert@exsample.com'
HOME='/home/****'
* * * * * cd $HOME && ruby sbin/blog_mysql.rb
odd number list for Hash
エラーが発生。
sbin/blog_mysql.rb:7: odd number list for Hash
default: "SELECT count(*) FROM wp_post...
^
sbin/blog_mysql.rb:7: syntax error, unexpected ':', expecting '}'
default: "SELECT count(*) FROM wp_post...
^
sbin/blog_mysql.rb:7: syntax error, unexpected ',', expecting $end
どうもレンサバ標準の ruby 1.8 が呼ばれているよう。
こんな形で調べたら、やっぱりそうでした。
* * * * * ruby -v >> $HOME/ruby_version
ruby 1.8.7 (2010-08-16 patchlevel 302) [x86_64-linux]
ということで再度修正。
MAILTO='alert@exsample.com'
HOME='/home/****'
RUBY_PATH='.rvm/rubies/default/bin'
* * * * * cd $HOME && $HOME/$RUBY_PATH/ruby sbin/blog_mysql.rb
gem が require できないとエラー
gem が require できないに戻りました。
/home/****/.rvm/rubies/ruby-2.1.0/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:55:in `require': cannot load such file -- mysql (LoadError)
from /home/****/.rvm/rubies/ruby-2.1.0/lib/ruby/site_ruby/2.1.0/rubygems/core_ext/kernel_require.rb:55:in `require'
from sbin/blog_mysql.rb:1:in `<main>'