Revista Informática

Git desde Cero: Utilizando Git Subtree

Publicado el 29 agosto 2013 por Codehero @codeheroblog

Bienvenidos a un nuevo capítulo de Git desde cero en este curso hablaremos sobre como agregar, actualizar y utilizar una alternativa a los submódulos de git, llamada subtree en nuestros proyectos. Los comandos a utilizar esta semana serán los siguientes:

  • git subtree (múltiples comandos)
  • git remote add *
  • git fetch

¿Por qué utilizar subtree y no submódulos?

Si recuerdan la semana pasada cuando aprendimos submódulos observamos que pueden existir ciertos problemitas o complejidades cuando se emplea el esquema de submódulos para el manejo de subprojectos. Existen varias razones por las cuales uno podría preferir utilizar subtree (subárbol) por encima de un submódulo, entre las más destacadas se encuentran:

  • Manejo del subtree utiliza prácticamente los mismos comandos básicos que aprendimos en las primeras lecciones.
  • Cuando clonamos un proyecto con un subtree no debemos aplicar más comandos adicionales.
  • Los subtrees no agregan “metadata” adicional al proyecto (.gitmodule).
  • Subtree es soportado por versiones viejas de git antes de la 1.5.2.

De las razones que probablemente no nos agraden tanto, se encuentran las siguientes:

  • Contribuir cambios desde el subtree al proyecto original es un poco más complicado de lo normal.
  • Tener la capacidad para no mezclar código entre el proyecto principal y el subtree queda de parte de nosotros.

¿Cómo se usa un subtree?

El comando o utilidad de subtree viene por defecto incluido en git desde la versión 1.7.11 de Mayo del 2012. Les recomiendo que de encontrarse en una versión más vieja que la antes mencionada actualicen para que disfruten de esta poderosa herramienta.

Existen dos formas básicas para utilizar subárbol, una “rápida” y otra “organizada”. La diferencia entre las dos es la longitud del comando que debemos memorizar. Comencemos por la rápida.

Para esta prueba vamos a utilizar el repositorio de node y express rutas de codehero.co.

¿Cómo agregar el subárbol al proyecto?

$ git subtree add --prefix node_express_subtree https://github.com/codeheroco/nodejs-y-express-rutas master --squash
git fetch https://github.com/codeheroco/nodejs-y-express-rutas master
From https://github.com/codeheroco/nodejs-y-express-rutas
 * branch            master     -> FETCH_HEAD
Added dir 'node_express_subtree'

Con este comando hemos creado una capeta llamada node_express_subtree donde estamos guardando la información del repositorio node y express rutas que se encuentra en la rama master y además solo estamos almacenando localmente el último commit en nuestro ordenador al usar la bandera --squash.

Si observamos el log, podemos apreciar lo que se describió en el párrafo anterior.

$ git log --pretty=format:'%h - %an, %ar : %s' --graph
*   08bddd4 - albertogg, 59 minutes ago : Merge commit '4f34bfe8efc8f797bac71dfcd736cb7fa14efc42' as 'node_express_subtree'
|\
| * 4f34bfe - albertogg, 59 minutes ago : Squashed 'node_express_subtree/' content from commit 0f81501
* 2614422 - albertogg, 7 days ago : Primer commit con un submódulo

¿Qué pasa si semanas después, se han introducido múltiples cambios al proyecto que nosotros tenemos como subproyecto y queremos actualizarlo?

Pues la respuesta es bastante sencilla. Al igual que cuando utilizamos pull para actualizar nuestro proyecto principal hacemos esto pero agregando el subcomando subtree, de la siguiente manera:

$ git subtree pull --prefix node_express_subtree https://github.com/codeheroco/nodejs-y-express-rutas master --squash
From https://github.com/codeheroco/nodejs-y-express-rutas
 * branch            master     -> FETCH_HEAD
Subtree is already at commit 0f815018df127cd663ecc8b89500d5f40f40b9b4.

Como el proyecto node y express rutas no presenta modificaciones el comando nos dice que se encuentra en el commit 0f815018df127cd663ecc8b89500d5f40f40b9b4, es decir en la última versión.

La manera más organizada de utilizar sería agregando en primera mano la ruta remota al proyecto con un “alias” para no tener que recordar el “URL” del mismo. El trabajo posterior a esto es prácticamente lo mismo que se realizó en la manera rápida con ligeras modificaciones.

$ git remote add -f node_express_subtree https://github.com/codeheroco/nodejs-y-express-rutas
Updating node_express_subtree
From https://github.com/codeheroco/nodejs-y-express-rutas
 * [new branch]      master     -> node_express_subtree/master

Si revisamos las ramas remotas que tenemos asociadas al proyecto observamos que node_express_subtree está identificada dentro de la lista.

$ git remote -v
node_express_subtree    https://github.com/codeheroco/nodejs-y-express-rutas (fetch)
node_express_subtree    https://github.com/codeheroco/nodejs-y-express-rutas (push)
origin  [email protected]:codeheroco/tutorial-git.git (fetch)
origin  [email protected]:codeheroco/tutorial-git.git (push)

Ahora agregamos el subárbol al proyecto.

$ git subtree add --prefix node_express_subtree node_express_subtree master --squash

Para actualizar el subárbol

$ git fetch node_express_subtree
$ git subtree pull --prefix node_express_subtree node_express_subtree  master --squash
From https://github.com/codeheroco/nodejs-y-express-rutas
 * branch            master     -> FETCH_HEAD
Subtree is already at commit 0f815018df127cd663ecc8b89500d5f40f40b9b4.

¿Cómo contribuir cambios desde el subtree?

Debemos tener una rama de upstream que debería ser un “fork” del proyecto original al que queremos contribuir en nuestra cuenta o carpeta personal de github (esto únicamente si dicho proyecto se encuentra en github) y agregar su dirección remota.

$ git remote add albertogg-node-express https://github.com/albertogg/nodejs-y-express-rutas

Una vez que tengamos esta dirección remota disponible queda hacer un push a nuestro proyecto y posteriormente hacer un pull-request al proyecto principal.

$ git subtree push --prefix=node_express_subtree albertogg-node-express master

Sé que puede parecer algo confuso, pero realmente es lo que hemos estado trabajado a lo largo de todos estos cursos, únicamente se está agregando el subcomando de git subtree antes del resto de las acciones principales de git.


Conclusión

En este último capítulo y en conjunto con los cursos anteriores hemos adquirido el conocimiento necesario para utilizar subárboles dentro de nuestros proyectos, ya sea para reutilizar nuestro propio código o simplemente agregar una librería externa. Si te surge algún tipo de duda no te detengas y déjanos un comentario, que gustosamente lo responderemos.

¡Hasta la semana entrante!


Volver a la Portada de Logo Paperblog