Можно ли как-то добавить «&& prog2» к уже запущенному prog1?


87

Большинство оболочек предоставляют такие функции, как &&и ;цепочка выполнения команд определенным образом. Но что, если команда уже запущена, могу ли я как-то добавить еще одну команду, которая будет выполняться в зависимости от результата первой?

Скажи я побежал

$ /bin/myprog
some output...

но я очень хотел /bin/myprog && /usr/bin/mycleanup. Я не могу убить myprogи перезапустить все, потому что слишком много времени будет потеряно. Я могу Ctrl+ Zэто и fg/ bgпри необходимости. Позволяет ли это мне соединиться в другой команде?

В основном меня интересует bash, но ответы на все распространенные оболочки приветствуются!

Ответы:


118

Вы должны быть в состоянии сделать это в той же оболочке, в которой вы используете waitкоманду:

$ sleep 30 &
[1] 17440

$ wait 17440 && echo hi

...30 seconds later...
[1]+  Done                    sleep 30
hi

выдержка из страницы руководства Bash

wait [n ...]
     Wait for each specified process and return its termination status. Each n 
     may be a process ID or a job specification; if a job spec is given,  all 
     processes  in that job's pipeline are waited for.  If n is not given, all 
     currently active child processes are waited for, and the return status is 
     zero.  If n specifies a non-existent process or job, the return status is 
     127.  Otherwise, the return status is the exit status of the last process 
     or job waited for.

Ожидание команды должно сделать работу.
— BillThor

Существует несколько кратких форм для ввода PID фонового процесса, таких как %, %1и $!. Важно указать PID, иначе всегда будет работать вторая команда.
— BillThor

@BillThor - вы просто уточняете ответ или говорите мне это?
— Slm

Я уточняю ответ. Равнина waitне сможет обеспечить желаемый результат. Обычно используются короткие формы, так как они менее подвержены опечаткам.
— BillThor

2
Позвольте мне первым поздравить вас с новым блестящим значком :)
— terdon

63

fgвозвращается с кодом выхода из программы, которую он возобновляет. Поэтому вы можете приостановить вашу программу с помощью, ^Zа затем использовать fg && ...для ее возобновления.

$ /bin/myprog
some output...
^Z
[1]+ Stopped              /bin/myprog
$ fg && /usr/bin/mycleanup

если вы снова приостановите работу до ее завершения и выполните то же самое с другой командой, заменяется ли первоначальная цепочка mycleanup?
— Бурхан Али

3
@BurhanAli Приостановка myprogво второй раз приводит fgк завершению с кодом завершения 20, который не равен нулю, поэтому связанная mycleanupкоманда не выполняется.
— n.st

1

Не уверен, что то, что вы запрашиваете, возможно, но если у вас все еще есть оболочка, из которой вы запустили программу, вы всегда можете проверить состояние $?завершения последнего процесса:

$ /bin/myprog
some output...
$ if [ $? -ne 0 ];then echo "non-zero exit status";else echo "0 exit status";fi

1
Это будет работать, но он должен будет выполнить это вручную после этого, он хочет запустить это автоматически, когда команда завершится.
— SLM

@slm Согласен. У меня нет решения этой проблемы.
— Джозеф Р.

3
Проверьте waitкоманду в Bash.
— SLM

1

Если задание находится на переднем плане, любая из этих команд будет работать так же, как вы ожидаете.

[ $? -eq 0 ] && prog2
(( $? )) || prog2

ПРИМЕЧАНИЕ: $? будет содержать статус возврата работающей программы при выходе.

Это явно указывает, что будет делать оболочка, если вы изначально ввели команду.

prog1 && prog2

Если первая команда не читает stdinи выполняется на переднем плане, новая команда может быть введена во время выполнения первой команды. Оболочка прочитает и выполнит ее при выполнении первой команды. Если команда будет работать в фоновом режиме, вряд ли она читает stdin.

РЕДАКТИРОВАТЬ: WAITТакже можно использовать задание в фоновом режиме и использовать команду. Это должно быть сделано с осторожностью, если другие задания также выполнялись в фоновом режиме. В спецификации задания требуется, чтобы WAITкоманда возвращала статус ожидаемого задания.


Это будет работать, но он должен будет выполнить это вручную после этого, он хочет запустить это автоматически, когда команда завершится.
— SLM

4
@slm Пока команда не читает stdin, новую команду можно вводить во время выполнения первой команды. Оболочка прочитает его, как только будет выполнена первая команда.
— BillThor

Если он что-то делает в скорлупе после того, как он был заземлен, скорее всего, он шланг. По крайней мере, согласно предварительному. тестирование я делал до сих пор!
— SLM

2
@BillThor Я думаю, вы должны добавить этот комментарий к своему ответу.
— Джозеф Р.

2
Да, использование waitтоже не идеально. Преимущество IMO заключается в том, что он дает нам более понятный API, с которым мы имеем дело. Вводить больше команд в командной строке после запуска чего-либо мне показалось немного странным. waitпо-прежнему страдает от отсутствия прямой ссылки на работающий PID, по сравнению с состоянием возврата. Похоже, это проблема больше, поскольку Bash реализует некоторые вещи: stackoverflow.com/questions/356100/… . Так что это может быть так же хорошо, как и получается.
— SLM
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.