6.7 Paths

You might have wondered why we write ./test.sh instead of just test.sh for executing the script. The reason is simple: BASH wouldn’t have found the file otherwise!

$ ./test.sh
Hello world
$ test.sh
Error in running command bash

But why?

When calling an executable such as test.sh, BASH looks for it in a list of directories that are stored in a variable called $PATH. This variable typically contains the following directories (separated by a colon :):

$ echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin:/snap/bin:/usr/lib/rstudio/resources/app/bin/quarto/bin:/usr/lib/rstudio/resources/app/bin/postback

BASH only looks for the executable in those directories and does not consider our current directory. Since test.sh is not located in one of these directories, BASH can not find it. We need to tell BASH the unique location of the file inside the filesystem - the so-called path. A path is how we refer to files and directories: it gives us the location of a file or a directory in the Linux directory system.

As a user, we need to know the path if we want to access a certain file or directory. We can specify the path as absolute or relative:

  1. Absolute path: The absolute path specifies the location of a file from the root directory. Everything on a Linux system is located under the root directory. The root directory is the top-most directory of all other directories, like the trunk of a tree where all branches originate from. It is represented with a /. After the /, the absolute path lists all directories that need to be entered in order to get to the file, separated by /. We can get the absolute path with the command pwd:
$ pwd
/data/TeachingMaterial/bash_lecture/tmp

We can run our script by pasting this path in front of its name:

$ /data/TeachingMaterial/bash_lecture/tmp/test.sh
Hello world
  1. Relative path: This is the path relative to the current location. For relative paths, we often use the following three symbols:
  • . (a single dot): represents the directory we’re in.
  • .. (a double dot): represents the parent directory (i.e. one level above).
  • ~ (tilde): represents the home directory. This is the default directory that occurs after logging in. Most of our files will be located somewhere in here.

Let’s make this clear with an example. In our current directory, create two new directories.

$ mkdir dir1 dir2

We can change directories using cd:

$ cd dir1
$ touch file1.txt
$ ls
file1.txt

Let’s now go to dir2 (via the parent directory), and copy file1 from dir1 here:

$ cd ../dir2
$ cp ../dir1/file1.txt .
$ ls
file1.txt

Finally, move file1 from dir1 to the parent directory:

$ mv ../dir1/file1.txt ../movedFile.txt
$ ls ../dir1

We have only used relative paths in this example. They are very handy, since they make code much more readable: suppose we had to replace each relative path above with its absolute path, it would have been a mess!

In summary: The absolute path always starts with the root / directory and is independent of our current location. The relative path depends on our current location.