7

I'm not sure I am using ZSH's globbing correctly, but I thought ls *(/) would just list the dirctories under pwd, but it doesn't, it recursively lists all files under every directory under pwd (I got the statement from this list of useful zsh tips)

What would be right globbing for exclusively listing the directories under my current path?

Michael Mrozek
  • 93,103
  • 40
  • 240
  • 233

3 Answers3

15

I suspect the problem is not the zsh globbing, but the ls default behavior, that when given a directory argument list the content of directory.

I suggest to try

ls -d -- <your-glob-here>

The best way to test your globs is with

printf '%s\n' <glob>

or

print -rC1 -- <glob>
Kusalananda
  • 333,661
enzotib
  • 51,661
2

Yet another way to achieve it is

 print *(/)

or

 echo *(/)

Update1

A bit more correct version (as noted by @Stéphane Chazelas) would be

print -rl -- *(/) 

or

echo -E - *(/)

to take care about spaces (-l), escape sequences (-r/-E) and leading hyphens (--/-) inside filenames.

Update2

Yet even more correct version is print -rN which additionally takes care of linebreaks inside filenames (linux allows them, windows doesn't) by separating the results with nulls, for example:

print -rN -- **/*(/) |xargs -0 -n10 chmod g+s

which recursively sets setguid bit - selectively addressing directories, as opposed to chmod -R g+s.

Update3

For huge trees this only processes a part of files (due to the limit on command line length) and silently leave the rest as is. The following commands can handle this situation:

find . -type d -print0 |xargs -0 -n10 chmod g+s
  • Should be print -rl -- *(/) or echo -E - *(/). Without -r/-E, print/echo expand escape sequences. The -l option to print prints one argument per line. See also -c (optionally with -a) to print in columns – Stéphane Chazelas Aug 13 '15 at 10:41
  • @Stéphane Chazelas Totally agree. I only use those without options if I created the files myself. That might not be secure enough, though. – Antony Hatchkins Aug 13 '15 at 12:19
-1

To list all directories in the current directory type

ls -d -- *(/)
ls -d *(/)

Otherwise use

ls -d */**(/)

to list all directories recursivley.

abu_bua
  • 249