If I don\'t want .html files tracked I can add the pattern to .gitignore and they\'ll be ignored. I\'d like to know how I can do the converse - at checkout, how could I ask git
If you want to package up files for deployment, you probably don't need - or want - the repo itself. This is exactly what git archive is for. A couple examples from the manpage (linked):
git archive --format=tar --prefix=junk/ HEAD | (cd /var/tmp/ && tar xf -)
Create a tar archive that contains the contents of the latest commit on the current branch, and extract it in the /var/tmp/junk directory.
git archive --format=tar --prefix=git-1.4.0/ v1.4.0 | gzip > git-1.4.0.tar.gz
Create a compressed tarball for v1.4.0 release.
You ought to be able to get it to do exactly what you want, with the help of the export-ignore
attribute:
export-ignore
Files and directories with the attribute export-ignore won’t be added to archive files. See gitattributes(5) for details.
For example, to exclude the directory private
and the files mine.txt
and secret.c
, you could put in the file .gitattributes
:
private/ export-ignore
secret.c export-ignore
Just like gitignore files, you can put those anywhere in your repository, and they'll operate from that directory, but starting from the top level is a good bet.
If you want just a one-time change (or not consistent) or you just don't want to put files in .gitignore
then do the below:
checkout
git stash push -m "files_to_ignore" my/path/of/the/file/file.txt
git checkout .
git stash apply stash^{/files_to_ignore}
The complete solution using git aliases can look like this:
alias reset-non-dev='git stash push -m "ignore_files" MyRepo/file1.txt MyRepo/dir/file2.js MyRepo/dir/dir2/file3.cs PSOne/Startup/PSOne/Views/Login.xaml.cs ; git checkout . ; git stash apply stash^{/ignore_files} ;'
Later you can use this alias simply by putting its name in git bash and hitting enter.
One benefit here that I observed is that with this approach you can change the files or skip them whenever you really need it and not marked such files as always ignored.
So I wanted to ship my code without the test files to the production server.
Easiest way for me was just to remove all the test files with: rsync --exclude 'tests'
after unpacking the archive.
If you only want to checkout a portion of your repository, you can use git's sparse-checkout option which has powerful include/exclude rules.
The following StackOverflow question has some helpful instructions:
GIT checkout except one folder
But as a summary:
Enable the sparseCheckout
option:
git config core.sparseCheckout true
Create the file called .git/info/sparse-checkout
containing:
/*
!node_modules
which effectively means include everything except the node_modules
directory when checking out a repository into the working directory.
You cannot retrieve part of an individual commit in Git. You either pull a commit or you don't - there's no half-way step.
This means that if there is a commit that adds a bunch of files then you can get all of those files (by pulling that commit into your local repo) or none of them (by not pulling that commit).
You can choose which commits you want with git cherry-pick
, but I suspect it's not going to help you much in this case.
Generally a file should either be in version control or not - I can't think of a reason why you'd want a file in Git only sometimes. If there's something in your .gitignore then it's probably a good candidate for removing from the repository altogether. .gitignore basically means "don't look at this file, it's not under version control".
(If you don't mind rewriting your repository history you could cherry-pick the add commit, then do a git reset --mixed HEAD^1
and create new commits that leave out the files you don't want...but don't do this unless you really know what you're doing. Better to just remove the files and push a new commit that records the removal.)
EDIT: Just saw your comment about wanting specific parts for a deployment. In that case I'd suggest you create a deployment branch that removes the irrelevant files. You can rebase this branch from mainline whenever you need to and it should magically remove the files for you each time.