8

I often need to search for a particular string from a directory that has git directory .git/. This is the command I use:

find . -name .git -prune -o -print | xargs grep <string-to-search>

The -name .git -prune -o -print option is to ignore the files under .git/. However, it outputs a lot of 'Is a directory' messages that clutter the whole result. For example,

...
grep: ./reports: Is a directory
grep: ./scripts: Is a directory
grep: ./scripts/js: Is a directory
grep: ./scripts/js/adapter: Is a directory
...

How to modify the command line so that I can ignore the .git/ directory and all other directories (i.e. only search the searchable files).

Apparently, the -type f option doesn't work well in:

find -type f . -name .git -prune -o -print
5
  • 4
    Why aren't you using git-grep? Commented Jan 1, 2013 at 10:03
  • 1
    Also, that last command should be find . -type f -name .git -prune -o -print. Commented Jan 1, 2013 at 10:05
  • Thanks, @Johnsyweb. find . -type f -name .git -prune -o -print actually still outputs directories. Commented Jan 1, 2013 at 10:13
  • 2
    You're right -- it's so much simpler using git-grep: git grep --untracked <string-to-search>. Let me keep this question open; I am still curious how we'd do this using the combination of grep and find. Commented Jan 1, 2013 at 10:24
  • What if you have multiple .git cloned from various places (example using repo), can git-grep (or some other tool) handle this? Commented Mar 21, 2017 at 11:23

4 Answers 4

27

You don't require find command. You can use grep to search in directory. You can ignore directory by using exclude-dir syntax.

grep -r --exclude-dir=".git;.svn" "string to search" <directory>
Sign up to request clarification or add additional context in comments.

7 Comments

N.B: This requires GNU Grep (>= 2.5.2).
Any alternative for a grep (BSD grep) 2.5.1-FreeBSD? Thanks!
find . -not -iwholename '.git'
This did not work for me with ; delimited paths. Try a single directory if you have any problems
Upvoted because this works well with multiple .git repositories when using repo. However, I had to split the ; file delimiter like so: grep -R --exclude-dir=".git" --exclude-dir=".svn" MyRegex
|
4

Answering my own question here (without giving any votes, etc.):

Since I was essentially doing a search specifically in a git-tracked directory, git grep is apparently much simpler and more apt tool for the job. Thanks to @Johnsyweb who initially brought this up!

I chose Vivek's answer because it provides a general grep solution as asked in the original question.

Comments

0

Recommend you try ripgrep https://github.com/BurntSushi/ripgrep

ripgrep is a line-oriented search tool that recursively searches the current directory for a regex pattern. By default, ripgrep will respect gitignore rules and automatically skip hidden files/directories and binary files.

It's faster and more developer friendly then other tools out there (that I've encountered) including grep and find

Comments

-1

The -type f is misplaced. It is filtering out directories before the -prune, which expects a directory name. The command should be find . -name .git -prune -o -type f -print. If you just want grep to shut up about directories, you can set the environment variable GREP_OPTIONS='--directories=skip'

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.