6 private links
This document is an attempt to be a fairly comprehensive guide to recovering from what you did not mean to do when using git. It isn't that git is so complicated that you need a large document to take care or your particular problem, it is more that the set of things that you might have done is so large that different techniques are needed depending on exactly what you have done and what you want to have happen.
Gitchain is an application of the exciting ideas behind Bitcoin, Namecoin and DHT applied to Git hosting. Once you install it, it acts as a local proxy to the entire Gitchain P2P network.
Un git merge ne devrait être utilisé que pour la récupération fonctionnelle, intégrale et finale d’une branche dans une autre, afin de préserver un graphe d’historique sémantiquement cohérent et utile, lequel représente une véritable valeur ajoutée.
Tous les autres cas de figure relèvent du rebase sous toutes ses formes : classique, tri-partite, interactif ou cherry picking.
Some git tips
Stage by hunks
Multiple server for git
Occasionally I dropped a DVD-rip into a website project, then carelessly git commit -a -m ..., and, zap, the repo was bloated by 2.2 gigs. Next time I made some edits, deleted the video file, and commited everything, but the compressed file is still there in the repository, in history.
With Git, you never really lose anything; even if you’ve done a filter-branch to re-write history, you’re only a reflog entry away from getting it all back.
Pull request by hand ?
Speed up git/ssh connection by keeping an open connection to the serv
Automatictly take screenshot of website at every commit, to see changes
-
Autocorrect
git config --global help.autocorrect 1
-
Tab-completion
Or you can let bash complete commands for you!
Download this file to your home directory and name it .git-completion.bash.
Add this to your .bash_profile: source ~/.git-completion.bash
- And my pickaxe!
So you can grep through your code base. But what if the code you’re grepping for lives in history? Git allows you to grep through your entire project history quickly and easily using git pickaxe:
git log -S[search term]
git log -Saws_secret_key # did this repo ever have an aws_secret_key?
That will show you all the commits including aws_secret_key. You can see the diff of each commit too by passing the -p flag:
git log -Saws_secret_key -p
- Stripping whitespace
Hey! Don’t you hate when you check in code with trailing whitespace? And then your co-workers stab you to death?
You can have git strip whitespace for you automatically.
First, make a .gitattributes file in your project root with these contents:
- filter=trimWhitespace
This says every file will go through the trimWhitespace filter. You could apply it to ruby files only like this:
*.rb filter=trimWhitespace
Now define the filter:
$ git config filter.trimWhitespace.clean trim_whitespace
Every filter can be run at two different hooks: right after you pull, or right before you push. The smudge filter is for right after pulling and the clean filter is for right before pushing. This says
create a new filter called trimWhitespace
for the “clean” action, run my code through the trim_whitespace utility.
Save this ruby script as trim_whitespace somewhere in your PATH and make it executable:
!/usr/bin/env ruby
lines = STDIN.readlines
lines.each do |line|
puts line.rstrip
end
- How to recover lost data
This is an important one. Here’s the golden rule of git: if you lose data but you checked it in somewhere, you can probably recover it. If you didn’t check it in, you probably can’t. So check in often!
When you make a commit, git takes a snapshot of your repo in that state:
Each commit has a SHA1 hash that you can use to reference the commit. And each commit points to it’s parent:
A “branch” is just a pointer to a commit:
So when you say git checkout master, you’re saying “give me the commit that the master pointer points to”.
Now, let’s say you accidentally do a git reset --hard and you are stuck on an older commit. You look at your log and it looks like you’ve lost a couple of commits! What’s happened? They are there, it’s just that master doesn’t point to them anymore so you can’t get to them:
But they’re still there! And you can get to any commit if you know it’s SHA1 hash! Well lucky for you, there are a couple of ways to figure out the SHA1. One way if to use the reflog:
reflog
Any action you take that updates a branch head will get logged in your reflog. Check it out by running git log -g:
commit ee68d62d4cbac3ffefc38398a63d70e4dd518e7d
Reflog: HEAD@{0} (Aditya Bhargava bluemangroupie@gmail.com)
Reflog message: commit: Finish writing the kernel
Author: Aditya Bhargava bluemangroupie@gmail.com
Date: Tue Aug 13 15:10:55 1991 -0700
Finish writing the kernel
commit 2f9eaea2ce5e6306cb37897417cf63a8d8c63ec4
Reflog: HEAD@{1} (Aditya Bhargava bluemangroupie@gmail.com)
Reflog message: checkout: moving from master to adit/experimental
Author: Linus Torvalds linus@git.com
Date: Tue Aug 13 14:27:36 1991 -0700
CSS Tweaks
Do you see your lost commits in here? If you do, grab the SHA1 of the newest commit, and do:
git branch lost_data [SHA1]
Now the lost_data branch should have all of your lost commits! Merge it into your branch:
git merge lost_data
Ta-da! Lost data recovered!
fsck
Here’s another way:
git fsck --full
This shows you all the objects that aren’t pointed to by another object. One of your commits should be in this list, and you can get the SHA1 hash!