Подтвердить что ты не робот

В Bash, как я могу запускать несколько бесконечно работающих команд и отменить их все с помощью ^ C?

Я хотел бы написать script, который запускает несколько разных бесконечно запущенных команд, например

run_development_webserver.sh
watch_sass_files_and_compile_them.sh
watch_coffeescript_files_and_compile_them.sh

Я хотел бы запустить каждую из них параллельно и убить всех, нажав ^ C. Возможно ли это, и если да, то как я могу это сделать?

4b9b3361

Ответ 1

Я позволю адмиралу Акбару ответить на этот вопрос.

trap

#!/bin/bash -e

run_development_webserver.sh &
PIDS[0]=$!
watch_sass_files_and_compile_them.sh &
PIDS[1]=$!
watch_coffeescript_files_and_compile_them.sh & 
PIDS[2]=$!

trap "kill ${PIDS[*]}" SIGINT

wait

Это запускает каждую из ваших команд в фоновом режиме (&), помещает их идентификаторы процесса ($!) в массив (PIDS[x]=$!), сообщает bash to kill все их (${PIDS[*]), когда ваш script получает сигнал SIGINT (Ctrl + C), а затем wait для всех процессов для выхода.

И я буду активно упоминать, что "kill ${PIDS[*]}" расширяет PIDS при создании trap; если вы смените двойные кавычки (") на одинарные кавычки ('), он будет расширен при выполнении trap, что означает, что вы можете добавить больше процессов в PIDS после установки trap и это тоже убьет их.

Если у вас есть упрямый процесс, который не хочет выходить после Ctrl + C (SIGINT), вам может потребоваться отправить более сильный сигнал kill - SIGTERM или даже SIGKILL (используйте это как последнее средство, он безоговорочно убивает процесс, не давая ему возможности очистить). Сначала попробуйте изменить строку trap на следующее:

trap "kill -TERM ${PIDS[*]}" SIGINT

Если он не отвечает на SIGTERM, сохраните этот процесс pid отдельно, скажем в STUBBORN_PID, и используйте это:

trap "kill ${PIDS[*]}; kill -KILL $STUBBORN_PID" SIGINT

Помните, что этот не позволит упрямому процессу очистить, но если ему нужно умереть, а его нет, вам может понадобиться его использовать.