Aprende git de nuevo, pero bien

De que va esto?

Estructura interna

git cat-file -p <hash>

Estructura interna (2)

Objects

Todos estos objetos se guardan en .git/objects, sin calcular deltas! Siempre que se repita un hash, se considera que el objeto ya está almacenado, y se ahorra tiempo en tráfico de red y disco.

Packs

Todos estos objetos se empaquetan en estructuras .pack, que son las que se comparten por red. Así, el cálculo de deltas es independiente, y se puede optimizar dependiendo de los datos a comprimir.

Estructura interna (3)

Conclusiones

  1. Si solamente se cambia el contenido de un fichero, el resto de blobs quedarán intactos, y también los árboles que no contengan a ese fichero o superiores.
  2. Si se cambia el nombre del autor, o el parent, o la fecha, o el msg, cambia el commit.
  3. Un tree hash representa el estado completo del working dir, unequívocamente.
  4. Un commit representa la historia completa hasta el momento del commit, incluído.
  5. Casi todas las operaciones van a cambiar el hash del commit, estropeando las comunicaciones por red.
  6. No se guardan fechas de modificación de ficheros.

Los mejores comandos de git

git format-patch

git am

git apply

Vas a querer darme las gracias al final de la charla.

Está mi email en la última diapositiva.

Me gusta el chocolate.

git format-patch

  • Genera unos ficheros que representan tus commits, normalmente un fichero por commit.

  • Puedes indicar un commit concreto o un rango de commits. Normalmente se le solicita que genere ficheros desde un commit concreto.

  • Esto es realmente lo mismo que un pull request. Old-school. Más flexible y fácil de utilizar. Proyectos enormes aún lo usan.

  • Los ficheros son texto plano: portables, editables.

  • Luego puedes aplicarlos en cualquier otro commit de tu repositorio o de otro repositorio.

git format-patch (ejemplo)

Genera un parche con un commit concreto

[g.indalecio@ctdesk235 unpack]$ git format-patch origin/master
0001-Fix-typo.patch

Mira el contenido

From e5beabd15a9e8136e3cf110ae28f05ca55227a95 Mon Sep 17 00:00:00 2001
From: Guillermo Indalecio Fernandez <guillermobox@gmail.com>
Date: Fri, 5 Dec 2014 20:25:37 +0100
Subject: [PATCH] Fix typo

---
 unpack.py | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/unpack.py b/unpack.py
index db502ba..fe4c780 100644
--- a/unpack.py
+++ b/unpack.py
@@ -43,7 +43,7 @@ class FileDriver(object):
         return target

     def extract(self, options):
-        command = self.extract_command(options)
+        command = self._extract_command(options)

         if not self.parent():
             if self.path:
-- 
1.9.1

git am

  • Aplica el parche en tu HEAD
  • Mantiene la fecha original de autor, y el nombre. Perfecto para compartir código. Perfecto para mover código de una rama a otra.
  • El parche no se elimina, así que puedes probar a aplicarlo en Detached Head, y si no te gusta el resultado, pasar de todo.
  • Si un parche no se aplica correctamente, da un merge conflict.
  • Las branches se pueden recolocar después, utilizando:

    git branch -f

git am (ejemplo)

Cambia a otra parte del código

[guille@localhost unpack]$ git checkout 1d658ca
HEAD is now at 1d658ca... Added gitignore

Aplica el parche

[guille@localhost unpack]$ git am 0001-Fix-typo.patch 
Applying: Fix typo

Mira el resultado

* 50dbf9a Fix typo (3 minutes ago)
| * 565065d Big refactor on progress (32 hours ago)
| * e5beabd Fix typo (12 days ago)
| * d6c7914 Parse options with optparse (3 weeks ago)
|/
* 1d658ca Added gitignore (3 weeks ago)
* 61a4f78 Always read file after creating Driver object (4 weeks ago)
* 632a0f1 First version (4 weeks ago)

git apply

  • Solamente aplica el parche al working tree, no crea commits.
  • Pierdes la información de autor y demás.
  • No crea commits, es cómodo para ver código.
  • Se llama como git am, utiliza los mismos parches.

Let the magic begin!

Rebase

  • Sirve para mover commits, como si los hubieses escrito empezando en otro estado.
  • Supongamos que hice un trabajo a partir de v1.0 y quiero aplicarlos a partir de v2.0.
  • La diferencia es que con rebase, ademas se recoloca el puntero de branch.
git format-patch v1.0
git checkout v2.0
git am *.patch

Rebase interactivo

  • Sirve para reescribir la historia, elimiando commits, uniendolos, cambiando mensajes.
  • Supongamos que hice trabajo a partir de v1.0, quiero editar los commits.
  • De nuevo, rebase interactivo es destructivo, cambia el puntero del branch.
git format-patch v1.0
vim *.patch
git am *.patch

cherry-pick

  • Toma un commit concreto de un branch, aplícalo en el HEAD.
  • Supongamos que hay el commit 1234567 que tiene un cambio que me interesa, estoy trabajando en v1.0 y quiero aplicarlo:
git format-patch 1234567^..1234567
git am *.patch

Pull request

  • Trabajamos en una rama local (master) y queremos compartir cambios respecto de la rama remota (origin/master).
  • Creamos los ficheros, y los compartimos:
git format-patch origin/master
# enviamos un email con los ficheros, o se comparten de otra manera
# otro developer hace lo siguiente
git am *.patch

Últimos consejos

Foza todo lo que quieras en el repo local. Destrúyelo. No tengas piedad. Una tarde fedellando con los comandos básicos de git (diff, show, status, branch, merge, format-patch) y ya no tendrás miedo.

Últimos consejos

Móntate un .gitconfig decente. Compártelo.

Últimos consejos

Los branches son super útiles. Manejándolos bien, la interacción con remotos, hooks y demás se entiende mejor. Pensad que son punteros, literalmente. Buscad en .git/refs/heads/.

Últimos consejos

Entender la estructura interna (commits, hashes, branches) lo es todo para comprender lo que sucede en cualquier otro caso. Échale un vistazo a los links de la siguiente diapositiva.

Links!

Algunos links de youtube para continuar aprendiendo git internals.

  1. Becoming a Git Master
  2. Git From the Bits Up
  3. Advanced git Tutorial: Linus Torvalds
  4. Becoming a Git Master
  5. Advanced Git - JavaZone

Extra!

Esta presentación está escrita en cleaver.

Ahora se lleva esto de las presentaciones HTML modernas.

  • Escribes markdown, sale html (mejor que LaTeX).
  • Más portable que un pdf
  • Más más más portable que un powerpoint
  • Quieres vídeos? No problem!