Introducción a Control de Versiones con Git

Git es un software de control de versiones, como lo son, por ejemplo: CVS, SVN o VSS.

Git fue diseñado por Torvalds con el objetivo de llevar el kernel de Linux en un repositorio confiable o como el propio Linus dijo “rápido, muy rápido, fácil, bonito y espectacular”.

Una de las referencias de Linus en el diseño de git fue CVS, pero como un ejemplo de lo que NO HAY QUE HACER, pues lo sufrió durante siete años en una compañía y allí aprendió a odiarlo con pasión. Linus tampoco quizo probar con SVN, pues el lema de SVN era “hacer CVS bien”, y eso ya lo condenaba, pues no había forma de hacer a CVS bien.

Dejando de lado las anécdotas anteriores, Git es utilizado por la mayoría de los desarrollos open source de la actualidad:

Para quienes no saben lo que es un software control de versiones, básicamente, se puede resumir en un servidor donde se suben los archivos de un proyecto y a medida que se van modificando se van registrando y documentando estos cambios (versionando). En principio la idea es sencilla y más de un improvisado podría cuestionar el uso del mismo. No obstante, en la medida que un proyecto crece, la cantidad de archivos aumenta, los cambios y la cantidad de programadores también, resulta totalmente insostenible trabajar sin un control de versiones.

Trabajar sin control de versiones implica no saber donde está el último fuente, arrancar trabajando de una versión anterior y perderse los cambios de la que realmente era la última, no saber cuales son y quien realizó los cambios, no deshacer fácilmente los cambios realizados (downgrade), o no poder facilitar la transición a una versión totalmente nueva de un proyecto manteniendo el soporte a la anterior.

Una cosa más, la mayoría de los IDEs actuales tienen integración con Git, o si no la tienen, tienen algún plugin para hacerlo. Ahora, si no utilizas un IDE, tu caso es un poco más delicado 😉

Sin más preámbulos, vamos a la práctica. En mis prácticas no utilizaré IDE, utilizaré un único archivo fuente y utilizaré el mismo equipo (dotado con Ubuntu Linux) como repositorio y cliente. Por lo tanto, primero, descargaré lo necesario: apt-get install git-core

Primer paso, en rol de “servidor”, creo el repositorio:

  1. $ git init mi_repositorio

Initialized empty Git repository in /home/luciano/mi_repositorio/.git/

En caso de no pasar el último argumento, en mi caso: mi_repositorio, el repositorio se inicializará en el directorio actual.

Ahora, en rol de “cliente”, supongamos que tengo mis desarrollos en este path:

  1. $ pwd
  2. /home/luciano/desarrollo

Si quiero “sincronizar” mi directorio de desarrollo con el repositorio de git, debe hacer un “clone”, así:

  1. $ git clone /home/luciano/mi_repositorio
  2. Cloning into luciano...
  3. done.
  4. warning: You appear to have cloned an empty repository.

Estamos arrancando de cero, por lo tanto el warning es ignorable 😉

El argumento que cambiará del “clone” en el caso que el repositorio se encuentre en otro servidor, será el path del repositorio, que deberá ser antecedido por usuario@host, por ejemplo:

  1. git clone username@host:/path/to/repository

Un repositorio administrador por git cuenta con lo que se denominan tres árboles, el primero, el directorio local (directorio de trabajo). El segundo es un “directorio intermedio” a donde van a parar los archivos que se agregan al proyecto, finalmente el “HEAD” donde reside la última versión confirmada. Ahora, veremos como agregar un archivo al repositorio y como “commitearlo”.

Primero, creo un archivo fuente en mi directorio de trabajo:

  1. $ pwd
  2. /home/luciano/desarrollo
  3. $ cd mi_repositorio
  4. $ touch holamundo.c

Observen lo siguiente, no hay nada que decir:

  1. $ git status
  2. # On branch master
  3. #
  4. # Initial commit
  5. #
  6. # Untracked files:
  7. # (use "git add ..." to include in what will be committed)
  8. #
  9. # holamundo.c
  10. nothing added to commit but untracked files present (use "git add" to track)

Ahora, agrego el archivo al repositorio:

  1. $ git add holamundo.c

Finalmente, commit:

  1. $ git commit -m "revision inicial" holamundo.c
  2. [master (root-commit) 2b983d9] revision inicial
  3. Committer: Luciano

Ahora, el estado nuevamente:

  1. $ git status
  2. # On branch master
  3. nothing to commit (working directory clean)

Un último comentario acerca de lo último, el commit quedó registrado con mi usuario (Committer) y mi host luciano@lucid.

Una opción, antes de lo anterior, es setear esos valores de la siguiente forma:

  1. $ git config –global user.name “Juan Del Rio”
  2. $ git config –global user.email juan@delrio.com

Ahora, modifico el fuente y observo el estado de nuevo:

  1. $ echo "/* holamundo program */" > holamundo.c
  2.  
  3. $ git status
  4. # On branch master
  5. # Changes not staged for commit:
  6. # (use "git add ..." to update what will be committed)
  7. # (use "git checkout -- ..." to discard changes in working directory)
  8. #
  9. # modified: holamundo.c
  10. #
  11. no changes added to commit (use "git add" and/or "git commit -a")

Hay cambios sin “commitear”, por lo tanto, hago un nuevo commit:

  1. $ git commit -m "agregue encabezado" holamundo.c
  2.  
  3. $ git status
  4. # On branch master
  5. nothing to commit (working directory clean)

Para terminar (por ahora), si elimino el archivo:

  1. $ rm holamundo.c
  2.  
  3. $ git status
  4. # On branch master
  5. # Changes not staged for commit:
  6. # (use "git add/rm ..." to update what will be committed)
  7. # (use "git checkout -- ..." to discard changes in working directory)
  8. #
  9. # deleted: holamundo.c
  10. #
  11. no changes added to commit (use "git add" and/or "git commit -a")

Por lo tanto debo:

  1. $ git rm holamundo.c
  2. $ git commit -m "bye bye adios" holamundo.c
  3. $ git status
  4. # On branch master
  5. nothing to commit (working directory clean)

Por hoy esto es todo, a pesar de que es muy poco y aún no es lo suficiente para compreder las virtudes de un sistema de control de versiones, basta para saber como hacer “altas, bajas y modificaciones”.

En la próxima entrega, quedo comprometido en tratar los “push” a un servidor remoto, trabajar con “branches”, hacer “merges” y un poco más.

Tags: , , , , , ,


Leave a Reply

Your email address will not be published. Required fields are marked *