Free tool
.gitignore generator
Pick the languages, frameworks, editors and operating systems in your project and get one clean, commented .gitignore. Duplicate rules are removed only when that cannot change the result, you can merge in your existing file, and the path tester shows whether git would ignore a path and which line decides it.
Free · no sign-up · runs in your browser, nothing is uploaded
Pick templates or a stack above. Your .gitignore appears here.
Type paths on the left to see whether git would ignore them and which line decides it.
Some browsers save the download as gitignore or _gitignore. Rename it to .gitignore in your project root.
.gitignore pattern syntax
Each line in a .gitignore is one pattern. Blank lines are ignored and lines starting with # are comments. The rules that trip people up:
| Pattern | Matches | Why |
|---|---|---|
| *.log | app.log, logs/debug.log | No slash: matches at any depth |
| build/ | build folders anywhere | A trailing slash matches folders only, not a file named build |
| /build | build at the root only | A leading slash anchors it to the .gitignore’s folder |
| docs/*.md | docs/a.md, not docs/x/a.md | A slash in the middle anchors it, and * does not cross / |
| **/cache | cache, a/cache, a/b/cache | Leading **/ means in any folder |
| logs/** | everything inside logs | Trailing /** means all contents |
| a/**/b | a/b, a/x/b, a/x/y/b | /**/ matches zero or more folders |
| !.env.example | re-includes that file | A later ! rule undoes an earlier match |
| \#notes.txt | a file named #notes.txt | Backslash escapes a leading # or ! |
The last matching line wins, which is why the generator keeps a duplicate rule when a ! rule sits between the two copies: removing it would change what is ignored. Trailing spaces are dropped unless you escape them with a backslash.
Re-including a file inside an ignored folder
This is the most common .gitignore surprise. Git skips ignored folders entirely, so a ! rule for a file inside one never gets a chance to match:
# Does NOT work: config/ is ignored, so git never looks inside it config/ !config/default.json # Works: ignore the contents, keep the folder visible config/* !config/default.json
The path tester above follows the same rule. Type config/default.json and it tells you when a parent folder is the reason the file stays ignored.
Common commands
| Command | What it does |
|---|---|
| git check-ignore -v path/to/file | Shows the file, line and pattern that ignore a path |
| git rm --cached file | Stops tracking a committed file but keeps it on disk |
| git rm -r --cached folder/ | The same for a whole folder |
| git status --ignored | Lists ignored files as well as untracked ones |
| git ls-files -ci --exclude-standard | Lists tracked files that your ignore rules would now ignore |
| git config --global core.excludesFile ~/.gitignore_global | Sets a personal ignore file for every repository |
After you add a rule for something that was already committed, run git rm --cached on it and commit. Until then git keeps tracking the file, whatever the .gitignore says.
What belongs in a .gitignore
- Dependencies and build output that can be recreated:
node_modules/,target/,dist/,__pycache__/,.next/. - Secrets:
.envfiles, private keys and credentials. Commit an.env.examplewith empty values instead. Ignoring a file does not remove it from history, so rotate any secret that was already pushed. - Machine files:
.DS_Store,Thumbs.db, editor folders. These are often better in your global ignore file, but many teams add them to the project too. - Not lock files.
package-lock.json,pnpm-lock.yaml,poetry.lock, andCargo.lockorpubspec.lockfor apps, should normally be committed so installs are repeatable. The templates here leave them tracked; the Rust and Dart ones say how to ignore them for a library.
Shipping with Docker? A .dockerignore uses similar patterns to keep files out of the build context. To turn your docker run commands into a Compose file, use the docker run to Compose converter. To set permissions on scripts you commit, see the chmod calculator.
More free developer tools
Looking for a full product instead? See DevOps tools on DevHunt.
FAQ
How do I create a .gitignore file?+
Pick your languages, frameworks, editors and operating system above (or one of the stacks), then download the file or copy it. Save it as .gitignore in the root of your repository and commit it, so everyone on the project uses the same rules.
Why is git still tracking a file I added to .gitignore?+
.gitignore only affects untracked files. If the file was committed before, git keeps tracking it. Run git rm --cached <file> (or git rm -r --cached <folder>) to stop tracking it without deleting it from disk, then commit.
Should .gitignore itself be committed?+
Yes. The .gitignore in your repository is meant to be shared. Rules that only apply to you, such as your own editor, can go in .git/info/exclude (this repository only) or in a global ignore file instead.
How do I set up a global .gitignore?+
Git reads the file set in core.excludesFile. If that is not set, it uses ~/.config/git/ignore (or $XDG_CONFIG_HOME/git/ignore). A common setup is git config --global core.excludesFile ~/.gitignore_global, with OS and editor rules like .DS_Store and .idea/ in it.
How do I find out which rule is ignoring a file?+
Run git check-ignore -v <path>. It prints the file, line number and pattern that decided it. The path tester on this page does the same in your browser: type paths and it shows ignored or tracked and the line that matched.
Why does !file not un-ignore my file?+
Git cannot re-include a file if one of its parent folders is excluded, because git does not look inside ignored folders. Ignore the folder contents with folder/* instead of folder/, then add !folder/file.
What does ** mean in .gitignore?+
A leading **/ matches in any folder, so **/logs matches logs anywhere. A trailing /** matches everything inside, so abc/** ignores all files under abc. a/**/b matches a/b, a/x/b and a/x/y/b.
Where do these templates come from?+
They are based on the public domain (CC0) github/gitignore collection and each tool’s own docs, trimmed to rules most projects need, with comments that say why each group is there. Nothing is fetched at run time, so the generator works offline once loaded.
Sources: git docs: gitignore · git docs: check-ignore · git docs: rm --cached · git docs: core.excludesFile · github/gitignore templates (CC0) · GitHub docs: ignoring files. Checked October 2026.