在 bash 脚本中正确使用 EXIT 和 ERR 陷阱

在 bash 脚本中正确使用 EXIT 和 ERR 陷阱

我正在编写一个 bash 脚本,在这个过程中,我了解了陷阱、信号、函数返回码和其他我以前没有使用过的功能。

我的想法可能是错误的 - 我正在寻求一些建议。

我正在设置以下选项:

set -o errexit
set -o nounset
set -o noclobber

我的 bash 脚本中有以下退出和错误陷阱:

# Error handler. This function is called anytime an ERR signal is received.
# This function should never be explictly called.
function _trap_error () {
    if [ ! -v _VERBOSE ]; then
        echo "An error has occurred. Exiting."
    else
        _name="$0"                # name of the script
        _lastline="$1"            # argument 1: last line of error occurence
        _lasterr="$2"             # argument 2: error code of last command
        echo "${_name}: line ${_lastline}: exit status of last command: ${_lasterr}"
        exit 1
    fi
}
trap '_trap_error ${LINENO} ${$?}' ERR

# Exit handler. This function is called anytime an EXIT signal is received.
# This function should never be explicitly called.
function _trap_exit () {
    [ -v _POPD ] && popd &> /dev/null
}
trap _trap_exit EXIT

他们的工作正如我所期望的那样。我没有将错误检查插入到我的所有函数中,而是尝试利用陷阱来为我处理这个问题,例如在检查文件是否存在时。如果无法加载指定的模块,我想将其捕获为错误,显示错误消息,然后退出。

function _module_path () {
    echo "mod.d/$2s/$1/__init__.sh"
}

function _module_exists () {
    [ -f $(_module_path $1 $2) ] && return 0 || return 1
}

function _module_push () {
    _module_exists $1 $2 && _MODULES+=$( _module_path $1 $2 ) || msg "Module $1 does not exist."
}

但是,将返回代码设置为 0 并结合 errexit 会触发 EXIT 信号,该信号会被我的退出陷阱捕获。我开始尝试弄清楚是否可以手动发出 ERR 信号,但还没有找到答案,并开始怀疑我是否正确地处理了这个问题。

相关内容