如何在unix中设置“module”命令以将软件包添加到$ PATH?

时间:2014-02-07 14:53:06

标签: bash shell module

我使用了大量的计算集群,这些集群通常使用模块系统来提供软件包。基本上,您使用module load sample_software之类的模块命令,并将sample_software路径添加到$PATH。在群集上,可以在交互式使用和作业提交使用期间调用此命令。

我有一个带有PBS / Torque排队系统的linux盒子,这样我就可以将沙盒软件用于以后在群集上使用。我需要一个非常相似的模块系统。我开始在我的`/etc/profile.d/目录中创建一个名为modules.sh的文件,如下所示:

module()
{
if [ $2 == "softwareX" ]; then
    PATH=$PATH:/home/me/dir/softwareX
    export PATH
fi
}

然后我将以下行放在我的.bash_profile脚本中:

source /etc/profile.d/modules.sh

现在,这适用于以下用途:1)如果我提交作业并且我的作业脚本使用module load softwareX,没问题,则作业运行完美。 2)如果我在命令行上以交互方式工作并输入module load softwareX,那么softwareX的路径将加载到我的$PATH中,一切正常。

但是,这不适用于以下情况:如果我创建一个包含行module load softwareX的简单bash脚本,则在执行bash脚本时会出现错误。例如,这是我的bash脚本:

#!/usr/bin/env bash
echo $PATH
module load softwareX
echo $PATH

执行此操作时,我收到错误script.sh: line 3L module: command not found

... $PATH永远不会改变。有谁知道如何在这三种情况下解决这个问题?谢谢你的帮助!

2 个答案:

答案 0 :(得分:1)

创建子shell时,可以创建新环境。当您退回到现有的shell时,会丢失该环境。

我怀疑这是你的模块函数调用正在发生的事情。如果您将echo $PATH添加到模块函数的底部,您是否看到PATH在函数内部被更改,但是当您离开函数时会再次更改?如果是这样,问题是子shell问题:

你应该做的是让你的模块功能打印出新的路径,然后这样做:

PATH=$(module load softwareX)

答案 1 :(得分:1)

bash脚本不会调用您的启动文件。你必须明确地这样做。

请参阅http://www.gnu.org/software/bash/manual/bashref.html#Bash-Startup-Files

  

非交互式调用

     
    

当以非交互方式启动Bash时,为了运行shell脚本,例如,它在环境中查找变量BASH_ENV,如果它出现在那里则展开它的值,并使用扩展值作为文件的名称来阅读和执行。 Bash的行为就像执行了以下命令一样:

   if [ -n "$BASH_ENV" ]; then . "$BASH_ENV"; fi
         

但PATH变量的值不用于搜索文件名。

         

如上所述,如果使用--login选项调用非交互式shell,Bash会尝试从登录shell启动文件中读取和执行命令。