shellscriptファイルを多重起動せず、アトミックに実行するにはちょっとしたコツが要るんだなって話。
大前提として、
- まず一番に案が出るであろう、ロックファイルの作成での排他制御は無理。
- シンボリックリンクの作成でアトミックに実行できるようになる。(flock、ハードリンクやフォルダ作成など、他にも方法はあるがこれが丁度良いか)
先に言っておくと以下の2記事以上のページは無いかと。
https://heartbeats.jp/hbblog/2013/10/atomic03.html
https://qiita.com/bsdhack/items/2492e9bdad0d3e17b7bb
上記記事を踏まえた上で、私の環境では以下が望ましい。
- シンボリックリンク作成失敗時、exitせずにループ確認したい
- ファイル途中からアトミックにしたいので、trap等によるシンボリックリンク削除は使用しない
- PID確認までは大げさか(ちょっと他の懸案点が出ないかが心配)
- 複数実行された場合、処理の順番は気にしない
という事で、カスタマイズを行った。
#!/bin/bash
LOCK_FILE=/tmp/lock
# 以下前処理
:
:
:
# 排他処理開始
count=0
while true ; do
if ln -s $$ $LOCK_FILE >/dev/null 2>&1; then
break
fi
# 1秒スリープ
sleep 1
count=$(( count + 1 ))
if [ $count -eq 60 ]; then
# 60秒でタイムアウト(イレギュラー)
echo "LOCK TIMEOUT ERROR !!!"
rm -f $LOCK_FILE >/dev/null 2>&1
exit 0
fi
done
# 以下メインプロセス
:
:
:
# プロセスの最後やexit前にシンボリックリンクを削除
rm -f $LOCK_FILE
シンボリックリンクはきちんと必ず消す事にはなるとは思うが、
念には念を、どうしても永久ループは避けるようにしたい。