【发布时间】:2019-08-28 17:44:57
【问题描述】:
当我启用set -o errexit 并且代码中的变量为空时,我有以下 bash 代码(在 Red Hat 上运行)退出,但在设置变量时工作正常;该代码旨在测试是否存在匹配.monitor_* 的屏幕会话,如果存在则执行操作。
我开启了以下功能:
set -o errexit
set -x xtrace; PS4='$LINENO: '
如果存在与上述模式匹配的会话,则它可以工作;但是,如果没有匹配项,它只会退出,除了 xtrace 的以下输出之外没有任何信息
someuser:~/scripts/tests> ./if_test.sh
+ ./if_test.sh
+ PS4='$LINENO: '
4: set -o errexit
5: set -o pipefail
6: set -o nounset
88: /usr/bin/ls -lR /var/run/uscreens/S-storage-rsync
88: grep '.monitor_*'
88: awk '{ print $9 }'
88: /usr/bin/grep -Ev 'total|uscreens'
8: ms=
我测试了我用来设置ms var 的命令,它与xtrace 输出一致,它没有设置。
someuser:~/scripts/tests> test -n "${mn}"
+ test -n ''
我尝试使用 select 语句并得到相同的结果...我无法弄清楚,有人能帮忙吗?谢谢。
我阅读了所有可能的解决方案建议,似乎没有任何解决我的问题。
代码:
#!/usr/bin/env bash
set -o xtrace; PS4='$LINENO: '
set -o errexit
set -o pipefail
set -o nounset
ms="$(/usr/bin/ls -lR /var/run/uscreens/S-"${USER}" | /usr/bin/grep -Ev "total|uscreens" | grep ".monitor_*" | awk '{ print $9 }')"
if [[ -z "${ms}" ]]; then
echo "Handling empty result"
elif [[ -n "${ms}" ]]; then
echo "Handling non-empty result"
fi
提出以下答案:Test if a variable is set in bash when using "set -o nounset";但是,它根本没有解决问题。在我的情况下,正在测试的变量已设置,正如我在详细信息中所述,它设置为"",或者什么都没有。谢谢;但是,它没有帮助。
这似乎是它不喜欢的变量声明。
ms="$(/usr/bin/ls -lR /var/run/uscreens/S-"${USER}" | /usr/bin/grep -Ev "total|uscreens" | grep ".monitor_*" | awk '{ print $9 }')"
【问题讨论】:
-
你正在运行
set -o pipefail。当grep不匹配任何内容时,它的退出状态为非零,而pipefail则使整个管道失败。这一切都完全按照你告诉你的shell它应该表现的方式。 -
顺便说一句,在决定使用
set -o errexit之前,我强烈建议先完成BashFAQ #105 中的练习。 -
好吧,我的 main 建议是不要使用
set -e。当然,您始终可以为特定的管道组件添加条件。