Bash Conditional Expressions
Conditional Expressions are signals - also called primaries - that bash uses as a means of performing tests, using the info you provide.
Lets say you are wanting to copy over a file from one location to another, but don’t need to do this if the file already exists in the final location. This is one way to test for that!
if [[ ! -e /etc/foo ]]; then
echo "Looks like /etc/foo doesn't exist"
fi
Breakdown
[[ ]]
So, the double brackets here are necessary for#!/bin/bash
, of which, to be honest, using the double brackets as the standard setup seems to be what makes the most sense.!
The exclamation point is how you negate expressions through a lot of bash in general. So, here, its testing if/etc/foo
exists.-e
True if File Exists. Its a very broad testing flag.After the brackets are closed, you use
;
to tell bash that your expression line is finished.Then, you do whatever you need to do.
fi
then, thefi
is what tells bash thatif
is finished.
Conditional Expression Primaries
The following test flags go with:
if [[ -e /bin/bash ]]; then ...
<some code>
elif [[ ! -e /bin/dash ]]; then
<some code>
fi
Use [[ ]]
with double ==
and use [ ]
with =
The first line, -e /bin/bash
is the positive side of the -e FILE
test.
There are a LOT of ways to test things, using either if-then-else
, case
or while
loops.
Flag |
Explainer |
---|---|
-a FILE |
True if file exists |
-b FILE |
True if file exists and is a block special file |
-c FILE |
True if file exists and is a character special file |
-d FILE |
True if file exists and is a directory |
-e FILE |
True if file exists |
-f FILE |
True if file exists and is a regular file |
-g FILE |
True if file exists and its set-group-id bit is set |
-G FILE |
True if file exists and is owned by the effective group id |
-h FILE |
True if file exists and is a symbolic link |
-k FILE |
True if file exists and its |
-L FILE |
True if file exists and is a symbolic link |
-n STRING |
True if the length of string is NON-zero |
-N FILE |
True if file exists and has been modified since it was last read |
-o OPTNAME |
True if the shell option |
-O FILE |
True if file exists and is owned by the effective user id |
-p FILE |
True if file exists and is a named pipe (FIFO) |
-r FILE |
True if file exists and is readable |
-R |
True if the shell variable |
-s FILE |
True if file exists and has a size greater than zero |
-S FILE |
True if file exists and is a socket |
-t FD |
True if file descriptor |
-u FILE |
True if file exists and its set-user-id bit is set |
-v |
True if the shell variable |
-w FILE |
True if file exists and is writable |
-x FILE |
True if file exists and is executable |
-z FILE or STRING |
True if STRING or FILE is null |
Compare Flags |
Explainer |
---|---|
file1 -nt file2 |
True if file1 exists and is newer than file2 |
file1 -ot file2 |
True if file1 exists and is older than file2 |
file1 -ef file2 |
True if file1 and file2 exist and refer to the same file |
Compare Strings |
Explainer |
---|---|
s1 == s2 |
True if strings |
s1 = s2 |
True if strings |
s1 != s2 |
True if strings |
s1 < s2 |
True if string |
s1 > s2 |
True if string |
Note
Bash-based conditionals - #!/bin/bash
- usually prefer you to use double-brackets, [[ ]]
. When you use [[ ]]
, you have to use double-equals - ==
. You can still use the single-brackets with single-equals =
.
But when using sh
- #!/bin/sh
- it prefers single-brackets - [ ]
. When you use the single-brackets, you use single-equals - =
.
Compare Strings |
Explainer |
---|---|
n1 -eq n2 |
True if the integers |
n1 -ne n2 |
True if the integers |
n1 -gt n2 |
True if the integer |
n1 -ge n2 |
True if the integer |
n1 -lt n2 |
True if the integer |
n1 -le n2 |
True if the integer |
Note
See man test
for more explanations.