Comment ouvrir tous les fichiers résultant d'une commande ls?

10

Je voudrais ouvrir tous les fichiers texte qui sont le résultat d'une commande ls à l'aide d'un éditeur de texte. Comment puis-je faire cela?

c0smikdebris
la source

Réponses:

12

Gilles a tout à fait raison , lsest un très mauvais exemple car l'expansion de glob de nom de fichier peut être faite beaucoup plus facilement sur la ligne de commande sans avoir à utiliser lsdu tout! Si vos soi-disant «fichiers texte» ont des extensions de nom de fichier pour les identifier, vous pouvez faire quelque chose comme ceci:

editor-command *.txt

Pour démontrer une technique, utilisons un exemple plus compliqué qui ne pourrait pas être fait avec juste une correspondance de nom de fichier et ouvrez des fichiers basés sur le contenu au lieu de simplement le nom de fichier. Disons que vous vouliez ouvrir tous les fichiers qui contenaient la chaîne "content-type".

En supposant que votre éditeur accepte plusieurs noms de fichiers et les ouvre tous à la fois dans des tampons séparés ou fonctionne séquentiellement, vous pouvez simplement exécuter:

editor-command $(grep -i content-type)

Revenons maintenant à votre question d'origine, disons que vous ne savez pas s'il s'agit de fichiers texte ou non basés sur leurs noms. Vous devrez ensuite utiliser un autre programme pour les identifier, puis les ouvrir en fonction de ces données. Le programme filevous indiquera de quel type de fichier il s'agit, et vous pouvez grep cette liste pour les fichiers texte uniquement, puis ouvrir uniquement les noms de fichiers correspondants comme ceci:

editor-command $(file -ni * | grep 'text/plain' | cut -d: -f1)

La sortie de la chaîne de commandes à l'intérieur de la $()construction sera utilisée comme arguments pour l'éditeur. Je le fais parfois en deux étapes. Disons que je regarde un ensemble de fichiers et que j'obtiens une liste de chaque fichier xml contenant la chaîne "content-type"

find -type f -iname '*xml' | xargs grep -Hi 'content-type' |  cut -d: -f1

... et décide que je veux les ouvrir. J'utilise ensuite le dernier raccourci de l'historique des commandes et je fais ceci:

vim $(!!)

... pour ouvrir tous les résultats de la commande précédente dans vim, mon éditeur préféré.

Si votre éditeur n'accepte qu'un seul fichier à la fois et que vous devez continuer à générer des éditeurs, vous devrez utiliser une variante de la boucle xargsou fordans la réponse de jmtd selon que vous utilisez un éditeur basé sur un terminal qui a besoin de stdio.

Caleb
la source
4
Ne pas analyser la sortie de ls! Usage editor-command *.css, etc.
Gilles 'SO- arrête d'être méchant'
@ Gilles: dûment noté, merci d'avoir souligné l'évidence que nous ne pouvions pas tous voir. @ c0smikdebris Notez que je viens de réécrire complètement ma réponse, y compris un cas pour si vous n'avez pas de moyen évident de faire correspondre les fichiers qui sont du texte par leur seul nom.
Caleb
$ () est ce que je cherchais. j'aurais dû mentionner que j'utilise ls comme exemple ici. +1 aux deux réponses.
c0smikdebris
"mon éditeur préféré". Inutile de préciser, @Caleb, car c'est plus ou moins clair depuis le début de la réponse, ahahah! Le meilleur éditeur de tous les temps!
Enrico Maria De Angelis
4

Pour ouvrir tous les fichiers appelés quelque chose .txt(ie *.txt) dans le répertoire courant:

$EDITOR *.txt

$EDITORest votre éditeur préféré, par exemple gedit *.txt, nano *.txt, vim *.txt, emacs *.txtou autre chose. Utilisez juste *pour faire correspondre tous les fichiers du répertoire actuel.

Notez que la lscommande n'est pas impliquée. Le travail de lsn'est pas vraiment d'afficher une liste de fichiers, bien que cela se produise lorsque vous l'invoquez dans un répertoire. Il lsest utile d'afficher les attributs de fichier (heure de modification, autorisations, taille, etc.). Pour simplement faire quelque chose sur un tas de fichiers correspondant à un certain motif générique, les globes du shell sont suffisants.

Des éditeurs suffisamment avancés vous permettent de le faire de l'intérieur. Par exemple, dans Emacs, utilisez simplement la commande normale d'ouverture de fichier ( C-x C-f) et entrez *.txt.

Si vous souhaitez également faire correspondre des fichiers dans des sous-répertoires, en zsh ou bash ≥4, vous pouvez utiliser $EDITOR **/*.txt.

Gilles 'SO- arrête d'être méchant'
la source
C'est vraiment spécifique à l'éditeur. Il n'y a aucune garantie que tous les éditeurs traiteront tous leurs arguments de ligne de commande gratuits comme des fichiers à ouvrir, ni ne prennent en charge l'ouverture de plusieurs fichiers à la fois.
jmtd
2

Cela dépend de certaines nuances de votre éditeur de texte. Les éditeurs avancés peuvent probablement gérer l'ouverture de plusieurs fichiers à partir de la ligne de commande en une seule instance. Mais disons, par exemple, que votre éditeur ($ EDITOR dans mes exemples ci-dessous) ne peut en ouvrir qu'un à la fois. Vous devez diriger la sortie d'un fichier approprié findvers xargs. Cela dépend également du fait que $ EDITOR ne prend pas en charge le téléscripteur (donc, en utilisant un graphique)

find . -maxdepth 1 -type f -name '*.c' -print0 | xargs -r0n 1 $EDITOR

Si vous souhaitez utiliser un éditeur de console, une boucle de shell peut être plus appropriée, mais elle échouera pour de nombreux noms de fichiers inhabituels (en réduisant ou en remplaçant les espaces blancs et diverses autres choses):

for i in *.c; do $EDITOR "$i"; done
jmtd
la source
2
Ne pas analyser la sortie de ls! Utilisez $EDITOR *.cou for i in *.c; do $EDITOR "$i"; done.
Gilles 'SO- arrête d'être méchant'
Bonne capture - édité de manière appropriée.
jmtd
Notez que la forcasse échouera pour de nombreux noms de fichiers, y compris la réduction / la modification des caractères d'espacement.
jmtd
Comme il est écrit maintenant, le forcas fonctionnera avec chaque nom de fichier (sauf éventuellement les noms commençant par -ou +avec certains éditeurs; for i in ./*.ccorrigerait cela).
Gilles 'SO- arrête d'être méchant'