通常包含脚本的方式是"source"

eg:

main.sh:

#!/bin/bash

source incl.sh

echo "The main script"

incl.sh:

echo "The included script"

执行“。/main.sh”的结果是:

The included script
The main script

... 现在,如果您试图从另一个位置执行该shell脚本,它将无法找到包含,除非它在您的路径中。

确保脚本能够找到包含脚本的好方法是什么,特别是在脚本需要可移植的情况下?


当前回答

替代:

scriptPath=$(dirname $0)

is:

scriptPath=${0%/*}

. .优点是不依赖于dirname,这不是一个内置命令(在模拟器中并不总是可用)。

其他回答

我建议您创建一个setenv脚本,其唯一目的是为整个系统中的各种组件提供位置。

然后,所有其他脚本将源此脚本,以便使用setenv脚本的所有脚本的所有位置都是通用的。

这在运行cronjobs时非常有用。当运行cron时,你会得到一个最小的环境,但是如果你让所有的cron脚本首先包含setenv脚本,那么你就能够控制和同步你想要cronjob在其中执行的环境。

我们在构建猴子上使用了这样的技术,用于跨大约2000 kSLOC的项目的持续集成。

当然,每个人都有自己的,但我认为下面的块是相当扎实的。我相信这涉及到查找目录的“最佳”方式,以及调用另一个bash脚本的“最佳”方式:

scriptdir=`dirname "$BASH_SOURCE"`
source $scriptdir/incl.sh

echo "The main script"

因此,这可能是包含其他脚本的“最佳”方式。这是基于另一个“最佳”答案,它告诉bash脚本它存储在哪里

替代:

scriptPath=$(dirname $0)

is:

scriptPath=${0%/*}

. .优点是不依赖于dirname,这不是一个内置命令(在模拟器中并不总是可用)。

我在这里看到的大多数答案似乎都把事情复杂化了。这个方法对我来说一直很有效:

FULLPATH=$(readlink -f $0)
INCPATH=${FULLPATH%/*}

INCPATH将保存脚本的完整路径,不包括脚本文件名,无论脚本是如何调用的(通过$ path,相对或绝对)。

在此之后,只需要在同一目录中包含文件即可:

. $INCPATH/file_to_include.sh

参考:TecPorto /位置独立包括

即使脚本是原始的,这也是有效的:

source "$( dirname "${BASH_SOURCE[0]}" )/incl.sh"