😊

Linuxジョブスケジューリング

2021/05/01に公開

ジョブスケジューリング

Linux環境で定期的に実行する作業については、ジョブスケジューリングを組むことによって自動的に実行されるように設定できる。自動的に実行されるように設定することで、システム管理コストの抑えることが可能になる。

cron

定期的にジョブを実行するためには使用するcronは、ジョブスケジューリングを管理するデーモンであるcrondと、スケジューリングを設定するcrontabコマンドから構成される。

実行環境

検証した環境はEC2でOSはAmazon Linux2。

[ec2-user@sandbox ~]$ cat /etc/os-release 
NAME="Amazon Linux"
VERSION="2"
ID="amzn"
ID_LIKE="centos rhel fedora"
VERSION_ID="2"
PRETTY_NAME="Amazon Linux 2"
ANSI_COLOR="0;33"
CPE_NAME="cpe:2.3:o:amazon:amazon_linux:2"
HOME_URL="https://amazonlinux.com/"
[ec2-user@sandbox ~]$ 

cronの登録

以下のコマンドでcron式を編集し、cronを登録する。

[ec2-user@sandbox ~]$ crontab -e

1分ごとにhello worldをechoし、hello.logに追記するジョブをcronに登録した。

# minite hour day month dow command
* * * * *  /home/ec2-user/hello.sh >> hello.log

cron式の確認

以下のコマンドで、cron式を確認することができる。

[ec2-user@sandbox ~]$ crontab -l
# minite hour day month dow command
* * * * *  /home/ec2-user/hello.sh >> hello.log

各値に設定できる数字は以下

  • minite: 0~59
  • hour: 0~23
  • day: 1~31
  • month: 1~12
  • dow: 0~7(0,7:日曜~6:土曜)

各ユーザがcrontab -eコマンドで生成したcrontabファイルは、/var/spool/cronディレクトリ配下に格納されている。

[ec2-user@sandbox ~]$ sudo cat /var/spool/cron/ec2-user
# minite hour day month dow command
* * * * *  /home/ec2-user/hello.sh >> hello.log

cron実行結果の確認

毎分hello.logにhello worldが追記されていることが確認できた。

[ec2-user@sandbox ~]$ cat hello.log 
hello world
hello world
hello world

cron設定の削除

以下のコマンドで、cronの設定を削除することができる。

[ec2-user@sandbox ~]$ crontab -l # cronの確認
# minite hour day month dow command
* * * * *  /home/ec2-user/hello.sh >> hello.log

[ec2-user@sandbox ~]$ crontab -r # cronの削除
[ec2-user@sandbox ~]$ crontab -l #cronの確認
no crontab for ec2-user
[ec2-user@sandbox ~]$ 

cron実行ログの確認

cronが正しく実行されているかは、/var/log/cronで確認可能。

[ec2-user@sandbox ~]$ sudo tail /var/log/cron
May  1 07:42:01 ip-xxx-xxx-xxx-xxx CROND[29297]: (ec2-user) CMD (/home/ec2-user/hello.sh >> hello.log)
May  1 07:43:01 ip-xxx-xxx-xxx-xxx CROND[29350]: (ec2-user) CMD (/home/ec2-user/hello.sh >> hello.log)
May  1 07:44:01 ip-xxx-xxx-xxx-xxx CROND[29403]: (ec2-user) CMD (/home/ec2-user/hello.sh >> hello.log)
May  1 07:45:01 ip-xxx-xxx-xxx-xxx CROND[29470]: (ec2-user) CMD (/home/ec2-user/hello.sh >> hello.log)

システム用のcrontabファイル

ユーザ用のcrontabファイルとは別に、システムが実行するジョブを定義した(logrotateとか)crontabファイルも存在する。
ユーザごとcrontab -eコマンドでcronを設定することもできるが、誤ってcrontab -rでcronを削除してしまう可能性もあるので、実行ユーザを指定することができる/etc/crontabまたは、/etc/cron.d/に設定することをおすすめする。

他crontab関連のファイルとディレクトリについて

