美文网首页Shell语言用例
bash脚本里如何得到脚本文件所在路径

bash脚本里如何得到脚本文件所在路径

作者: CodingCode | 来源:发表于2018-11-21 11:02 被阅读0次

bash脚本里如何得到脚本文件所在路径

应用背景

我们在脚本里面会经常调用外部程序,如何指定外部程序路径:

  1. 绝对路径写死;缺点是不方便移植,比如更改安装路径等。
  2. 加到PATH搜索目录下面;缺点是PATH路径会被替换,同名程序的存在会导致调用到另一个程序。

而有时,我们希望被调用的外部程序是相对当前脚本文件的,例如和脚本文件在同一目录下面,或者临近相对的子目录等等;

|-- ROOT
|-- mains.h
|   |-- scripts
|   |   |-- sub1.sh
|   |   |-- sub2.sh
|   |-- tools
|   |   |-- tool1
|   |   |-- tool2

例如main.sh是主脚本,它需要调用scripts/sub.sh,tools/tool1,和tools/tool2,此时如果把所有的路径(ROOT:ROOT/scripts:ROOT/tools)都加到PATH里面显得有点重,那么我们只想把ROOT加到PATH里面,然后让main.sh来去搜索sub.sh和tool。

思路

这种场景下,我们就需要在main.sh里面得到脚本自己所在的路径(例如,SCRIPTDIR),然后按如下方式调用子程序:

${SCRIPTDIR}/scripts/sub.sh
${SCRIPTDIR}/tools/tool

方法

如何得到main.sh脚本所在的路径呢,下述命令可以得到:

SCRIPTDIR=$(cd $(dirname "${BASH_SOURCE[0]}") >/dev/null && pwd)
  1. 例子1:

假设脚本main.sh所在的路径是/home/<username>/main.sh

$ cat main.sh 
#!/bin/bash

SCRIPTDIR=$(cd $(dirname "${BASH_SOURCE[0]}") >/dev/null && pwd)

echo ${SCRIPTDIR}
$ pwd
/home/<username>/tmp
$ ./main.sh 
/home/<username>/tmp
$ cd ..
$ pwd
/home/<username>
$ ./tmp/main.sh 
/home/<username>/tmp

我们可以看到,不管当前的路径在哪里,调用起main.sh的时候它都能打印出脚本所在的路径。

再看一个例子。

  1. 例子2:
$ pwd
/home/<username>
$ ln -snf tmp/main.sh main.sh
$ ./main.sh 
/home/<username>

我们创建一个符号链接,main.sh链接到tmp/main.sh,然后我们运行外层的main.sh这个符号链接,结果我们看到:打印出来的是符号链接文件所在的路径,而不是脚本所在的路径。

这是合理的设计行为,因为我们调用的是外面的main.sh这个链接文件,但是对我们的需求就有问题了,因为在main.sh这个真正脚本里面就没法调用到子命令sub.sh和tool了,无法根据外面符号链接的路径来找scripts和tools路径了。

解决办法呢,我们要不停的解决符号链接行为,直到遇到真正的脚本为止。
重新改写tmp/main.sh脚本如下:

#!/bin/bash

#SCRIPTDIR=$(cd $(dirname "${BASH_SOURCE[0]}") >/dev/null && pwd)
SOURCE="${BASH_SOURCE[0]}"
while [ -h "${SOURCE}" ]; do
  SCRIPTDIR="$(cd -P "$(dirname "${SOURCE}")" >/dev/null && pwd)"
  SOURCE="$(readlink "${SOURCE}")"
  [[ ${SOURCE} != /* ]] && SOURCE="${SCRIPTDIR}/${SOURCE}"
done
SCRIPTDIR="$(cd -P "$(dirname "${SOURCE}")" >/dev/null && pwd)"

echo ${SCRIPTDIR}

再次运行符号链接文件:

$ pwd
/home/<username>
$ ln -snf tmp/main.sh main.sh
$ ./main.sh 
/home/<username>/tmp

这回打印出来的就是真正的脚本文件所在的路径了。

相关文章

  • bash脚本里如何得到脚本文件所在路径

    bash脚本里如何得到脚本文件所在路径 应用背景 我们在脚本里面会经常调用外部程序,如何指定外部程序路径: 绝对路...

  • bash脚本内部变量

    bash脚本内部变量 $BASH bash的程序文件的路径,如/bin/bash $BASH_ENV 该环境变量保...

  • shell脚本

    which bash 查看bash 的安装路径 1创建shell 脚本文件 touch ip.sh 赋予 she...

  • Day5:脚本

    写脚本: 进入文件夹所在路径mkdir ~/localcd ~/local查看路径: pwd 创建文件touch ...

  • 8.2 系统模块下的路径操作

    经常要对大量文件和大量路径进行操作,这就依赖于os模块 OS命令:更改路径,脚本所在路径,现在脚本的路径 os.r...

  • Mac 使用 sequel pro / sequel Ace

    1. 执行SQL脚本 也就是导入已存在的SQL脚本:File —— Import —— 选择.sql 文件所在路径

  • blender下检查文件路径的方法

    在blender的内置脚本里运行下面命令检查文件路径 bpy.data.images.values()[0].fi...

  • shell脚本

    简述 标志:#! 目的告诉系统后面的路径文件以那种脚本来执行,有#! bin/sh(标准)和#!bin/bash ...

  • shell脚本常用语法——获得当前目录

    1 获得shell脚本所在的绝对路径 或者 执行步骤解析: dirname $0: 取得当前执行的脚本文件所在的目...

  • Nodejs全局变量和对象

    __filename 当前正在执行的脚本的文件名,输出绝对路径 __dirname 脚本所在目录 setTimeo...

网友评论

    本文标题:bash脚本里如何得到脚本文件所在路径

    本文链接:https://www.haomeiwen.com/subject/iiyqqqtx.html