Double asterisk brings double expedience to pathname expansion
If you are a Linux command-line user, most likely, you are familiar with the use of the single asterisk ('*') in pathname expansion (aka globbing). How the asterisk behaves is standardized across all shells (bash
, zsh
, tcsh
, etc). For example, the ls *
command lists the files and the immediate sub-directories of the current directory.
$ ls *
The single asterisk, however, is not recursive: it does not traverse beyond the target directory. You may use the find
command to generate a recursive listing of pathnames. A simpler solution is the use of the double asterisk ('**').
Unlike the single asterisk, the double asterisk is not standardized. Different shells introduced the feature at different times with slightly different behavior. This post focuses on the use of '**' for the bash
shell.
The double asterisk feature for bash
first appears with bash4
. To find out which bash
version you are running, execute the following command:
$ bash --version
GNU bash, version 4.2.37(1)-release (x86_64-pc-linux-gnu)
...
Before you use '**', you must first enable the globstar
shell option:
$ shopt -s globstar
With globstar
enabled, you may use '**' for pathname expansion.
$ ls **/abc.txt
In the above example, the ls
command returns any occurrence of the file abc.txt
in the current directory and sub-directories.
Notes:
By default, the double asterisk does not expand to include a hidden file. For example, the following command will not find
.htaccess
because it is a hidden file.
$ ls **/.htaccessTo allow hidden files in '**' output, enable the
dotglob
shell option:
$ shopt -s dotglobWhen you do a pathname expansion using '*' or '**', you run the risk that a returned filename is the same as a command-line flag, e.g.,
-r
. To mitigate that risk, precede '**' with '--' as below. The double dash marks the spot where command-line flags end, and positional parameters begin.
$ ls -- **Under
bash
, '**' expands to follow symbolic links. This behavior, however, is shell-specific. Forzsh
, expanding the double asterisk does not follow a symbolic link.
The double dash is a useful tool to add to your everyday command-line usage.