git: adicionar arquivos por pedaço

Freqüentemente, eu só quero confirmar algumas partes de um arquivo e não outras. Talvez eu tenha uma mudança na parte superior que está pronta para ser comprometida, mas uma na parte inferior quero adiar.

Para casos como este, basta usar

git add -p

E o git perguntará interativamente sobre cada pedaço:

$ git add -p
diff
--git a/chance.js b/chance.js
index ec32b52
..cf4ddbb 100644
--- a/chance.js
+++ b/chance.js
@@ -143,6 +143,7 @@

Chance.prototype.integer = function (options) {
var num, range;
+ // This is a useless change, do not commit ;)

options
= initOptions(options, {min : MIN_INT, max : MAX_INT});

Stage this hunk [y,n,q,a,d,/,e,?]?

Ele mostrará uma diferença para cada um e você pode adicioná-la ou ignorá-la.

Escolher a opção ?abrirá o menu de ajuda, que colei abaixo para sua conveniência (grite para @bobz pela sugestão!)

Stage this hunk [y,n,q,a,d,/,e,?]? ?
y
- stage this hunk
n
- do not stage this hunk
q
- quit; do not stage this hunk nor any of the remaining ones
a
- stage this hunk and all later hunks in the file
d
- do not stage this hunk nor any of the later hunks in the file
g
- select a hunk to go to
/ - search for a hunk matching the given regex
j
- leave this hunk undecided, see next undecided hunk
J
- leave this hunk undecided, see next hunk
k
- leave this hunk undecided, see previous undecided hunk
K
- leave this hunk undecided, see previous hunk
s
- split the current hunk into smaller hunks
e
- manually edit the current hunk
? - print help

Você verá que existem algumas opções ocultas que podem ser bastante úteis!

Eu o uso basicamente sempre que faço commit, então adicionei um alias para isso no meu .gitconfig:

[alias]
a
= add -p

Então eu posso apenas usar

git a

E ele vai me perguntar, pedaço por pedaço, o que eu quero cometer.

Isso não é apenas útil para preparar apenas parte de um arquivo, mas ajuda ao trabalhar com uma equipe, pois o forçará a revisar cada alteração antes de adicioná-la.

Usando isso, posso ter certeza de que nunca sou o cara que acidentalmente comete o conflito de mesclagem 🙂