まずは、atコマンドで次の日の深夜零時に実行するコマンドを登録する例。これと同じスキームで、様々なコマンドをキューイングして一時間おきに先入れ先出しで順番に実行するようにしたい。
$ echo -e 'hoge;\nfuga;' | at midnight
実行予定のコマンドはatで登録、登録時にコマンドの実行時刻を指定する部分を工夫する。新しいコマンドの登録時に登録済みのコマンド実行時刻を走査し、最も未来に実行するコマンドの実行時刻を見つけ、これに+1時間したものを新しいコマンドの実行時刻としてコマンドを登録。新しいコマンドの登録時に登録済みコマンドが見つからなければ次の日の0時を新しいコマンドの実行時刻としてコマンドを登録。以下の様なスクリプトとしてまとめてみた。基本的には上のat midnightの部分をsh delay_run.shに置換するだけで解決。
$ cat delay_run.sh #!/bin/sh # $ echo -e 'hoge;\nfuga;' | sh delay_run.sh set -e -x QUEUE=A TIME=`at -l -q ${QUEUE} | sort -k6,6n -k3,3M -k4,4n -k5,5 | tail -n 1 | awk '{cmd = sprintf("date --date \"%s %s %s %s\" +\"%%s\"",$4,$3,$6,$5); cmd | getline t; close(cmd); print t;}'` if [ "${TIME}" != "" ] ; then #num=`expr \( \( ${B} - ${A} \) / 3600 \) + 1` TIME=`expr ${TIME} + 3600` else TIME=`date --date '1 day 0:00' +'%s'` fi TIME=`date --date @${TIME} +'%R %F'` cat < /dev/stdin | at -q ${QUEUE} ${TIME}
実行管理はat任せなので、jobを入れ替えたいとか、順番を変えたいとかの場合はいちいち登録作業をやり直さなければいけないけれどね。