Make .gitignore ignore everything except a few files – Dev

The best answers to the question “Make .gitignore ignore everything except a few files” in the category Dev.

QUESTION:

I understand that a .gitignore file cloaks specified files from Git’s version
control. I have a project (LaTeX) that generates lots of extra files (.auth,
.dvi, .pdf, logs, etc) as it runs, but I don’t want those to be tracked.

I’m aware that I could (maybe should) make it so all those files are put in an
separate subfolder in the project, since I could then just ignore the folder.

However, is there any feasible way to keep the output files in the root of the
project tree and use .gitignore to ignore everything except the files I’m
tracking with Git? Something like

# Ignore everything
*

# But not these files...
script.pl
template.latex
# etc...

ANSWER:

If you want to ignore the whole content of a directory except one file inside it, you could write a pair of rules for each directory in the file path. E.g. .gitignore to ignore the pippo folder except from pippo/pluto/paperino.xml

pippo/*
!pippo/pluto
pippo/pluto/*
!pippo/pluto/paperino.xml

Note that if you simply had written above:

pippo/*
!pippo/pluto/paperino.xml

It wouldn’t work because the intermediary pluto folder would not exist to Git, so paperino.xml could not find a place in which to exist.

ANSWER:

An optional prefix ! which negates the pattern; any matching file excluded by
a previous pattern will become included again. If a negated pattern matches,
this will override lower precedence patterns sources.

# Ignore everything
*

# But not these files...
!.gitignore
!script.pl
!template.latex
# etc...

# ...even if they are in subdirectories
!*/

# if the files to be tracked are in subdirectories
!*/a/b/file1.txt
!*/a/b/c/*

ANSWER:

A little more specific:

Example: Ignore everything in webroot/cache – but keep webroot/cache/.htaccess.

Notice the slash (/) after the cache folder:

FAILS

webroot/cache*
!webroot/cache/.htaccess

WORKS

webroot/cache/*
!webroot/cache/.htaccess

ANSWER:

You want to use /* instead of * or */ in most cases

Using * is valid, but it works recursively. It won’t look into directories from then on out. People recommend using !*/ to whitelist directories again, but it’s actually better to blacklist the highest level folder with /*

# Blacklist files/folders in same directory as the .gitignore file
/*

# Whitelist some files
!.gitignore
!README.md

# Ignore all files named .DS_Store or ending with .log
**/.DS_Store
**.log

# Whitelist folder/a/b1/ and folder/a/b2/
# trailing "https://stackoverflow.com/" is optional for folders, may match file though.
# "https://stackoverflow.com/" is NOT optional when followed by a *
!folder/
folder/*
!folder/a/
folder/a/*
!folder/a/b1/
!folder/a/b2/
!folder/a/file.txt

# Adding to the above, this also works...
!/folder/a/deeply
/folder/a/deeply/*
!/folder/a/deeply/nested
/folder/a/deeply/nested/*
!/folder/a/deeply/nested/subfolder

The above code would ignore all files except for .gitignore, README.md, folder/a/file.txt, folder/a/b1/ and folder/a/b2/ and everything contained in those last two folders. (And .DS_Store and *.log files would be ignored in those folders.)

Obviously I could do e.g. !/folder or !/.gitignore too.

More info: http://git-scm.com/docs/gitignore