Je voudrais écrire quelque chose comme ceci:
$ ls **.py
afin d'obtenir tous les noms de fichiers .py, parcourant récursivement une hiérarchie de répertoires.
Même s'il y a des fichiers .py à trouver, le Shell (bash) donne cette sortie:
ls: cannot access **.py: No such file or directory
Une façon de faire ce que je veux?
EDIT: Je voudrais préciser que je ne suis pas intéressé par le cas spécifique de ls
, mais la question porte sur la syntaxe glob.
Pour faire des globs récursifs dans bash, vous avez besoin de la fonctionnalité globstar
de bash version 4 ou supérieure.
Depuis la page de manuel bash:
globstar
If set, the pattern ** used in a pathname expansion context will
match all files and zero or more directories and subdirectories.
If the pattern is followed by a /, only directories and
subdirectories match.
Pour votre exemple de modèle:
shopt -s globstar
ls **/*.py
find . -name '*.py'
** ne fait rien de plus qu'un seul *, les deux fonctionnent dans le répertoire courant
Depuis Bash 4 (incluant également zsh) ne nouvelle option de globbing (globstar
) a été ajoutée pour traiter le motif **
différemment lorsqu'il est défini.
Il correspond au modèle générique et renvoie les noms de fichiers et de répertoires qui correspondent, puis en remplaçant le modèle générique dans la commande par les éléments correspondants.
Normalement, lorsque vous utilisez **
, cela fonctionne comme *
, mais c'est récursif tous les répertoires récursivement (comme une boucle).
Pour voir s'il est activé, vérifiez-le par shopt globstar
(dans les scripts, utilisez shopt -q globstar
).
L'exemple **.py
ne fonctionnerait que pour le répertoire courant, car il ne retourne pas la liste des répertoires qui peuvent être récurrents, c'est pourquoi vous devez utiliser plusieurs caractères génériques au niveau du répertoire **/*.py
, donc ça peut aller plus loin.
Veuillez trouver sur SO quelques tests de syntaxe que j'ai fait pour trouver tous les fichiers récursivement.