To search multiple files with the grep command, insert the filenames you want to search, separated with a space character. The terminal prints the name of every file that contains the matching lines, and the actual lines that include the required string of characters. You can append as many filenames as needed.
Specifying File Type To do so, we can use a special type of option that starts with two hyphens: $ grep -ri "hello" --include=*. cc Test/test.cc:Hello World!
To read a list of files to exclude from a file, use --exclude-from FILE .
Since many files contain database references, you might get a lot of data on output, so if you are only interested in all the files containing matching text, you can use the grep -l option. This option of grep only shows filenames that contain matching text.
You can use multiple --include
flags. This works for me:
grep -r --include=*.html --include=*.php --include=*.htm "pattern" /some/path/
However, you can do as Deruijter suggested. This works for me:
grep -r --include=*.{html,php,htm} "pattern" /some/path/
Don't forget that you can use find
and xargs
for this sort of thing too:
find /some/path/ -name "*.htm*" -or -name "*.php" | xargs grep "pattern"
Using {html,php,htm}
can only work as a brace expansion, which is a nonstandard (not POSIX-compliant) feature of bash
, ksh
, and zsh
.
In other words: do not try to use it in a script that targets /bin/sh
- use explicit multiple --include
arguments in that case.
grep
itself does not understand {...}
notation.
For a brace expansion to be recognized, it must be an unquoted (part of a) token on the command line.
A brace expansion expands to multiple arguments, so in the case at hand grep
ends up seeing multiple --include=...
options, just as if you had passed them individually.
The results of a brace expansion are subject to globbing (filename expansion), which has pitfalls:
Each resulting argument could further be expanded to matching filenames if it happens to contain unquoted globbing metacharacters such as *
.
While this is unlikely with tokens such as --include=*.html
(e.g., you'd have to have a file literally named something like --include=foo.html
for something to match), it is worth keeping in mind in general.
If the nullglob
shell option happens to be turned on (shopt -s nullglob
) and globbing matches nothing, the argument will be discarded.
Therefore, for a fully robust solution, use the following:
grep -R '--include=*.'{html,php,htm} pattern /some/path
'--include=*.'
is treated as a literal, due to being single-quoted; this prevents inadvertent interpretation of *
as a globbing character.
{html,php,htm}
, the - of necessity - unquoted brace expansion[1]
, expands to 3 arguments, which, due to {...}
directly following the '...'
token, include that token.
Therefore, after quote removal by the shell, the following 3 literal arguments are ultimately passed to grep
:
--include=*.html
--include=*.php
--include=*.htm
[1] More accurately, it's only the syntax-relevant parts of the brace expansion that must be unquoted, the list elements may still be individually quoted and must be if they contain globbing metacharacters that could result in unwanted globbing after the brace expansion; while not necessary in this case, the above could be written as'--include=*.'{'html','php','htm'}
Try removing the double quotes
grep --include=*.{html,php,htm} pattern -R /some/path
is this not working?
grep pattern /some/path/*.{html,php,htm}
It works for the same purpose, but without --include
option. It works on grep 2.5.1 as well.
grep -v -E ".*\.(html|htm|php)"
Try this. -r will do a recursive search. -s will suppress file not found errors. -n will show you the line number of the file where the pattern is found.
grep "pattern" <path> -r -s -n --include=*.{c,cpp,C,h}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With