by @nyarla

pycronからcygwinのcronに乗り換えた

概要: pycron から cygwin の cron に乗り換える


今まで PC で定期実行する際は pycron 使ってたんですが、 pycron がタスクを実行するときに Windows が起動中だと Windows の動作がおかしくなり、 深刻なエラーから回復しましたとか出てたので、PC のログイン時に起動するようにした cygwin の cron を使うようにしました。

で、まあ Google で検索してみるとサービスとして実行する方法はよく載ってるんですが、

サービスとしてインストールせずに使用する方法 が載ってないので、

自分のやったことをまとめてみる次第。

1. cygwin の cron をインストールする

まずはともかく cygwin の cron をインストール。

まあこれはsetup.exeで cron のパッケージ探してインストールだけなので、詳しい説明はカット。

2. cygwin 上からcron-configを実行する

で次に cron の起動準備を整えるために、

$ cron-config

を実行。そうすると、cron を実行する際にエラーとなることを言ってくるので、 それを修正。

で、修正が終わってからもう一度cron-configを実行すると

$ cron-config
Do you want to install the cron daemon as a service? (yes/no) no (ここはnoを入力)
Running cron_diagnose ...
... no problem found.

Do you want to start the cron daemon as a job now? (yes/no) no (これも同じくnoを入力)
OK. Type '/usr/sbin/cron' to start the cron daemon job.

In case of problem, examine the log file for cron,
/var/log/cron.log, and the Windows event log (using /usr/bin/cronevents)
for information about the problem cron is having.

Examine also any cron.log file in the HOME directory
(or the file specified in MAILTO) and cron related files in /tmp.

If you cannot fix the problem, then report it to [email protected]
Please run the script /usr/bin/cronbug and ATTACH its output
(the file cronbug.txt) to your e-mail.

という感じで、 ... no problem found. と出たら OK。 これで cron を実行できる準備ができました。

3. crontabでジョブを登録する

まあ cygwin 上での作業はこれで最後なんですが、crontabコマンドでジョブを登録します。

$ crontab -e

でエディタが立ち上がってくるので

* * * * * /bin/date >>/tmp/date.log 2>&1

みたいな感じでジョブを登録。ちなみに上記は cron がちゃんと動くかどうかテストするときに使ったコマンドです。

あと注意点としては Linux の crontab の書式と cygwin の crontab の書式は微妙に違うので(cygwin の方はユーザーの指定がない)、 その点注意しないとはまることになります。俺も最初ちょろっとはまりました。

で、まあ最初はテスト用のコマンドを入力しておいて、コマンドがきちんと指定したとおりに実行できることを確認してから、 本番用のコマンドを入力するのが良いと思います。

4. cron を立ち上げる bat ファイルを書く

で、最後にこれ。今回自分が結構はまったポイント。

最初に cygwin を起動する bat ファイルを加工して、cron を直接実行するようにしたんだけど、 なんか無限ループっつーかおかしな挙動をしたので、 今回は シェルスクリプト経由でcronを立ち上げる という方法を取りました。

で、まずcronを立ち上げるシェルスクリプトを用意。

#!/bin/sh

cron &

で、次に cygwin を実行する bat ファイルを加工して、シェルスクリプトを実行する bat ファイルを作成。自分の場合こんな感じ。

set CYGDRIVE=Z:
set HOME=%CYGDRIVE%\cygwin\home\nyarla
set PATH=%CYGDRIVE%\cygwin\bin;Z:\cygwin\usr\X11R6\bin;%CYGDRIVE%\cygwin\usr\sbin

sh /cygdrive/z/backup/bin/cron.sh

で、ここで一回はまったんだけど、sh の引数でシェルスクリプトを指定するときに、相対パスで指定すると、 bat ファイルの実行する加減によってはシェルスクリプトを見つけられないということになるっぽいので、 絶対パスで指定するようにした方がいいです。

で、このまま bat ファイルをスタートアップに登録すれば無事 cron をログイン時に起動させる事ができるようになるんだけど、 そのままでは一瞬だけコマンドプロンプトが表示されてしまうので、

まず上記のリンクからアーカイブを落としてきて、適当なディレクトリにファイルを解凍、 んで、解凍したらhideconsole.exeのショートカットを作成して、 リンク先を

{hideconsoleのディレクトリ}\hideconsole.exe {cronを実行するbatファイルへのフルパス}

という感じで指定します。

で、あとは出来上がったショートカットをダブルクリックして実行すれば、 裏で cron が立ち上がるようになります。

で、さっきも書いたけど最初このときにshの引数で指定するシェルスクリプトのパスが相対パスだったもんで、 bat ファイルを直接実行するとcronが立ち上がるのにhideconsole経由で実行すると cron が立ち上がらないという状況になりました。 まあ絶対パスで指定したら直ったんだけど。

で、あとは出来上がったショートカットをスタートアップフォルダに放り込めば、 Windows のログイン時に cron が立ち上がるようになります。

5. 以上終了

で、自分のところでは大体 1 時間ぐらいで上記の作業をやりました。

実は前にも一回途中までやってたんだけど、cron を実行するところでつまずいて、 数時間無駄にしたことがあったんだけど、今回やり直してみたら、なんとかできた次第。

あと自分の場合、rsync でバックアップする bat ファイルも cron で実行できるように シェルスクリプトとして書き直したりしてました。 まあシェルスクリプトとして書き直したら結構スマートになったり。

まあ正直 cygwin の cron をサービスとして使用せずに使う なんて事に需要あるのかわかりませんが、 今回作業したことをまとめてみました。

良かったら試してみてください。

#FIXME