Tapez simplement "man grep" et vous verrez les options --exclude et --exclude-dir listées juste là - à partir du titre de cette question, je suppose que vous connaissiez déjà grep ...
arcseldon
35
Si vous Grepping pour le code dans un dépôt git et node_modulesest dans votre .gitignore, git grep "STUFF"est la meilleure façon. git greprecherche les fichiers suivis dans l'arborescence de travail, ignorant tout de.gitignore
0xcaff
2
Un exemple pour node: grep -R --exclude-dir={node_modules,bower_components} "MyString" | cut -c1-"$COLUMNS"- en outre, vous pouvez toujours alias ceci dans le shell pour 'nodegrep' ou autre chose et utiliser un argument de commande comme entrée de chaîne ..
bshea
Réponses:
395
SOLUTION 1 (combiner findet grep)
Le but de cette solution n'est pas de traiter les grepperformances mais de montrer une solution portable: devrait également fonctionner avec busybox ou une version GNU antérieure à 2.5.
Utilisez find, pour exclure les répertoires foo et bar:
Vous connaissez déjà cette solution, mais je l'ajoute car c'est la solution la plus récente et la plus efficace. Notez qu'il s'agit d'une solution moins portable mais plus lisible par l'homme.
Pour exclure plusieurs répertoires, utilisez --exclude-dircomme:
--exclude-dir={node_modules,dir1,dir2,dir3}
SOLUTION 3 (Ag)
Si vous recherchez fréquemment du code, Ag (The Silver Searcher) est une alternative beaucoup plus rapide à grep, qui est personnalisée pour la recherche de code. Par exemple, il ignore automatiquement les fichiers et répertoires répertoriés dans .gitignore, vous n'avez donc pas à passer les mêmes options d'exclusion lourdes à grepou find.
cette combinaison recherche plus vite que --exclude-dir=diret elle montre des résultats avec des couleurs - facile à lire
Maxim Yefremov
27
"cette combinaison" find ... -execn'est pas plus rapide que grep --exclude-dirpour moi. Un énorme avantage pour grep (environ cinq fois plus rapide avec 26k + fichiers, filtré sur 38k + sur un disque dur), sauf si vous remplacez le \;par +pour le combo find / exec. Grep est alors "seulement" environ 30% plus rapide. La syntaxe grep est également lisible par l'homme :).
Kjell Andreassen
D'accord, car cela est évident. Certaines boîtes occupées n'ont pas la commande GREP.
hornetbzz
10
notant également que vous pouvez exclure plusieurs avec--exclude-dir={dir1,dir2}
suh
4
Je ne suis pas le moins du monde surpris que ce node_modulessoit l'exemple canonique.
pdoherty926
984
Les versions récentes de GNU Grep (> = 2.5.2 ) fournissent:
--exclude-dir=dir
ce qui exclut les répertoires correspondant au modèle dirdes recherches de répertoires récursives.
@Manocho: Si vous pensez que ackc'est génial, essayez The Silver Searcher et voyez la vitesse augmenter!
Johnsyweb
30
Syntaxe pour les impatients: --exclude-dir=dirutilise greples modèles d'expression régulière de, et non la globalisation des fichiers du shell. Les modèles fonctionnent sur les chemins relatifs à votre répertoire actuel. Utilisez donc le modèle --exclude-dir=dir, non --exclude-dir="/root/dir/*".
tanius
15
Si vous souhaitez exclure plusieurs répertoires de la recherche, y a-t-il une meilleure option que d'utiliser $ grep -r --exclude-dir=dir1 --exclude-dir=dir2 "string" /path/to/search/dir:?
Darshan Chaudhary
4
J'ai probablement passé beaucoup trop de temps à ce sujet que n'importe quelle personne sensée, mais je ne peux pas pour la vie de moi comprendre comment exclure un sous-répertoire de la recherche - grep -r --exclude-dir=public keyword .fonctionne, mais grep -r --exclude-dir='public/dist' keyword .ne le fait pas. J'ai essayé d'ajouter des caractères génériques regex, des caractères d'échappement, etc., mais rien ne semble aider.
dkobozev
73
Exclure plusieurs répertoires comme ceci:grep -r "Request" . --exclude-dir={node_modules,git,build}
maverick97
78
Si vous souhaitez exclure plusieurs répertoires :
"r" pour récursif, "l" pour imprimer uniquement les noms des fichiers contenant des correspondances et "i" pour ignorer les distinctions de casse:
Exemple: je souhaite rechercher des fichiers contenant le mot «bonjour». Je veux rechercher dans tous mes répertoires linux sauf le répertoire proc , le répertoire de démarrage , le répertoire sys et le répertoire racine :
REMARQUE: n'ajoutez pas d'espaces après les virgules{dir1,dir2,dir3}
skplunkerin
Merci, pratique lorsque vous parcourez l'espace de travail SVN:grep -Irsn --exclude-dir=.svn 'foo' .
RAM237
1
Vous pouvez simplement fournir l' --exclude-diroption plusieurs fois.
Walf
45
Cette syntaxe
--exclude-dir={dir1,dir2}
est développé par le shell (par exemple Bash), pas par grep, en ceci:
--exclude-dir=dir1 --exclude-dir=dir2
Citer empêchera le shell de le développer, donc cela ne fonctionnera pas:
--exclude-dir='{dir1,dir2}' <-- this won't work
Les modèles utilisés avec --exclude-dirsont les mêmes types de modèles décrits dans la page de manuel de l' --excludeoption:
--exclude=GLOB
Skip files whose base name matches GLOB (using wildcard matching).
A file-name glob can use *, ?, and [...] as wildcards, and \ to
quote a wildcard or backslash character literally.
Le shell essaie généralement de développer un tel modèle lui-même, donc pour éviter cela, vous devez le citer:
--exclude-dir='dir?'
Vous pouvez utiliser les accolades et les motifs d'exclusion cités ensemble comme ceci:
--exclude-dir={'dir?','dir??'}
Un motif peut s'étendre sur plusieurs segments de chemin:
--exclude-dir='some*/?lse'
Cela exclurait un répertoire comme topdir/something/else.
greppeut être utilisé conjointement avec -r(récursif), i(ignorer la casse) et -o(imprime uniquement une partie correspondante des lignes). Pour exclure l' filesutilisation --excludeet exclure l'utilisation des répertoires --exclude-dir.
En l'assemblant, vous vous retrouvez avec quelque chose comme:
Le décrire le rend beaucoup plus compliqué qu'il ne l'est réellement. Plus facile à illustrer avec un exemple simple.
Exemple:
Supposons que je recherche le projet en cours pour tous les endroits où j'ai explicitement défini la valeur de la chaîne debuggerlors d'une session de débogage et que je souhaite maintenant réviser / supprimer.
J'écris un script appelé findDebugger.shet utilise greppour trouver toutes les occurrences. Toutefois:
Pour les exclusions de fichiers - je souhaite m'assurer que cela .eslintrcest ignoré (cela a en fait une règle sur les peluches debuggeret doit donc être exclu). De même, je ne veux pas que mon propre script soit référencé dans les résultats.
Pour les exclusions de répertoires - je souhaite exclure node_modulescar il contient de nombreuses bibliothèques qui font référence debuggeret je ne suis pas intéressé par ces résultats. Aussi je voudrais juste Omettre .ideaet .gitrépertoires cachés parce que je ne me soucie pas de ces lieux de recherche non plus , et je souhaite de garder la recherche performant.
Voici donc le résultat - je crée un script appelé findDebugger.shavec:
Je crois que l'option "r" devrait être imprimée avec un "-R" majuscule.
hornetbzz
1
Intéressant. "r" a toujours fonctionné pour moi sur nix et mac.
arcseldon
Quand j'ai écrit ma réponse , j'ai utilisé -R(je ne me souviens plus pourquoi maintenant). J'utilise généralement -r. Il s'avère que la version majuscule suit les liens symboliques . TIL.
Johnsyweb
@Johnsyweb - merci. a voté pour votre réponse - ne me souviens pas quand, probablement en 2016 quand j'ai ajouté celui-ci :)
Pas une bonne solution dans certains cas. Par exemple: si le répertoire 'node_modules' est énorme avec beaucoup de fausses correspondances positives (d'où la nécessité de filtrer le répertoire), alors le premier grep perd beaucoup de temps à chercher dans un sous-répertoire et ALORS le deuxième filtrage grep les matchs. Il est plus rapide d'exclure node_modules dans le premier grep lui-même.
GuruM
2
je ne me soucie pas de la lenteur, je peux regarder la commande et savoir ce qu'elle fait
Funkodebat
1
Idem pour le commentaire de Guru. Un grep de se /varbloque quand il frappe /var/rundans mon cas. D'où la raison pour laquelle je veux éviter le répertoire en premier lieu.
2015 à 9h48
3
--exclude-direst la meilleure solution à partir de 2016.
Omar Tariq
10
Si vous Grepping pour le code dans un dépôt git et node_modulesest dans votre .gitignore, vous pouvez utiliser git grep. git greprecherche les fichiers suivis dans l'arborescence de travail, ignorant tout de.gitignore
Propre, y compris plusieurs répertoires entre parenthèses
Mijo
2
Beaucoup de bonnes réponses ont été données ici, mais j'ajoute celle-ci pour souligner un point qui a provoqué l'échec de certaines tentatives précipitées: exclude-dirprend un modèle , pas un chemin vers un répertoire.
Dites que votre recherche est:
grep -r myobject
Et vous remarquez que votre sortie est encombrée de résultats du src/other/objects-folder. Cette commande ne vous donnera pas le résultat souhaité:
Et vous vous demandez peut-être pourquoi ça exclude-dirne marche pas! Pour exclure réellement les résultats de la objects-folder, procédez simplement comme suit:
grep -r myobject --exclude-dir=objects-folder
En d'autres termes, utilisez simplement le nom du dossier , pas le chemin d'accès. Évident une fois que vous le savez.
Depuis la page de manuel:
--exclude-dir = GLOB Ignore
tout répertoire de ligne de commande avec un suffixe de nom qui correspond au modèle GLOB. Lors d'une recherche récursive, ignorez tout sous-répertoire dont le nom de base correspond à GLOB. Ignorez toutes les barres obliques redondantes dans GLOB.
node_modules
est dans votre.gitignore
,git grep "STUFF"
est la meilleure façon.git grep
recherche les fichiers suivis dans l'arborescence de travail, ignorant tout de.gitignore
grep -R --exclude-dir={node_modules,bower_components} "MyString" | cut -c1-"$COLUMNS"
- en outre, vous pouvez toujours alias ceci dans le shell pour 'nodegrep' ou autre chose et utiliser un argument de commande comme entrée de chaîne ..Réponses:
SOLUTION 1 (combiner
find
etgrep
)Le but de cette solution n'est pas de traiter les
grep
performances mais de montrer une solution portable: devrait également fonctionner avec busybox ou une version GNU antérieure à 2.5.Utilisez
find
, pour exclure les répertoires foo et bar:Combinez ensuite
find
et l'utilisation non récursive degrep
, comme solution portable:SOLUTION 2 (utilisation récursive de
grep
):Vous connaissez déjà cette solution, mais je l'ajoute car c'est la solution la plus récente et la plus efficace. Notez qu'il s'agit d'une solution moins portable mais plus lisible par l'homme.
Pour exclure plusieurs répertoires, utilisez
--exclude-dir
comme:--exclude-dir={node_modules,dir1,dir2,dir3}
SOLUTION 3 (Ag)
Si vous recherchez fréquemment du code, Ag (The Silver Searcher) est une alternative beaucoup plus rapide à grep, qui est personnalisée pour la recherche de code. Par exemple, il ignore automatiquement les fichiers et répertoires répertoriés dans
.gitignore
, vous n'avez donc pas à passer les mêmes options d'exclusion lourdes àgrep
oufind
.la source
--exclude-dir=dir
et elle montre des résultats avec des couleurs - facile à lirefind ... -exec
n'est pas plus rapide quegrep --exclude-dir
pour moi. Un énorme avantage pour grep (environ cinq fois plus rapide avec 26k + fichiers, filtré sur 38k + sur un disque dur), sauf si vous remplacez le\;
par+
pour le combo find / exec. Grep est alors "seulement" environ 30% plus rapide. La syntaxe grep est également lisible par l'homme :).--exclude-dir={dir1,dir2}
node_modules
soit l'exemple canonique.Les versions récentes de GNU Grep (> = 2.5.2 ) fournissent:
ce qui exclut les répertoires correspondant au modèle
dir
des recherches de répertoires récursives.Vous pouvez donc faire:
Pour un peu plus d'informations sur la syntaxe et l'utilisation, voir
Pour les anciens GNU Greps et POSIX Grep , utilisez
find
comme suggéré dans d'autres réponses.Ou utilisez simplement
ack
( Edit : ou The Silver Searcher ) et terminez!la source
ack
c'est génial, essayez The Silver Searcher et voyez la vitesse augmenter!--exclude-dir=dir
utilisegrep
les modèles d'expression régulière de, et non la globalisation des fichiers du shell. Les modèles fonctionnent sur les chemins relatifs à votre répertoire actuel. Utilisez donc le modèle--exclude-dir=dir
, non--exclude-dir="/root/dir/*"
.$ grep -r --exclude-dir=dir1 --exclude-dir=dir2 "string" /path/to/search/dir
:?grep -r --exclude-dir=public keyword .
fonctionne, maisgrep -r --exclude-dir='public/dist' keyword .
ne le fait pas. J'ai essayé d'ajouter des caractères génériques regex, des caractères d'échappement, etc., mais rien ne semble aider.grep -r "Request" . --exclude-dir={node_modules,git,build}
Si vous souhaitez exclure plusieurs répertoires :
"r" pour récursif, "l" pour imprimer uniquement les noms des fichiers contenant des correspondances et "i" pour ignorer les distinctions de casse:
Exemple: je souhaite rechercher des fichiers contenant le mot «bonjour». Je veux rechercher dans tous mes répertoires linux sauf le répertoire proc , le répertoire de démarrage , le répertoire sys et le répertoire racine :
Remarque: l'exemple ci-dessus doit être root
Note 2 (selon @skplunkerin): n'ajoutez pas d'espaces après les virgules dans
{dir1,dir2,dir3}
la source
{dir1,dir2,dir3}
grep -Irsn --exclude-dir=.svn 'foo' .
--exclude-dir
option plusieurs fois.Cette syntaxe
est développé par le shell (par exemple Bash), pas par
grep
, en ceci:Citer empêchera le shell de le développer, donc cela ne fonctionnera pas:
Les modèles utilisés avec
--exclude-dir
sont les mêmes types de modèles décrits dans la page de manuel de l'--exclude
option:Le shell essaie généralement de développer un tel modèle lui-même, donc pour éviter cela, vous devez le citer:
Vous pouvez utiliser les accolades et les motifs d'exclusion cités ensemble comme ceci:
Un motif peut s'étendre sur plusieurs segments de chemin:
Cela exclurait un répertoire comme
topdir/something/else
.la source
Utilisez fréquemment ceci:
grep
peut être utilisé conjointement avec-r
(récursif),i
(ignorer la casse) et-o
(imprime uniquement une partie correspondante des lignes). Pour exclure l'files
utilisation--exclude
et exclure l'utilisation des répertoires--exclude-dir
.En l'assemblant, vous vous retrouvez avec quelque chose comme:
Le décrire le rend beaucoup plus compliqué qu'il ne l'est réellement. Plus facile à illustrer avec un exemple simple.
Exemple:
Supposons que je recherche le projet en cours pour tous les endroits où j'ai explicitement défini la valeur de la chaîne
debugger
lors d'une session de débogage et que je souhaite maintenant réviser / supprimer.J'écris un script appelé
findDebugger.sh
et utilisegrep
pour trouver toutes les occurrences. Toutefois:Pour les exclusions de fichiers - je souhaite m'assurer que cela
.eslintrc
est ignoré (cela a en fait une règle sur les peluchesdebugger
et doit donc être exclu). De même, je ne veux pas que mon propre script soit référencé dans les résultats.Pour les exclusions de répertoires - je souhaite exclure
node_modules
car il contient de nombreuses bibliothèques qui font référencedebugger
et je ne suis pas intéressé par ces résultats. Aussi je voudrais juste Omettre.idea
et.git
répertoires cachés parce que je ne me soucie pas de ces lieux de recherche non plus , et je souhaite de garder la recherche performant.Voici donc le résultat - je crée un script appelé
findDebugger.sh
avec:la source
-R
(je ne me souviens plus pourquoi maintenant). J'utilise généralement-r
. Il s'avère que la version majuscule suit les liens symboliques . TIL.Vous pourriez essayer quelque chose comme
grep -R search . | grep -v '^node_modules/.*'
la source
/var
bloque quand il frappe/var/run
dans mon cas. D'où la raison pour laquelle je veux éviter le répertoire en premier lieu.--exclude-dir
est la meilleure solution à partir de 2016.Si vous Grepping pour le code dans un dépôt git et
node_modules
est dans votre.gitignore
, vous pouvez utilisergit grep
.git grep
recherche les fichiers suivis dans l'arborescence de travail, ignorant tout de.gitignore
la source
Très utile, surtout pour ceux qui traitent avec Node.js où nous voulons éviter de chercher dans "node_modules":
la source
Une commande de travail simple:
Ci-dessus, je demande le texte "creativecommons.org" dans le répertoire courant "dspace" et j'exclus les répertoires {log, assetstore}.
Terminé.
la source
Beaucoup de bonnes réponses ont été données ici, mais j'ajoute celle-ci pour souligner un point qui a provoqué l'échec de certaines tentatives précipitées:
exclude-dir
prend un modèle , pas un chemin vers un répertoire.Dites que votre recherche est:
Et vous remarquez que votre sortie est encombrée de résultats du
src/other/objects-folder
. Cette commande ne vous donnera pas le résultat souhaité:Et vous vous demandez peut-être pourquoi ça
exclude-dir
ne marche pas! Pour exclure réellement les résultats de laobjects-folder
, procédez simplement comme suit:En d'autres termes, utilisez simplement le nom du dossier , pas le chemin d'accès. Évident une fois que vous le savez.
Depuis la page de manuel:
la source
Celui-ci fonctionne pour moi:
la source
la source
Une manière plus simple serait de filtrer vos résultats en utilisant "grep -v".
grep -i needle -R * | grep -v node_modules
la source