Skip to content
Foxipa

Suggest an edit

Tell us what should be corrected, clarified, or improved. Submission will be connected to Foxipa’s contribution service later.

No information is sent anywhere yet. Your suggestion is only prepared in your browser.

Learning

Git Grep: Repository-Aware Search

Search tracked content, index entries, committed trees, and selected untracked files with Git-aware patterns and pathspecs.

Levels: Advanced ~35 min read

Advanced

Learner goal

By the end of this lesson, you should be able to use `git grep` to search tracked working-tree content, the index, committed trees, and selected untracked files; constrain searches with pathspecs; and choose focused matching options without confusing Git-aware search with ordinary recursive shell search.

What `git grep` searches

With no special source option, `git grep` searches tracked files in the working tree. Git can instead search blobs registered in the index with `--cached`, or blobs in one or more tree objects by naming the tree. These modes let you compare the content you are currently editing with staged or committed content without first exporting it.

bash
git grep 'pattern'
git grep --cached 'pattern'
git grep 'pattern' HEAD

Quick check

Which source does `git grep --cached` search?

Stage a line that is not yet in HEAD.git grep --cached 'that line'

Working tree, index, and committed tree are different sources

The distinction matters when the same path has different content in different Git states. A normal `git grep` sees the tracked working-tree version; `--cached` sees the index version; and a tree argument such as `HEAD` searches the blobs stored in that tree. The command is therefore useful for asking a precise content question about a precise repository state.

bash
git grep 'feature'
git grep --cached 'feature'
git grep 'feature' HEAD

Quick check

Why can `git grep 'feature'` and `git grep --cached 'feature'` produce different results for the same path?

Limit the search with a pathspec

Put `--` before pathspecs when you want an unambiguous boundary between options or the search pattern and paths. A pathspec can narrow the search to a directory or matching path pattern. This is often safer and more useful than searching the whole repository when you already know where the relevant content lives.

bash
git grep 'TODO' -- src/
git grep 'TODO' -- 'src/*.c'

Quick check

What is the purpose of `--` before the pathspec in these examples?

Useful matching controls

`-n` adds line numbers, `-i` ignores case, `-l` reports only filenames containing matches, and `-F` treats the pattern as a fixed string rather than a regular expression. These options answer different questions: where is the match, does capitalization matter, which files match, or should punctuation be interpreted literally?

bash
git grep -n -i 'warning'
git grep -l 'deprecated'
git grep -F 'a.b'

Quick check

Which option makes `git grep` print only filenames containing a match?

Searching untracked files deliberately

Normal `git grep` searches tracked working-tree files. `--untracked` adds untracked files to that search. Ignored files are still excluded by the normal ignore rules; the official manual provides `--no-exclude-standard` for deliberately including ignored files when using `--untracked`. Use this distinction intentionally so a repository search does not silently become a search of generated or ignored material.

bash
git grep --untracked 'TODO'
git grep --untracked --no-exclude-standard 'TODO'

Quick check

What does `--untracked` add to the search?

When `--no-index` is appropriate

`--no-index` tells Git to search files without treating the current directory as a Git repository. The official manual describes it as similar to recursive ordinary `grep`, with Git pathspec benefits. It cannot be combined with `--cached` or `--untracked`. This is a useful boundary case, but it should not obscure the main purpose of `git grep`: repository-aware content search.

bash
git grep --no-index 'pattern' path/to/file

Quick check

Which combination is invalid according to the official `git grep` documentation?

A precise investigation workflow

When investigating a repository-wide text question, first decide which state you need to search. Use the default mode for tracked working-tree content, `--cached` for staged content, a tree such as `HEAD` for committed content, and `--untracked` when untracked files are intentionally in scope. Then narrow paths and add only the output or matching options needed for the question.

bash
git grep -n 'needle' -- src/
git grep --cached -n 'needle' -- src/
git grep -n 'needle' HEAD -- src/

Practice what you learned

Use the dedicated Git code-completion exercise for this lesson.

Official source boundary

This lesson uses the official Git `git-grep` documentation for command semantics, options, source-selection modes, pathspec behavior, and constraints. No third-party documentation is used for the command semantics.

Was this page helpful?

Mark this learning resource complete to track your learning progress.