The test command can be used to compare either numbers or strings, and to check file properties via numerous tests.
test ex_expression
Each test returns either a 0 (True) or 1 (False).
The test command supports an abbreviated notation where the expression to be evaluated is enclosed in double brackets (with spaces after and before the brackets), e.g., [[ ex_expression ]]. Often, this shorthand notation is used in scripts.
An expression can be negated by placing the logical NOT operator before it (!), e.g., test ! ex_expression.
The logical AND (&&) and logical OR (||) operators can be used to join multiple expressions, e.g., test ex_expression_1 && test ex_expression_2. The logical AND operator has precedence over the logical OR operator.
The logical operators are supported within the [[ ex_expression ]] syntax, as well:
[[ ! ex_expression ]][[ ex_expression_1 && ex_expression_2 ]][[ ex_expression_1 || ex_expression_2 ]]
Note: If you are not familiar with the GNU/Linux command line interface, or you intend to use a script obtained from this site, review the Conventions page before proceeding.
Internal and External test Commands
On your GNU/Linux system, there will likely be both an internal and external version of the test command. Usually, the external command is the version your shell will end up using when you employ test.
For example, on Debian, the version of test that is used (unless otherwise specified) is located at /usr/bin/test. To use the internal version of test, you can use the builtin command (e.g., builtin test). This tells your shell that you intend to use the internal version of the test command.
Examples
Supplying a variable name to test as an argument makes the command check whether or not the variable is non-empty, i.e., whether or not the variable contains a value.
$ test "${PATH}" && echo 'Not empty!' || echo 'Empty!'
Not empty!
Above, we test whether or not the PATH variable has a value. If it does have a value, the test "${PATH}" command will return a 0, which will cause the execution of the echo 'Not empty!' command via the use of the logical AND operator (i.e., &&). This tells us that the PATH variable is not empty. If PATH was empty, the echo 'Empty!' command would have been executed instead, via the use of the logical OR operator (i.e., ||).
The value that a test command returns can be verified by displaying the contents of the ? variable:
$ test "${PATH}" ; echo "${?}"
0
The next example tests whether the variable x contains a value greater than 20:
$ x='15'
$ test "${x}" -gt 20 ; echo "${?}"
1
Since 15 is less than 20, the test "${x}" -gt 20 command returns a 1 (False).
The following example checks whether the value in the variable x sorts after the character d based on lexicographic ordering:
$ x='a'
$ builtin test "${x}" \> 'd' ; echo "${?}"
1
Since a comes before d in a lexicographic sort, test "${x}" \> 'd' returns 1 (False).
The final example checks whether a .bashrc file in the current user's home directory exists and is readable:
$ test -r "${HOME}/.bashrc" ; echo "${?}"
0
${HOME}/.bashrc exists and is readable, so test -r "${HOME}/.bashrc" returns 0 (True).
Tests
The test command supports:
- Arithmetic tests
- File tests
- Shell tests
- String tests
Arithmetic Tests
ex_integer_1 -eq ex_integer_2ex_integer_1is equal toex_integer_2.ex_integer_1 -ge ex_integer_2ex_integer_1is greater than or equal toex_integer_2.ex_integer_1 -gt ex_integer_2ex_integer_1is greater thanex_integer_2.ex_integer_1 -le ex_integer_2ex_integer_1is less than or equal toex_integer_2.ex_integer_1 -lt ex_integer_2ex_integer_1is less thanex_integer_2.ex_integer_1 -ne ex_integer_2ex_integer_1is not equal toex_integer_2.
In regard to the order of operations, BEDMAS is observed:
- Brackets/Braces/Parentheses
- Exponents
- Division
- Multiplication
- Addition
- Subtraction
File Tests
The following file tests use unary operators, i.e., they require one file (argument) to test.
-a ex_file- True if
ex_fileexists. Equivalent to-e. This test is for use with the internal version of thetestcommand. -b ex_file- True if
ex_fileexists and is a block special file. -c ex_file- True if
ex_fileexists and is a character special file. -d ex_file- True if
ex_fileexists and is a directory. -e ex_file- True if
ex_fileexists. Equivalent to-a. -f ex_file- True if
ex_fileexists and is a regular file. -g ex_file- True if
ex_fileexists and its setgid bit is set. -G ex_file- True if
ex_fileexists and is owned by the effective group ID (EGID). -h ex_file- True if
ex_fileexists and is a symbolic link. Equivalent to-L. -k ex_file- True if
ex_fileexists and its sticky bit is set. -L ex_file- True if
ex_fileexists and is a symbolic link. Equivalent to-h. -N ex_file- True if
ex_fileexists and has been modified since it was last read. -O ex_file- True if
ex_fileexists and is owned by the effective user ID (EUID). -p ex_file- True if
ex_fileexists and is a named pipe (FIFO, First In First Out). -r ex_file- True if
ex_fileexists and is readable. -s ex_file- True if
ex_fileexists and its size is greater than zero. -S ex_file- True if
ex_fileexists and is a socket. -t ex_file_descriptor- True if
ex_file_descriptoris open and refers to a terminal. -u ex_file- True if
ex_fileexists and its setuid bit is set. -w ex_file- True if
ex_fileexists and is writable. -x ex_file- True if
ex_fileexists and is executable.
These file tests use binary operators, i.e., they require two files (arguments) to test.
ex_file_1 -ef ex_file_2- True if
ex_file_1andex_file_2refer to the same device and inode numbers (hard link test). ex_file_1 -nt ex_file_2- True if
ex_file_1is newer (according to modification date) thanex_file_2, or ifex_file_1exists andex_file_2does not. ex_file_1 -ot ex_file_2- True if
ex_file_1is older thanex_file_2(according to modification date), or ifex_file_2exists andex_file_1does not.
Shell Tests
The following tests are for use with the internal version of the test command.
-o ex_option_name- True if the shell option
ex_option_nameis enabled. -R ex_variable- True if the shell variable
ex_variableis set and is a name reference. -v ex_variable- True if the shell variable
ex_variableis set (i.e., has been assigned a value).
In contrast to the external version of test, when using the internal version, do not include the $ when referencing variables (e.g., builtin test -v 'PATH' ; echo "${?}").
String Tests
ex_string_1 == ex_string_2- True if
ex_string_1andex_string_2are equal, e.g.,[[ 'a' == 'a' ]]. ex_string_1 != ex_string_2- True if
ex_string_1andex_string_2are not equal. ex_string_1 < ex_string_2- True if
ex_string_1sorts beforeex_string_2lexicographically, e.g.,[[ 'a' < 'b' ]]. This test is for use with the internal version of thetestcommand. ex_string_1 > ex_string_2- True if
ex_string_1sorts afterex_string_2lexicographically. This test is for use with the internal version of thetestcommand. -n ex_string- True if the length of
ex_stringis non-zero. -z ex_string- True if the length of
ex_stringis zero, e.g.,[[ -z 'GNU/Linux' ]].
Documentation
For more information on the test command, refer to its man page, either from the command line, or online.