
Linux Systems and Unix systems are composed of multiple files and directories. So it is likely that at some point you will need to verify if specific files or directories exist. In this blog post, we will look at the traditional method of checking by hand and using the test command from within shell scripts. The shell script section will break down flags, and syntax options, in addition to some examples.
Traditional Method
If you’re working from a shell the ls command or stat command are the most common commands to check if a file or directory exists. Below are some examples of these commands.
Using ls
ls path
Using stat
stat path
Advanced File Checking In Shell Scripts
The methods we explored won’t cut it for scripting, below we will explore some better methods suited for scripts. Instead, for scripts we will use part of GNU coreutils called the test command.
The flags used will change what is being tested, below are the flags I think will be most useful:
-d FILE
FILE exists and is a directory
-e FILE
FILE exists
-f FILE
FILE exists and is a regular file
-h FILE
FILE exists and is a symbolic link (same as -L)
-N FILE
FILE exists and has been modified since it was last read
-p FILE
FILE exists and is a named pipe
-r FILE
FILE exists and the user has read access
-s FILE
FILE exists and has a size greater than zero
-S FILE
FILE exists and is a socket
-u FILE
FILE exists and its set-user-ID bit is set
-w FILE
FILE exists and the user has write access
-x FILE
FILE exists and the user has execute (or search) access
These are some examples taken from the man page for the test command which you can view by typing man test.
man test
POSIX Compliant
There are two different options for use of the test command that are POSIX compliant. By sticking to the POSIX standard, meaning you can use the test command on any system that uses POSIX shells not just on Linux but Unix-like operating systems as well.
Using the test command directly:
test -f path
In this command, the -f flag stands for regular files. Also, replace the path with the full file path including the file name.
Another method is to put the flag and path inside one line of square brackets as shown in the following command.
[ -f "path" ]
Double Square Brackets
In certain scenarios where you are using Bash shell, Zsh, Ksh, and other compatible shells you can use the following syntax.
[[ -f path ]]
Using this syntax with a compatible shell will provide better error handling and no need to quote
Shell Script Examples
Here are three examples of scripts (multiple commands strung together) all using an if statement. One script using the test command, one script file with double square brackets, and one script incorporating an Associative Array.
Using the test command:
# Prompt the user to enter the file path
read -p "Enter the file path: " file_path
if test -f "$file_path"; then
echo "File exists: $file_path"
# Add your actions here, such as reading the file or processing its contents
else
echo "File does not exist: $file_path"
# Add error handling or other actions for when the file does not exist
fi
Bash Script:
#!/bin/bash
# Prompt the user to enter the file path
read -p "Enter the file path: " file_path
if [[ -f $file_path ]]; then
echo "File exists: $file_path"
# Add your actions here, such as reading the file or processing its contents
else
echo "File does not exist: $file_path"
# Add error handling or other actions for when the file does not exist
fi
This next example will loop through multiple files at once using an array.
#!/bin/bash
# Prompt the user to enter a list of file paths separated by spaces
read -p "Enter a list of file paths separated by spaces: " file_paths
# Split the input into an array using space as the delimiter
IFS=' ' read -r -a file_paths_array <<< "$file_paths"
# Loop through each file path in the array
for file_path in "${file_paths_array[@]}"
do
if [ -f "$file_path" ]; then
echo "File exists: $file_path"
# Add your actions here for when the file exists
else
echo "File does not exist: $file_path"
# Add error handling or other actions for when the file does not exist
fi
done
Bonus: Would you like to do the exact opposite of the test use an exclamation mark before what you want the inverse of.
Conclusion
Though traditional methods like ls and stat are perfectly suited for checking if a file or directory exists manually, the same can’t be said when scripting this is where the test command comes into place. With the test command, we explore POSIX-compliant and noncompliant options. From there wrap up with some code examples.

Embracing a lifelong passion for technology since childhood, CJ delved into the intricate workings of systems, captivated by the desire to understand the unknown. This innate curiosity led to his discovery of Linux, a revelation that resonated deeply. With more than 7 years of on the job experience, he’s honed his technical skills as a Geek and Senior Linux Systems Administrator.
Leave a Reply