【Linux】anacronの制御について検証しながら理解した際の話

Linux

はじめに

cronの説明は参考書でもインターネット上でも豊富に得られますが、anacronについては話題が少ない気がします。私自身、/etc配下に「anacrontab」というファイルがあったことは知っていましたが、「なにこれ?」と思うだけで、実際に調べて検証までする気になりませんでした。でも、知らない中で運用していると、思わぬ所で意図しない動作をすることがわかったので、今回はまとめることに至りました。

なお以下の記事については、私が個人的に検証している環境がCentOS8なので、CentOS8で検証等を行っています。

cronについて

cronについては、違う記事で書いたので、そちらを参考にしていただければと思います。

anacronの設定ファイルと動作

上記cronに対して、anacronって何?と思いますが、まずは設定ファイルから見ていきます。

anacronの設定ファイルは、/etc/anacrontabです。こんな記述があります。

細かい仕様はありますが、ポイントは最終の3行です。/etc/cron.daily、/etc/cron.weekly、/etc/cron.monthlyそれぞれの配下のファイルをrun-partsで実行することになっています。/etc/cron.hourlyにあるファイルはanacronの対象ではないことも明記しておきます。

anacrontabの内容を実行する0anacron

/etc/anacrontabを実際に実行するのは、「0anacron」というファイルです。0anacronは/etc/cron.hourly配下にあります。/etc/cron.hourly配下にあるファイルは、/etc/cron.d配下にある「0hourly」というファイルの記述よって、1時間ごと実行されます。つまり、cronが1時間ごとに0anacronを実行し、結果的にanacrontabの内容が実行されることになります。(あくまでも実行されるまでの流れであって、必ずしも実行されないことについては続きをお読みください)

0anacronは履歴を見て実行する

ここで疑問が。「0anacronで1時間に1回実行されるって?1日に1回とか1週間に1回に実行するという話はどこへいった?」と思いますよね。たしかに、1時間に1回「0anacron」は起動しますが、その際にcronのように必ず実行するとは限りません。

anacronは1時間に1回、「anacronが持っている実行履歴を見て」実行をするか判断します。つまり、実行するかどうかは履歴の情報次第となります。

anacronの実行履歴は、「/var/spool/anacron」配下にそれぞれdaily、weekly、monthlyの履歴が記録されています。

anacronは1時間ごとに上記の履歴を確認しに行き、その日やるべきjobが実行されたかを履歴をもとに確認します。実行されていれば何もしないし、実行されていなかったら実行するという仕組みをとっています。

お気づきの通り、cron.hourlyの記述はありません。/etc/cron.hourly配下のファイルについては、上記でも述べた通り/etc/cron.d配下にある0hourlyが実行します。これまでの話をまとめると、次のよう表が作れます。

ディレクトリ配下のファイル実行するファイル
/etc/cron.hourly//etc/cron.d/0hourly
/etc/cron.dailyanacron
/etc/cron.weeklyanacron
/etc/cron.monthlyanacron

anacronを知らないと発生する問題

かつてはanacronという仕組みはありませんでした。比較的に新しい仕組みのようです。

なので、anacronが無かったかつてのcronは、以下のようにcrontabに全て書かれていたようです。

上記のような書き方は、参考書などでも一例として書かれていることがあります(割と有名なIT資格の参考書とかね)。それは、anacronが動作していないことが前提になっています。

では、anacronも動いていて、crontabにも上記のように書いていたらエラーが発生するかというと、「エラーにならない」という答えになります。

上記設定を仮に書いてしまった場合、cronとanacronは独自して動くので1日1回実行して欲しいことでも、crontabに記載された分で1回、anacronで1回実行されます。

全部crontabで制御したい!という人はanacronが動作しないようにする必要があります。

全部crontabじゃだめ?

出来ないことはないけど、それなりに問題があったらかanacronが出来たという考えが自然でしょう。上記のcrontabには分かりやすい欠点がありました。それは、「指定した時刻にシステムが停止していると、実行できない」という問題です。

システム停止が続くなんてことは大事件なのでそう起こりませんが、システムメンテナンスのために定期的にシステムを一時的に落とすことはよくあります(よくと言っても毎日とかではないけどね)。メンテナンスの際に、cronのスケジュールを意識するのは、正直面倒なことですし、cronのスケジュールをその都度変えるのも億劫。ただ、実行されないのも困る…。ということが起こってしまいます。

時間の指定が曖昧なanacron

ご察しの通り、上記のような1日の中にシステムが停止している時間があっても関係なく実行してくれるのがanacronのメリットでもあります。以下、本番環境ではできないOSの時間を意図的に変えて、anacronの動作を見てみたいと思います。

検証

anacronのステータスを確認する

まず、直前に実行した履歴を確認します。

1日に1回実行するものは「2020年10月1日」が最後の実行履歴になっていますね。(週に1回、1か月に1回の実行するもの9月30日です)

日付を意図的にずらしてみる

dailyが20201001なので、日付をずらしてみます。

意図的に1日進めて、10月2日になった状態で待ちます。いきなり10月2日になったので、当然10月2日分のジョブは実行されていません。

ログで確認

cronのログを見ます。