通过脚本(Bash)执行时未加载模块



我正在编写一个bash脚本来对文件执行一些命令。为了做到这一点,我需要加载包含这些命令的模块。现在我可以从命令行完成这些工作,但是我想在脚本中实现检查,看看这些模块是否已加载,如果没有,则加载它们。以下是我到目前为止所做的(我刚刚学习bash 3天,所以请原谅任何新手错误):

#A list with all the necessary modules
declare -a modules=("CDO/1.9.7-gompi-2019a" "ncview/2.1.7-gompi-2019a")
echo "Running script"
echo ""
#Check if modules are loaded. If not, load them
for mod in "${modules[@]}"
do
module is-loaded $mod
if [ $? = 1 ]
then
echo "Loading ${mod}"
module load $mod
else
echo "${mod} is already loaded"
fi
done
echo ""
echo "Finished running script"

它进入if语句,意味着模块没有加载,然后说"Loading CDO…",但是当我试图使用这个模块的命令时,它不起作用,因为模块似乎没有被执行。但是"模块已加载"执行得很好。我做错了什么?

[diyon@login2 scripts]$ ./script.sh
Running script
Loading CDO/1.9.7-gompi-2019a
Loading ncview/2.1.7-gompi-2019a
Finished running script
[diyon@login2 scripts]$ cdo
-bash: cdo: command not found

线索就在全名中:" Environment Modules "

这些模块(不要与内核模块或任何其他模块混淆)是用于配置当前环境(用于开发环境,管理员等)的工具。

直到今天我才听说这些。根据这些幻灯片,他们使用包含用Tcl编写的声明性环境描述的模块文件。当您加载它们时,它们被转换为shell语法,并在当前环境中执行eval

<>———————-

你的脚本没有工作的原因是一个shell脚本在一个新的进程中执行,并且不能改变它的父进程的环境-你启动它的shell。您配置了脚本的环境(模块相关命令将在其中工作),但是当脚本退出时,该环境就消失了。解决方案可能是在模块文件(man modulefile或https://linux.die.net/man/4/modulefile)中配置您的环境模块,或者根据"模块"文档的建议配置。

或者,您可以将脚本实现为shell函数. Shell函数在当前的Shell环境中执行,所以你的模块仍然会在Shell环境结束时被加载。

如果你运行type module,你可以看到module本身是一个shell函数,这就是为什么它能够修改当前环境。

如果在~/.bashrc文件中附加以下函数并重新启动shell,则可以运行load_modules来执行它。

我认为在这种情况下引用(变量等)是不必要的,但我还是添加了它。

load_modules ()
{
# A list with all the necessary modules
local -a modules=('CDO/1.9.7-gompi-2019a'
'ncview/2.1.7-gompi-2019a')
local mod
echo "Running function"
echo
# Check if modules are loaded. If not, load them
for mod in "${modules[@]}"
do
if module is-loaded "$mod"
then
echo "$mod is already loaded"
else
echo "Loading $mod…"
module load "$mod"
fi
done
echo
echo "Finished running the function"
}

module命令,来自环境模块软件更新当前环境会话。

正如@dan所解释的,当作为./script.sh执行时,您的脚本在脚本执行结束时结束的子shell中运行。因此,当以这种方式运行时,脚本将更新子shell的shell环境,而不是父shell。

如果您在当前shell会话中使用source script.sh源脚本,您将在当前shell(而不是子shell会话)中执行module load命令,因此您将以更新的当前shell环境结束。

最新更新