ファイル/ディレクトリ 説明
/etc/cron.hourly/ 1時間に1度実行されるcronジョブを記述したファイルを収めたディレクトリ
/etc/cron.daily/ 1日に1度実行されるcronジョブを記述したファイルを収めたディレクトリ
/etc/cron.weekly/ 週に1度実行されるcronジョブを記述したファイルを収めたディレクトリ
/etc/cron.monthly/ 月に1度実行されるcronジョブを記述したファイルを収めたディレクトリ
/etc/cron.d/ 個別に設定した時間で実行されるcronジョブを記述したファイルを収めたディレクトリ
上記に記載したディレクトリ内のファイルがいつ実行されるかは、/etc/crontabファイル内に記載する。

/etc/crontabファイルの中身

[ec2-user@sandbox ~]$ cat /etc/crontab 
SHELL=/bin/bash
PATH=/sbin:/bin:/usr/sbin:/usr/bin
MAILTO=root

# For details see man 4 crontabs

# Example of job definition:
# .---------------- minute (0 - 59)
# |  .------------- hour (0 - 23)
# |  |  .---------- day of month (1 - 31)
# |  |  |  .------- month (1 - 12) OR jan,feb,mar,apr ...
# |  |  |  |  .---- day of week (0 - 6) (Sunday=0 or 7) OR sun,mon,tue,wed,thu,fri,sat
# |  |  |  |  |
# *  *  *  *  * user-name  command to be executed
00 * * * * root run-parts /etc/cron.hourly
00 0 * * * root run-parts /etc/cron.daily
00 0 * * 0 root run-parts /etc/cron.weekly
00 0 1 * * root run-parts /etc/cron.monthly

run-partsコマンド

run-partsコマンドは、指定したディレクトリ内にあるスクリプトや実行ファイルを実行するコマンド。

cronのアクセス制御

cronを実行可能なユーザを制御するためには、/etc/cron.allow、/etc/cron.denyを設定する。

  • /etc/cron.allow: cronの利用を許可するユーザを指定する。
  • /etc/cron.deny: cronの利用を拒否するユーザを指定する。

/etc/cron.allowが存在すれば、記述されているユーザのみがcronを利用できる。(/etc/cron.denyは無視される)
/etc/cron.allowがなければ、/etc/cron.denyを参照し、/etc/cron.denyに記述されていない全てのユーザがcronを利用できる。

at

atコマンドは1回限りの実行スケジュールを扱い、atコマンドの実行にはatデーモンが動作している必要がある。

atコマンドの実行

atコマンドを実行してみる。
以下、コマンド

[ec2-user@sandbox ~]$ at -t 202105011106
at> echo 'test' > at_test.txt         
at> <EOT> # ctl + dでatコマンド終了
2021年  5月  1日 土曜日 11:05:46 UTC

atコマンドで登録されたジョブの一覧を確認

atコマンドで登録されたジョブの一覧を確認するためには、atqコマンド、または、at -lを実行する。

[ec2-user@sandbox ~]$ atq # atqコマンドで登録されたジョブを確認
3	Sat May  1 11:06:00 2021 a ec2-user

atコマンドで登録したジョブの実行結果を確認

atコマンドで登録したジョブが実行され、at_test.txtが作成されている。

[ec2-user@sandbox ~]$ ls | grep at_*
at_test.txt
[ec2-user@sandbox ~]$ 

atコマンドで登録したジョブを削除する

atコマンドで登録したジョブを削除するためには、atrm ジョブ番号または、at -d ジョブ番号を実行する。

[ec2-user@sandbox ~]$ at -t 202105021106
at> echo 'test' > atrm_test.txt
at> <EOT>
job 4 at Sun May  2 11:06:00 2021
[ec2-user@sandbox ~]$ at -l
4	Sun May  2 11:06:00 2021 a ec2-user
[ec2-user@sandbox ~]$ atrm 4
[ec2-user@sandbox ~]$ at -l

atのアクセス制御

atを実行可能なユーザを制御するためには、/etc/at.allow、/etc/at.denyを設定する。

  • /etc/at.allow: atの利用を許可するユーザを指定する。
  • /etc/at.deny: at利用を拒否するユーザを指定する。

/etc/at.allowが存在すれば、記述されているユーザのみがatを利用できる。(/etc/at.denyは無視される)
/etc/at.allowがなければ、/etc/at.denyを参照し、/etc/at.denyに記述されていない全てのユーザがcronを利用できる。
どちらのファイルもなければ、rootユーザだけがatを利用することができる。

atコマンドでの日時指定書式一覧

指定日時 書式
午前10時 10:00、10am
正午 noon
今日 today
3日後 now + 3days
2週間後の22:00 10pm + 2weeks

Discussion