我想在bash中杀死一个后台进程
$SCRIPT_DIR/utils/monitor.sh -f $root/save &
$SCRIPT_DIR/utils/run.sh -f $save
$SCRIPT_DIR/utils/Monkey.sh -f $save
我想在完成Monkey.sh后杀死monitor.sh。
我尝试使用pid,但它无效。
答案 0 :(得分:1)
您正在寻找'jobs'和'kill'命令
$ ls -l
total 4.0K
-rwxr-xr-x. 1 probinson probinso 52 Aug 13 14:25 x.sh
lrwxrwxrwx. 1 probinson probinso 4 Aug 13 14:28 y.sh -> x.sh
lrwxrwxrwx. 1 probinson probinso 4 Aug 13 14:28 z.sh -> y.sh
$ cat x.sh
for i in $(find / 2> /dev/null ); do echo ${i} &> /dev/null; done
$ ./x.sh & ./y.sh & ./z.sh &
$ jobs
[1] Running ./x.sh &
[2]- Running ./y.sh &
[3]+ Running ./z.sh &
$ kill %2
$ jobs
[1] Running ./x.sh &
[2]- Terminated ./y.sh &
[3]+ Running ./z.sh &
$ jobs
[1]- Running ./x.sh &
[3]+ Running ./z.sh &
# this should kill job one after job three finishes
$ ./x.sh; x.sh & y.sh & z.sh; kill %1
答案 1 :(得分:1)
看起来这个问题可能与调用monitor.sh的方式有关。如果我有一个脚本' foo.sh'它只有一个shell命令,我不认为它被识别为' foo.sh'在ps
列表中,但如果我使用sh
(或bash
)调用它,那么我会这样做。似乎如果' foo.sh'是一个shell命令列表,shell会将其更改为bash,你不会看到foo.sh'在ps
列表中,但如果我用bash明确地称它,即
bash foo.sh
然后我在ps列表中看到它。
然而,shell脚本的最佳实践是从适当的' hashbang'开始。命令,即对于bash脚本,第一行应该是
#!/bin/bash
这似乎也解决了我的问题。我猜测monitor.sh可能会遗漏这一行,这就是为什么你不能使用ps
或killall
看到它。一旦到位,你应该可以做到
killall -9 monitor.sh
或类似的它会起作用。要么是以bash monitor.sh
调用它,要么将其作为{{1}}调用,但通常的最佳做法是以任一方式包含第一行。
答案 2 :(得分:1)
另一种方法是保存后台进程的PID:
$SCRIPT_DIR/utils/monitor.sh -f $root/save &
MONITOR_PID=$!
...
kill $MONITOR_PID
这优于killall
的优势在于它会杀死这个特定的过程。如果您运行的脚本有多个副本,则不会终止同时运行的其他monitor.sh
脚本。
答案 3 :(得分:0)
您有多种选择:
首先,您可以使用kill。但是您需要使用ps,pidof或pgrep来获取流程的pid。
ps -A // to get the pid, can be combined with grep
-or-
pidof <name>
-or-
pgrep <name>
kill <pid>
可以通过知道名称来杀死进程。使用pkill或killall。
pkill <name>
-or-
killall <name>
所有命令都向进程发送信号。如果进程挂起,可能需要向进程发送sigkill(这是信号9,因此以下示例也是如此):
pkill -9 <name>
pkill -SIGKILL <name>
您也可以将此选项与kill
和killall
一起使用。
阅读这篇关于controlling processes的文章,以获得有关流程的更多信息。
归功于tanascius
你应该试试
killall Monkey.sh