私はバックグラウンドで3つのプログラムを実行し、フォアグラウンドでいくつかのプログラムを実行するシェルスクリプトを持っており、起動しtrap
て失敗した場合に再起動できるwait
ようにユニットファイルを設定しました。systemd
しかし、プロセスが終了すると、そのスクリプトのすべてのエントリが終了して再起動されるわけではないことがわかりました。このアプリケーションでは、どちらか一方が終了したら再起動する必要があります。
2つの合理的なパスがあります。
- ユニットファイルをハイブし、例外が検出され、すべての例外が終了するようにスクリプトを変更してから、スクリプトを再実行してください。私は何をすべきかわかりません。
- 3つのバックグラウンドプロセスをそれぞれ別々のファイルを持つ独自の単位で構成します
.service
。しかし、.service
失敗したファイルの1つを終了して再起動するためにファイルを作成する方法がわかりません。私は彼らの依存関係を順番に始めるようにソートすることができることを知っていますが、#2が死んだときに#1を殺すか、その逆にする方法がわかりません。
私は管理者を書いたり、プログラムにそれを見つけて自分で終了させたりしたくありません。それが目的ですsystemd
。私は正しい注文を見逃していることを願っています。
.サービスファイル:
[Unit]
Description=Foobar Interface
After=network.target
[Service]
Type=simple
WorkingDirectory=/home/user/scripts
ExecStart=/home/user/scripts/myscript.sh
Restart=always
[Install]
WantedBy=multi-user.target
クンクンスクリプト:
#!/usr/bin/env bash
tty_port=/dev/ttyUSB0
#Clean up any old running processes
pkill -f "cat ${tty_port}"
pkill transport
pkill backgroundprogram
#Configure the target
source /home/user/somescript.sh
foregroundprogram
#Set up the serial port
stty -F $tty_port 115200
#Read from the port in the background
cat $tty_port &
tty_pid=$!
#Wait for tty device to waken
sleep 15
#Send commands to tty device
echo "command1" > $tty_port
sleep 1
echo "command2" > $tty_port
sleep 1
#Start up the transport
/home/user/transport &>> /dev/null &
transport_pid=$!
#Wait a bit for the transport to start
sleep 1
#Start up the main process
/home/user/backgroundprogram &
background_pid=$!
#Wait a bit for it to start
sleep 1
#Finally, start the tty device
echo "command3" > $tty_port
trap "kill ${background_pid} ${tty_pid} ${transport_pid}; exit 1" INT
wait
これらの操作はすべてログに記録するのと同じように機能しますが、3つのプロセスのいずれかが失敗した場合は、すべてのプロセスを終了して再起動せずに実行を続けます。
ベストアンサー1
しかし、プロセスが終了すると、そのスクリプトのすべてのエントリが終了して再起動されるわけではないことがわかりました。このアプリケーションでは、どちらか一方が終了したら再起動する必要があります。
systemd は、下付き文字ではなくシェルスクリプトを監視します。あなたはしません考えるsystemd は子プロセスの終了に応答します。これにより再起動されます。コマンドを実行するたびに。考えてみてください。実行されるシェルスクリプトがある場合...
date
子プロセスを作成して実行し、終了しました。これにより、プロセスの監督者が何らかの措置を講じたくない。
systemdに子プロセスを監視させるには、各プロセスごとに別々の単位ファイルを生成します。
- シリアルポートを設定して読み取るデバイス
- 一つのために
/home/user/transport
- 一つのために
/home/user/backgroundprogram
systemd依存関係を使用してサービスの正しい開始順序を確保し(1つのサービスを停止するとすべて停止することができます)、ディレクティブを使用してEnvironmentFile
ファイルから構成をロードできます。$tty_port
一部の設定コマンド(「ttyデバイスにコマンドを送信...」)を1行に入力するか、ExecStartPre
独自のType=oneshot
サービスを受けることもできます。