bash 脚本在函数返回后意外退出
bash script exits unexpectedly after returning from function
这是我的 关于堆栈溢出的后续问题。
我会将脚本缩减为基本部分,但如果 s.o。认为,了解脚本的作用可能会有所帮助,您可以查看其他问题。
#!/usr/bin/env bash
set -eu -o pipefail
declare -a framelist
#Print all results
function output_values() {
echo "Results!";
}
#parsing information from stdin
function parser () {
while read tc;
do
if [ -z "$tc" ]; then
continue
fi
#Evaluation and saving result to array
echo $result_value;
framelist+=($result_value);
if (( <<some abort condition>> )); then
exec 0>&-
echo "Last result: $result_value";
return 0
fi
done
}
some_command_writing_to_stdout | parser ;
output_values;
脚本执行命令并将输出通过管道传输到我的本地函数,最终 returns 在行 echo "Last result: $result_value";
处得到预期的结果。在此之后,它将终止提供在此函数中解析的数据的命令 - 这也有效。
当到达 return 0
时,我想应该执行脚本的下一行(命令的正下方)output_values;
,但实际上没有。
即使我直接在 echo 行之前调用 output_values 函数,在解析器函数中打印结果,它也不会被执行。
它变得更加奇怪,因为我可以注释掉 exec 0>&-
并且所有行为都一样。一旦退出解析器函数,即使是应该由此行终止的命令也会终止。
在 returns 之后,我必须更改什么才能处理我的解析器函数的结果?这不是故意的行为。
此致
曼纽尔
让我们看看 man bash
,关于 pipefail
的部分:
pipefail
If set, the return value of a pipeline is the value of the last (rightmost) command to exit with a non-zero status, or zero if all commands in the pipeline exit successfully. This option is disabled by default.
结合set -e
,只要命令(管道)以非零退出状态退出,就会退出,唯一合乎逻辑的结论是:
您的 some_command_writing_to_stdout
必须以非零退出状态退出 (因为显然 parser
与 0
一起存在)。
这可以解释为什么管道中的下一个命令 (parser
) 会被执行,以及为什么您的脚本会在那之后完成。
验证这一点很容易。只需将倒数第二条语句替换为:
(some_command_writing_to_stdout || true) | parser
这是我的
#!/usr/bin/env bash
set -eu -o pipefail
declare -a framelist
#Print all results
function output_values() {
echo "Results!";
}
#parsing information from stdin
function parser () {
while read tc;
do
if [ -z "$tc" ]; then
continue
fi
#Evaluation and saving result to array
echo $result_value;
framelist+=($result_value);
if (( <<some abort condition>> )); then
exec 0>&-
echo "Last result: $result_value";
return 0
fi
done
}
some_command_writing_to_stdout | parser ;
output_values;
脚本执行命令并将输出通过管道传输到我的本地函数,最终 returns 在行 echo "Last result: $result_value";
处得到预期的结果。在此之后,它将终止提供在此函数中解析的数据的命令 - 这也有效。
当到达 return 0
时,我想应该执行脚本的下一行(命令的正下方)output_values;
,但实际上没有。
即使我直接在 echo 行之前调用 output_values 函数,在解析器函数中打印结果,它也不会被执行。
它变得更加奇怪,因为我可以注释掉 exec 0>&-
并且所有行为都一样。一旦退出解析器函数,即使是应该由此行终止的命令也会终止。
在 returns 之后,我必须更改什么才能处理我的解析器函数的结果?这不是故意的行为。
此致
曼纽尔
让我们看看 man bash
,关于 pipefail
的部分:
pipefail
If set, the return value of a pipeline is the value of the last (rightmost) command to exit with a non-zero status, or zero if all commands in the pipeline exit successfully. This option is disabled by default.
结合set -e
,只要命令(管道)以非零退出状态退出,就会退出,唯一合乎逻辑的结论是:
您的 some_command_writing_to_stdout
必须以非零退出状态退出 (因为显然 parser
与 0
一起存在)。
这可以解释为什么管道中的下一个命令 (parser
) 会被执行,以及为什么您的脚本会在那之后完成。
验证这一点很容易。只需将倒数第二条语句替换为:
(some_command_writing_to_stdout || true) | parser