一定時間毎に起動させたい外部と通信するPHPがあります。
cronから呼び出すようにしたところ動作間隔がまちまちでイマイチでした。
そこで、無限ループするシェルスクリプトを記述してPHPを呼び出す際、開始時間と終了時間の差からsleepを入れるようにしたところ、想定通りの間隔で動作するようになりました。
当然ログアウト後も常時動作させたいので /etc/systemd/system に記述したところ(追記に記載します)…当時はサービスとして正常に起動していましたが、数週間後の昨日PHP部分?にて勝手に無限ループが停止しました。
PHPの実行時に何かあったのかもしれませんが…強制終了しようがそれはログに記録しておいて(としていたのに今回はログを調べていても原因が見つからないので困っていますが、それは一旦置きます)、構わず無かったかのように自動でそのまま無限ループを続けさせたいので、何卒よろしくお願い致します。
> 当然ログアウト後も常時動作させたいので /etc/systemd/system に記述したところ(追記に記載します)
/etc/systemd/system に call__hogehoge.service として以下のように記述しています。
[Unit]
Description = call__hogehoge daemon
[Service]
ExecStart = /var/www/cron/hogehoge.sh
ExecStopPost = /var/www/cron/hogehoge.sh
Restart = always
Type = simple
[Install]
WantedBy = multi-user.target
※勿論hogehogeの部分は仮名です。
以上よろしくお願い致します。
ExecStopPost = /var/www/cron/hogehoge.sh
これはいらないと思います。
Restart = always
これが入ってるなら異常終了しても再起動するはずなんですが…。
ログに何か出てませんか?
あと無限ループするシェルスクリプトですが、これで一応希望通りの動作はするでしょうけど書き方がすごく変です(echoのタイミングとかphp-cgiとかwaitとか)。
ずーっと動いているはずのプロセスが止まる原因として、ふたつほど思いつきます。
trap でシグナルを捕捉してください。
$? を残しておけば、どのシグナルを受け取ったか分かります。
何らかの理由で外部から受け取ってるかもしれませんし、スクリプト中の echo は PIPE を通してファイルなどに書かれるでしょうから SIGPIPE を受け取る可能性はあります。
プロセスの制限の方は、ulimit で設定するあれです。
/etc/systemd/system/ の [Service] のところで定義できます。
使えるのは、こちらの Limit で始まるやつ。
http://www.ict.griffith.edu.au/teaching/3420ICT/cgi-bin/man.cgi?systemd.directives+7
CPU とか FSIZE とか、上限に達していても不思議ではありません。
後は、考え方を変えてループしない作りにしてみるとか。
sleep した後に、自分自身を nohup でバックグラウンドで起動する。
#! /bin/sh ... sleep $diference_time nohup hogehoge.sh & # もうひとつ呼び出しておいて、自分は終了する
echo は、なにがしかのファイルにめがけて吐きましょう。
a-kuma3さんありがとうございます。
シェルスクリプトのサービス割り当て自体今回が初めてなので、ご説明いただいた内容についてまだ意味が理解できていないところがあるのですが、租借させていただきます!
a-kuma3さんありがとうございます。
通信プロセスにおけるタイムアウト処理が怪しいことがわかりましたので、その辺を強化して様子を見ることになりました。
ExecStopPost = /var/www/cron/hogehoge.sh
これはいらないと思います。
Restart = always
これが入ってるなら異常終了しても再起動するはずなんですが…。
ログに何か出てませんか?
あと無限ループするシェルスクリプトですが、これで一応希望通りの動作はするでしょうけど書き方がすごく変です(echoのタイミングとかphp-cgiとかwaitとか)。
コメントの編集はできませんね。削除して上げなおすしかありません。
php-cgiだとHTTPヘッダーが出力されるので、php-cliを使うべきだと思います。
waitの理由はわかりました。
「無限ループが停止しました」というのは実際にこのシェルスクリプトのプロセスがなくなっていたということでしょうか?
そうでないなら、他と処理のタイミングを合わせるところでデッドロックが発生していた可能性があるように思います。またはPHPの処理が終わらなかったとか。
uuinfoさんありがとうございます。
ログの記録からPHP内に実装していた通信プロセスにおけるタイムアウト処理が怪しいことがわかりましたので、その辺を強化して様子を見ることになりました。
コメントの編集はできませんね。削除して上げなおすしかありません。
2017/09/04 22:14:48php-cgiだとHTTPヘッダーが出力されるので、php-cliを使うべきだと思います。
waitの理由はわかりました。
「無限ループが停止しました」というのは実際にこのシェルスクリプトのプロセスがなくなっていたということでしょうか?
そうでないなら、他と処理のタイミングを合わせるところでデッドロックが発生していた可能性があるように思います。またはPHPの処理が終わらなかったとか。
uuinfoさんありがとうございます。
2017/09/23 12:16:19ログの記録からPHP内に実装していた通信プロセスにおけるタイムアウト処理が怪しいことがわかりましたので、その辺を強化して様子を見ることになりました。