How to Discover, From Inside a Bash Script, the Path the Script Is In

When you develop complex Bash scripts and start putting various scripts into a folder, where one script interacts with another by, for example, starting it, it quickly becomes necessary to ensure we know the path the script was started from, so we can start the other scripts with a fully qualified pathname. This is important because the first script may have been started from outside the script’s directory. We could have also done so by using a relative path, so even – somehow – reading the command that started the current script will not work.

In this tutorial, you will learn:

  • What the pwd command is, and what it does
  • How to discover from inside a Bash script what path that same script is in

How to Discover, From Inside a Bash Script, the Path the Script Is In

How to Discover, From Inside a Bash Script, the Path the Script Is In

Software requirements and conventions used

Software Requirements and Linux Command Line Conventions
Category Requirements, Conventions or Software Version Used
System Linux Distribution-independent
Software Bash command line, Linux based system
Other Any utility which is not included in the Bash shell by default can be installed using sudo apt-get install utility-name (or yum install for RedHat based systems)
Conventions # – requires linux-commands to be executed with root privileges either directly as a root user or by use of sudo command
$ – requires linux-commands to be executed as a regular non-privileged user

What is pwd?

The pwd command in Linux returns the Path Working Directory when executed. Whatever path we currently find ourselves in, and have previously navigated to (or have been placed into by our Operating System, like, for example, when we open a command prompt/terminal), will be what is return when we execute pwd.

$ cd /
$ pwd
/
$ cd /home
$ pwd
/home


Here, we changed to the root directory (/) and executed pwd. Our current path was the root directory, so / is returned. We then changed to the /home directory and executed pwd again. The path returned is now /home.

Inside a bash script, the pwd command will work in the same way. It is also noteworthy to know that from within a Bash script (and on the command line outside of a Bash script also), we can use the special operating system variable ${PWD} which will automatically be kept up-to-date by the operating system to contain our current path. This saves us from having to do something like calling a subshell, i.e. MYPATH="$(pwd)" is not needed, we can simply invoke the ${PWD} variable.

So we can use pwd, right?

Not exactly. Picture the following situation:

$ touch 'mypath.sh'
$ echo '#!/bin/bash' >> mypath.sh
$ echo 'echo ${PWD}' >> mypath.sh
$ chmod +x mypath.sh 

Here we defined a script named mypath.sh and made it executable. Next, we jump up one directory from our home directory, and execute our script:

$ pwd 
/home/roel
$ cd ..
$ ./roel/mypath.sh 
/home

Whereas the pwd command inside our mypath.sh script is working correctly, there is a problem here: pwd has returned the path we currently find ourselves in, namely /home whereas the script is actually stored in the /home/roel directory!

Remember the title of the article; we are looking for the path the script is stored in! So how can we find this?

The method!

Whereas there is no special variable in Bash to cover the path the script is stored in, there is a simple method to obtain it.

$ cd -
/home/roel
$ touch 'mypath2.sh'
$ echo '#!/bin/bash' >> mypath2.sh
$ echo 'MYPATH="$(cd "$(dirname \$0)" && pwd)"' >> mypath2.sh 
$ echo 'echo "${MYPATH}"' >> mypath2.sh
$ chmod +x mypath2.sh 


Here we defined a secondary script named mypath2.sh. Within it we place a little special code ($(cd "$(dirname \$0)"; && pwd)) which will find the path the script is in (by changing into it’s directory, based on the \$0 variable (which is the script name in the way we called it, i.e. using a potential relative or fully qualified path) and requesting the dirname for it (by reference, and note it can still be a relative path if the script was started using a relative path), and then changing into it (via the cd) and subsequently requesting the pwd (Path Working Directory) for the same, giving us the fully qualified path.

Let’s see if this works more correctly than only using pwd:

$ cd ..
$ pwd
/home
$ ./home/mypath2.sh 
/home/roel

The script works correctly, and even though mypath2.sh was relatively called, from outside the directory of where the script resides, the output returned correctly reflected the information sought; the path where the script exists. We stored the same in the ${MYPATH} variable, and this variable could now be used to for example call ${MYPATH}/someotherscript.sh where someotherscript.sh is another script in the same directory as mypath2.sh

Conclusion

In this article, we first look at pwd and whether it would fulfill the problem at hand, finding out the path our script resides in, at all times. Whereas pwd may work if we have not changed directories, it will not work correctly if we are outside of the path the script is in. We then introduced a small piece of code (MYPATH="$(cd "$(dirname \$0)" && pwd)" which will always return the directory our script is in correctly.

A small piece of code, but a big solution for our Bash script coding issue! Enjoy!



Comments and Discussions
Linux Forum