Ignore "no matches" from zsh when using brace expansion with glob *.{a,b,}test
Solution 1
It may be best to do this with find
:
find ./foldername -maxdepth 1 -name '*.atest' -o -name '*.btest' -o -name '*.test'
Solution 2
In
ls -d ./foldername/*.{a,b,}test
{a,b,...}
is not a glob operator, that's brace expansion, that's first expanded to:
ls -d ./foldername/*.atest ./foldername/*.btest ./foldername/*.test
And each glob expanded individually, and if any glob doesn't match, the command is cancelled as you'd expect in zsh
(or fish
; in bash
, you need the failglob
option to get a similar behaviour).
Here, you'd want to use a single glob that matches all those files, and only cancel the command if that one glob didn't match any file:
ls -d ./foldername/*.(a|b|)test
You don't want to use nullglob
, as if none of the globs matched, it would run ls
without arguments, so list the current directory. cshnullglob
is better in that regard as it removes non-matching globs but still cancels the command if all the globs fail to match.
You wouldn't want to use nonomatch
, as that would give you the broken behaviour of bash
which would be a shame.
For a glob alternative that works in both zsh
and bash
, you could use the ksh globs (set -o kshglob
in zsh
and shopt -s extglob
in bash
).
Then, you'd do:
ls -d ./foldername/*.@(a|b|)test
or:
ls -d ./foldername/*.?([ab])test
Add the failglob
option in bash
to avoid the glob being passed literally to ls
when it doesn't match.
See Why is nullglob not default? for more information.
Related videos on Youtube
Jonathan Hodgson
Updated on September 18, 2022Comments
-
Jonathan Hodgson over 1 year
I would like to list all of the files in a folder called
foldername
that have the extensiontest
,atest
orbtest
.My immediate thought was to run
ls ./foldername/*.{a,b,}test
This works fine unless there is nothing with the extension
atest
, in which case I get the errorzsh: no matches found: ./foldername/*.atest
.Is there any way I can simply ignore this error and print the files that do exist?
I need this to work in both zsh and Bash.
-
Pankaj Goyal over 6 yearsRedirect standard error to
/dev/null
?
-
-
Jeff Schaller over 6 yearsI'm not sure why it's a requirement of the OP, but is there an extglob that works for this in both bash and zsh? I had to use
?(...)
or+(...)
for bash. -
Jeff Schaller over 6 yearsperhaps with a
-maxdepth 1
, to closer emulate thels
behavior -
Stéphane Chazelas over 6 years@JeffSchaller, note that
-maxdepth
is a GNU extension. Note 3 other differences with globs:find
would include hidden files, not sort the list and fail to match file names that contain bytes not forming valid characters (like a$'St\xe9phane.atest'
in a UTF-8 locale) -
Stéphane Chazelas over 6 years@JeffSchaller, see edit
-
Stéphane Chazelas about 2 yearsNo, it wouldn't work in zsh where this question is about as you'd only be redirecting
ls
' stderr, andls
is not even run here in zsh if any of those globs fail.