在shell脚本中捕获函数的退出状态

6

我有一个非常简单的脚本。

test.sh

_EXECUTE_METHOD () {
  exit 1
}

_EXECUTE_METHOD
ERROR_CODE=$?
if [[ $ERROR_CODE -eq 1 ]]; then
  echo "Got error"
  exit 0
fi

当在函数内部执行exit 1时,此脚本会立即终止。我想从函数中捕获此退出状态并在主脚本中处理它。

我尝试了set -eset +e,但仍然没有成功。我不能使用return语句。

实际输出:

$ sh test.sh 
$ echo $?
1
$

实际输出:

$ sh test.sh
Got error 
$ echo $?
0
$

4
"我不能使用 return 语句。" - 是的,你可以尝试一下。 - melpomene
分号后面缺少 then。另外,[[ 只是可移植性的陷阱;应该使用 [ - Jens
@Jens 即使完全放弃使用 [ 也是可能的。示例 - Jimmix
2个回答

6

在函数内部需要使用return而不是exit

_EXECUTE_METHOD () { return 1; }

_EXECUTE_METHOD || echo "Got error"

exit命令将终止当前shell。如果您必须使用exit命令,请像这样将此函数放入脚本或子shell中:

declare -fx _EXECUTE_METHOD
_EXECUTE_METHOD () { exit 1; }

_EXECUTE_METHOD || echo "Got error"

(..)会在子Shell中执行函数,因此exit只会终止子Shell。


子壳(..),退出代码捕获ERROR_CODE=$?和Bash测试[[似乎是冗余的 - Jimmix
虽然有时需要更多的冗长表述以便更好地理解,但是我同意这个观点。即使是 if..then..else 也可以像现在更新的答案一样缩短。 - anubhava
只是评论一下,我陷入了“declare”内置功能的兔子洞。由于这是一个高级主题,如果您能添加更多信息以解释为什么需要它,那将是很棒的。 - Kiteloopdesign

1

不需要使用[[[

#!/bin/sh

set -eu

_EXECUTE_METHOD () {
  return 1
}

if ! _EXECUTE_METHOD; then
  echo "Got error"
  exit 0
fi

或者如果你想简洁一些:

#!/bin/sh

set -eu

_EXECUTE_METHOD () {
  return 1
}

_EXECUTE_METHOD || { echo "Got error"; exit 0; }

今天学到了一个在Shell脚本中可以实现的之前从未意识到的功能,收获新知识。 - Sharuzzaman Ahmat Raslan

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接