From a shell script, how do I check if a directory contains files?
Something similar to this
if [ -e /some/dir/* ]; then echo "huzzah"; fi;
but which works if the directory contains one or several files (the above one only works with exactly 0 or 1 files).
to test a specific target directory
Works well for me this (when dir exist):
With full check:
How about the following:
This way there is no need for generating a complete listing of the contents of the directory. The
read
is both to discard the output and make the expression evaluate to true only when something is read (i.e./some/dir/
is found empty byfind
).So far I haven't seen an answer that uses grep which I think would give a simpler answer (with not too many weird symbols!). Here is how I would check if any files exist in the directory using bourne shell:
this returns the number of files in a directory:
you can fill in the directory path in where directory is written. The first half of the pipe ensures that the first character of output is "-" for each file. egrep then counts the number of line that start with that symbol using regular expressions. now all you have to do is store the number you obtain and compare it using backquotes like:
x is a variable of your choice.
Three best tricks
shopt -s nullglob dotglob; f=your/dir/*; ((${#f}))
This trick is 100%
bash
and invokes (spawns) a sub-shell. The idea is from Bruno De Fraine and improved by teambob's comment.Note: no difference between an empty directory and a non-existing one (and even when the provided path is a file).
There is a similar alternative and more details (and more examples) on the 'official' FAQ for #bash IRC channel:
[ -n "$(ls -A your/dir)" ]
This trick is inspired from nixCraft's article posted in 2007. Add
2>/dev/null
to suppress the output error"No such file or directory"
.See also Andrew Taylor's answer (2008) and gr8can8dian's answer (2011).
or the one-line bashism version:
Note:
ls
returns$?=2
when the directory does not exist. But no difference between a file and an empty directory.[ -n "$(find your/dir -prune -empty)" ]
This last trick is inspired from gravstar's answer where
-maxdepth 0
is replaced by-prune
and improved by phils's comment.a variation using
-type d
:Explanation:
find -prune
is similar thanfind -maxdepth 0
using less charactersfind -empty
prints the empty directories and filesfind -type d
prints directories onlyNote: You could also replace
[ -n "$(find your/dir -prune -empty)" ]
by just the shorten version below:This last code works most of the cases but be aware that malicious paths could express a command...