Git, Binary Files and Cherry Picking Patches
Steve Dekorte has some things he dislikes about git. This post is how I work around these issues in my own git repositories.
Git has a heuristic for detecting binary files. You can force other file types to be binary by adding a .gitattributes file to your repository. This file contains a list of glob patterns, followed by attributes to be applied to files matching those patterns. By adding .gitattributes to the repository all cloned repositories will pick this up as well.
For example, if you want all *.foo files to be treated as binary files you can have this line in .gitattributes:
Now when you pull from another repository that has changes to a .foo file you'll see something like:
Given a commit id, 'cherry-pick' will take the patch for that commit and apply it to your current branch. It's used like:
If you decide later you want all John's commits and do a merge which includes the commit that you cherry picked from you might expect conflicts. Git handles this case fine and does an automatic merge, noticing the patches are the same. So it effectively gives you the same functionality as Darcs selective patch pulling, but not as nice a user interface.
Categories: git
Git has a heuristic for detecting binary files. You can force other file types to be binary by adding a .gitattributes file to your repository. This file contains a list of glob patterns, followed by attributes to be applied to files matching those patterns. By adding .gitattributes to the repository all cloned repositories will pick this up as well.
For example, if you want all *.foo files to be treated as binary files you can have this line in .gitattributes:
*.foo -crlf -diff -mergeThis will mean all files with a .foo extension will not have carriage return/line feed translations done, won't be diffed and merges will result in conflicts leaving the original file untouched.
Now when you pull from another repository that has changes to a .foo file you'll see something like:
test.foo | Bin 32 -> 36 bytesNote that it shows it is a binary file. If you pull from another repository with changes to test.foo you'll get:
Auto-merged test.fooThe file will be untouched and you can change it manually to be the correct version. Either by leaving it untouched, or copying a new file over it. Then you need to commit the merge conflict fix (even if you left the file untouched):
CONFLICT (content): Merge conflict in test.foo
git commit -a -m "Fix merge conflict in test.foo"The cherry picking of patches works differently to Darcs. There are a couple of ways of handling this, but I use 'git cherry-pick'. If you have a number of contributers with their own repositories that you regularly pull from you can set up remote tracking branches:
git remote add john http://...Now when you want John and Mary's most recent patches you can fetch them:
git remote add mary http://...
git fetch johnThis does not make any changes to your local branches. It gets and stores their changes in a separate remote tracking branch. If you want to see what John has changed, compared to yours:
git fetch mary
git log -p master..john/masterFrom there you can decide to pull in all John's commits:
git merge john/masterIf you want one commit, but not its dependencies then this is where 'cherry-pick' is used.
Given a commit id, 'cherry-pick' will take the patch for that commit and apply it to your current branch. It's used like:
git cherry-pick abcdefghThis creates a commit with a different commit id than the original, but with the same contents. It needs to be a different id as it doesn't have the same dependencies as the original.
If you decide later you want all John's commits and do a merge which includes the commit that you cherry picked from you might expect conflicts. Git handles this case fine and does an automatic merge, noticing the patches are the same. So it effectively gives you the same functionality as Darcs selective patch pulling, but not as nice a user interface.
Categories: git

2 Comments:
That's just what I needed to be able to store graphic files that happen to be in XML format (i.e. Adobe Illustrator files). Marking them as binary works a lot better and doesn't introduce meaningless merges on their contents.
Thanks!
Hi!
Could this
*.foo -crlf -diff -merge
be done automatically, every time I create new repository?
Post a Comment
<< Home