Bash,评估中的CTRL + C不会中断主脚本 [英] Bash, CTRL+C in eval not interrupting the main script
问题描述
在我的bash脚本中,我正在运行一个存储在 $ cmd
变量中的外部命令.(可以是任何东西,甚至可以是一些简单的bash oneliner.)
In my bash script, I'm running an external command that's stored in $cmd
variable. (It could be anything, even some simple bash oneliner.)
如果在运行脚本时按下 ctrl + C ,我希望它杀死当前正在运行的 $ cmd
,但仍应继续运行主脚本.但是,我想保留在运行主脚本时使用 ctrl + C 杀死主脚本的选项.
If ctrl+C is pressed while running the script, I want it to kill the currently running $cmd
but it should still continue running the main script. However, I would like to preserve the option to kill the main script with ctrl+C when the main script is running.
#!/bin/bash
cmd='read -p "Ooook?" something; echo $something; sleep 4 '
while true; do
echo "running cmd.."
eval "$cmd" # ctrl-C now should terminate the eval and print "done cmd"
echo "done cmd"
sleep 5 # ctrl-C now should terminate the main script
done
有人知道如何以一种不错的bash方式进行操作吗?
Any idea how to do it some nice bash way?
根据答案应用的更改:
#! /bin/bash
cmd='read -p "Ooook1?" something; read -p "Oook2?" ; echo $something; sleep 4 '
while true; do
echo "running cmd.."
trap "echo Interrupted" INT
eval "($cmd)" # ctrl-C now should terminate the eval and print "done cmd"
trap - INT
echo "done cmd"
sleep 5 # ctrl-C now should terminate the main script
done
现在,在"Ooook1?"时按 ctrl + C .只有完成读取后,读取才会中断评估.(它将在"Oook2"之前中断.)但是,它将立即中断"sleep 4".
Now, pressing ctrl+C while "Ooook1?" read will break the eval only after that read is done. (it will interrupt just before "Oook2") However it will interrupt "sleep 4" instantly.
在这两种情况下,它都将做正确的事情-它将中断eval子外壳,所以我们快到了-只是那种奇怪的读取行为.
In both cases it will do the right thing - it will just interrupt the eval subshell, so we're almost there - just that weird read behaviour..
推荐答案
如果您有能力在子shell中运行 eval
部分,那么您要做的全部"就是捕获SIGINT.>
If you can afford having the eval
part run in a subshell, "all" you need to do is trap SIGINT.
#! /bin/bash
cmd='read -p "Ooook1?" something; read -p "Oook2?" ; echo $something; sleep 4 '
while true; do
echo "running cmd.."
trap "echo Interrupted" INT
eval "($cmd)" # ctrl-C now should terminate the eval and print "done cmd"
trap - INT
echo "done cmd"
sleep 5 # ctrl-C now should terminate the main script
done
虽然不知道这是否适合您的特定需求.
Don't know if that will fit your specific need though.
$ ./t.sh
running cmd..
Ooook1?^CInterrupted
done cmd
^C
$ ./t.sh
running cmd..
Ooook1?qsdqs^CInterrupted
done cmd
^C
$ ./t.sh
running cmd..
Ooook1?qsd
Oook2?^CInterrupted
done cmd
^C
$
GNU bash, version 4.1.9(2)-release (x86_64-pc-linux-gnu)
这篇关于Bash,评估中的CTRL + C不会中断主脚本的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!