今までなんとなく使ってきたが
以下の4つのパターンで設定することができるらしく
何が違うのかはっきりさせたかったので、学習し直すことにした。
1)/etc/cron.(daily|weekly|monthly)/内に設定する方法
2)crontabコマンドで設定する方法
3)/etc/crontabで設定する方法
4)/etc/cron.d/内に設定する方法
先に結論
/etc/corn.d/内に拡張子なしのテキストファイルを置く。
例)/etc/cron.d/test_cron
文法は以下
*[Space]*[Tab]*[Space]*[Space]*[Tab]root[Tab]Commands
テンプレート
SHELL=/bin/bash
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
# m h dom mon dow user command
# 分 時 日 月 曜日 ユーザー コマンド
# 1分ごと
* * * * * root touch /home/ubuntu/test.txt
# 1:00〜1:59まで1分ずつ実行
* 1 * * * root touch /home/ubuntu/test.txt
# 毎日1:00に実行
0 1 * * * root touch /home/ubuntu/test.txt
# 毎月12日~20日00:00に実行
0 0 12-20 * * root touch /home/ubuntu/test.txt
# 毎週月曜日〜金曜日00:00に実行
0 0 * * 1-5 root touch /home/ubuntu/test.txt
17 * * * * root cd / && run-parts --report /etc/cron.hourly
25 6 * * * root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.daily )
47 6 * * 7 root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.weekly )
52 6 1 * * root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.monthly )
タイムゾーンの設定
Ubuntu 18.04のデフォルトは、UTCになっていた。
Tips:
タイムゾーンは crond の起動時にのみ実行環境に設定されている値を取得しています
起動後にはタイムゾーンの更新は行われないので crond の起動後にタイムゾーンを変更しても変更前のタイムゾーンのまま動作します
cron の意外な落とし穴! - もろず blog
このためタイムゾーンを更新したら、必ずcrondを再起動すること
$ sudo service cron restart
確認コマンド
$ timedatectl
Local time: Wed 2020-03-04 17:16:21 UTC
Universal time: Wed 2020-03-04 17:16:21 UTC
RTC time: Wed 2020-03-04 17:16:22
Time zone: Etc/UTC (UTC, +0000)
System clock synchronized: yes
systemd-timesyncd.service active: yes
RTC in local TZ: no
なので、タイムゾーンを直す。
タイムゾーン名一覧は以下
List of tz database time zones - Wikipedia
例)Asia/Tokyo
$ timedatectl set-timezone Asia/Tokyo
$ timedatectl
Local time: Thu 2020-03-05 02:28:08 JST
Universal time: Wed 2020-03-04 17:28:08 UTC
RTC time: Wed 2020-03-04 17:28:09
Time zone: Asia/Tokyo (JST, +0900)
System clock synchronized: yes
systemd-timesyncd.service active: yes
RTC in local TZ: no
ログ出力設定(Ubuntuの場合)
以下記事を参考
[ubuntu] cronのログが出力されない時の対処方法 | BlueBear I/O
cronのログは、将来的に問題が発生した場合などの原因究明に役に立つので有効化しておく。
ログの出力されていない場合は、以下のように変更
/etc/rsyslog.d/50-default.confを編集
$ vi /etc/rsyslog.d/50-default.conf
cronログ設定のコメントを外す。
-#cron.* /var/log/cron.log
+cron.* /var/log/cron.log
rsyslogの再起動
$ service rsyslog restart
1)/etc/cron.(hourly|daily|weekly|monthly)/内に設定する方法
実行時間は「/etc/crontab」で設定されている。
※CentOS6であれば「/etc/anacrontab」
/etc/crontabの中身例
SHELL=/bin/sh
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
# m h dom mon dow user command
# 分 時 日 月 曜日 ユーザー コマンド
17 * * * * root cd / && run-parts --report /etc/cron.hourly
25 6 * * * root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.daily )
47 6 * * 7 root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.weekly )
52 6 1 * * root test -x /usr/sbin/anacron || ( cd / && run-parts --report /etc/cron.monthly )
文法は以下
*[Space]*[Tab]*[Space]*[Space]*[Tab]root[Tab]Commands
スクリプトの実行時間に対して、厳密な時間に実行するなどのルールが
なければ、任意のディレクトリに実行ファイルを入れておけば
勝手に実行されるのでこの方法が一番簡単。
2)crontabコマンドで設定する方法
この方法でcronを設定する場合は、crontabコマンドを使用する。
主に使用するコマンドは
「crontab -l」:設定内容の確認
「crontab -e]:設定の編集
まずは「crontab -e」でcron設定を行うためのエディタを設定
$ vi ~/.bashrc
デフォルトエディタをvimに設定する例
$ export EDITOR=vim
$ source ~/.bashrc
設定を行うとユーザ毎に/var/spool/cron/crontabs/[username]というファイルが作成される。
このファイルは直接編集することは推奨されていないので
編集するときは必ず「crontab -e」を使用する。
書式は左から、[分] [時] [日] [月] [曜日] [コマンド]
5分おきにfuga.shを実行する例
*/5 * * * * /home/hoge/fuga.sh
- 分は0~59の数字で指定
- 時は0~23の数字で指定
- 日は1~31の数字で指定
- 月は1~12の数字で指定
- 曜日に関しても数字で指定し、0と7が日曜日、1以降は順に、月、火、水、木、金、土となる
- コマンドは、設定ファイルでパスを通していないものに関してはフルパスで指定するかカレントディレクトリからの相対パスで指定しなければならない。
※各cronのジョブが実行される際のカレントディレクトリは,ユーザのホームディレクトリ。
時間の書き方例
43 23 * * * 23:43に実行
12 05 * * * 05:12に実行
0 17 * * * 17:00に実行
0 17 * * 1 毎週月曜の 17:00に実行
0,10 17 * * 0,2,3 毎週日,火,水曜の 17:00と 17:10に実行
0-10 17 1 * * 毎月 1日の 17:00から17:10まで 1分毎に実行
0 0 1,15 * 1 毎月 1日と 15日と 月曜日の 0:00に実行
42 4 1 * * 毎月 1日の 4:42分に実行
0 21 * * 1-6 月曜日から土曜まで 21:00に実行
0,10,20,30,40,50 * * * * 10分おきに実行
*/10 * * * * 10分おきに実行
* 1 * * * 1:00から 1:59まで 1分おきに実行
0 1 * * * 1:00に実行
0 */1 * * * 毎時 0分に 1時間おきに実行
0 * * * * 毎時 0分に 1時間おきに実行
2 8-20/3 * * * 8:02,11:02,14:02,17:02,20:02に実行
30 5 1,15 * * 1日と 15日の 5:30に実行
※ちなみに全部 * だと毎分実行される。e
by クーロン(cron)をさわってみるお - Qiita
間違いやすい例としては
例えば毎朝5時ちょうどにバックアップを走らせたいというような場合。
○:間違った設定
* 5 * * * /path/to/backup.sh
○:正しい設定
0 5 * * * /path/to/backup.sh
間違った設定をしてしまうと、毎朝5時台の1分毎にバックアップ処理が走ってしまう。
3)/etc/crontabで設定する方法
基本的には2)の方法と同じ書式で設定が可能だが、
あまりこのファイルを直接編集することは推奨されていない。
4)/etc/cron.d/内に設定する方法
ちなみに、「/etc/cron.d/」は
インストールされたパッケージ専用ディレクトリらしいので、
いじる必要なさそう。
by /etc/cron.monthly/ と crontabコマンド の違い - pospomeのプログラミング日記
上記参考記事のような意見もあるが
この方法を使用すると、以降で説明する「crontab -r」で設定を吹き飛ばしてしまう心配がなくなる。
設定する場合は、crontabコマンドの書式と違い、以下のように「ユーザ」を指定する必要がある。
書式は左から、[分] [時] [日] [月] [曜日][ユーザ][コマンド]
5分おきにfuga.shを実行する例
*/5 * * * * root /home/hoge/fuga.sh
またこの方法を使用した場合、複数ファイルに分けて管理ができるため
プロジェクト毎だったり、担当者毎だったりとファイルを分けられることはありがたい。
「crontab -r」対策
詳細は以下ページから参照
crontab -e は「絶対に」使ってはいけない - ろば電子が詰まつてゐる
crontabコマンドには「crontab -r」という一発で全ての設定を消してしまうコマンドがあるため
ミスタイプしてしまうと悲惨なことになる。(eとrは隣同士なので間違えるか可能性が比較的高い)
それを避けるために、は以下のような方法がある。
crontabを使用せず/etc/cron.d/内で設定する方法を使用する
上記でも紹介しているので説明は省略
「crontab -l」後に「crontab -e」を行う
こうすることで、スクリーンログを残しておけば、
何かあったときにサルベージできる。
※ iTerm2を使用しているはデフォルトではログは残さない設定になっているので、別途設定が必要
「crontab -l > /path/file/to」でバックアップを作成後、「crontab -e」を行う。
シンプルな方法。
「crontab -e」にエイリアスを付ける
alias cronedit='crontab -e'
またはcrontabをエイリアスにする
alias crontab='crontab -i'
「/var/spool/cron/crontabs/」内をgitで管理する
$ cd /var/spool/cron/crontab/
$ git init
$ git add root
$ git commit -m "initial commit"
誤って消してしまったら
$ git reset --hard HEAD^