bash 脚本多个 if 条件不执行/工作

bash 脚本多个 if 条件不执行/工作

我正在尝试编写基于输入的 bash 脚本,该脚本将触发相应的应用程序构建脚本。如果输入是“all”,那么所有应用程序都会被调用。我在这里面临问题,如果输入为“all”,则只有 app_1 和 app_2 被调用。可能是什么问题,

if [ "${_BUILD_MODE}" = "all" ] || [ "${_BUILD_MODE}" = "app_1" ]
then 
   echo "BUILD_STAGE APP_1 build started"
fi
if [ "${_BUILD_MODE}" = "all" ] || [ "${_BUILD_MODE}" = "app_2" ]
then 
   echo "BUILD_STAGE APP_2 build started"
fi
if [ "${_BUILD_MODE}" = "all" ] || [ "${_BUILD_MODE}" = "app_3" ]
then 
   echo "BUILD_STAGE APP_3 build started"
fi
if [ "${_BUILD_MODE}" = "all" ] || [ "${_BUILD_MODE}" = "app_4" ]
then 
   echo "BUILD_STAGE APP_4 build started"
fi
if [ "${_BUILD_MODE}" = "all" ] || [ "${_BUILD_MODE}" = "app_5" ]
then 
   echo "BUILD_STAGE APP_5 build started"
fi
if [ "${_BUILD_MODE}" = "all" ] || [ "${_BUILD_MODE}" = "app_6" ]
then 
   echo "BUILD_STAGE APP_6 build started"
fi

答案1

您在此处提供的示例代码不会发生这种情况。想必这些echos 只是您正在执行的更复杂任务的占位符,我的猜测是任务实际上app_2改变了 的值$_BUILD_MODE

在这里,你可以这样做:

case $_BUILD_MODE in
  (all | app_1) task for app_1 ;;&
  (all | app_2) task for app_2 ;;&
  (all | app_3) task for app_3 ;;&
  ...
esac

这将使它更短、更整洁,并且还避免了这个特定问题,因为$_BUILD_MODE在开始时只取消引用一次。

;;&上面是 bash 特定的。在 zsh 和 mksh 中,等效语法是 with ;|。 zsh、mksh 和 bash 支持;;(来自 Bourne shell,也是唯一的标准 shell)和;& (来自 Korn shell)。

app_2调用exit或或 的任务也可能exec some-other-command遇到致命错误或 shell 进程被终止。解决这个问题的方法是通过将子 shell 包装在(...).

bash -o xtrace尝试使用(与 相同)运行脚本,bash -x看看会发生什么。


1 例如,如果内置程序写入损坏的管道,则通过 SIGPIPE;如果超出某些资源限制,则通过 SIGXCPU...

答案2

并不是真正关于你在问什么,但是当你在那里重复一些代码时,这种 if 链看起来很尴尬,即使它只是在[ "${_BUILD_MODE}" = "all" ]这里。

相反,我将任务放入例如函数中,并用它们的名称创建一个数组(未经测试):

app_1() {
    echo "BUILD_STAGE APP_1 build... "
}
app_2() {
    echo "BUILD_STAGE APP_2 build... "
}
tasks=(app_1 app_2)

for task in "${tasks[@]}"; do 
    if [ "${_BUILD_MODE}" = "all" ] || [ "${_BUILD_MODE}" = "$task" ]; then
        "$task"
    fi
done

请注意,函数名称必须与此处使用的任务名称相同_BUILD_MODE

在这里,如果您需要更改任务的运行方式,例如将它们包装在子 shell 中,例如斯蒂芬建议,或者添加一些打印输出来分隔它们,您可以在循环中的一个位置执行此操作。

相关内容