bash - 在带有函数的 bash 中使用 set -e/set +e

标签 bash shell

我一直在我的脚本中使用这样一个简单的 bash 序言:

#!/bin/bash
set -e

结合模块化/使用功能,这让我今天很头疼。

所以,假设我在某个地方有一个函数

foo() {
  #edit: some error happens that make me want to exit the function and signal that to the caller 
  return 2
}

理想情况下,我希望能够使用多个小文件,将它们的函数包含在其他文件中,然后像这样调用这些函数

set +e
foo
rc=$?
set -e

.这恰好适用于两层例程。但如果 foo 也像那样调用子例程,返回前的最后设置将是 set -e,这将使脚本在返回时退出 - 我不能在调用函数中覆盖它。所以,我要做的是

foo() {
  #calling bar() in a shielded way like above
  #..      

  set +e
  return 2
}

我觉得这非常违反直觉(而且也不是我想要的 - 如果在某些情况下我想使用该函数而不屏蔽故障,而在其他情况下我想处理清理怎么办?)最好的方法是什么?处理这个?顺便提一句。我在 OSX 上这样做,我还没有测试这种行为在 Linux 上是否不同。

最佳答案

Shell 函数实际上没有“返回值”,只有退出代码。

您可以将 && : 添加到调用者,这使得命令“已测试”,并且不会退出它:

foo() {
    echo 'x'
    return 42
}

out=$(foo && :)
echo $out

: 是“空命令”(即它什么都不做)。在这种情况下,它甚至不会被执行,因为它只有在 foo 返回 0(它没有)时才会运行。

这个输出:

x

可以说它有点难看,但话又说回来,所有 shell 脚本都可以说有点难看 ;-)

从 FreeBSD 引用 sh(1),这比 bash 的手册页解释得更好:

 -e errexit
         Exit immediately if any untested command fails in non-interactive
         mode.  The exit status of a command is considered to be explicitly
         tested if the command is part of the list used to control an if,
         elif, while, or until; if the command is the left hand operand of
         an “&&” or “||” operator; or if the command is a pipeline preceded
         by the ! operator.  If a shell function is executed and its exit
         status is explicitly tested, all commands of the function are con‐
         sidered to be tested as well.

关于bash - 在带有函数的 bash 中使用 set -e/set +e,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27793264/

相关文章:

bash - shell 中文件的一列中的唯一单词数

bash - 在子文件夹中查找具有特定文件命名的 mp4 文件,并使用 ffmpeg 每秒从中提取帧

linux - 如何修复 Linux bash 的 'find' 命令中包含空格的路径

linux - 尝试将大量 PDF 的页数输出到日志文件

带有 truecrypt 密码隐藏的 Linux bash shell 脚本

linux - 下载所有网页的Shell脚本?

c - 调用shell脚本后返回主C程序

php - cURL 在 php shell_exec() 上没有按预期工作

linux - 如何递归列出所有文件和目录

python - 从 bash 脚本向 python 传递参数