Git BásicoTutoriales

Tutorial Git – Fundamentos y Órdenes Básicas

Continuamos con nuestra serie sobre Git. En este artículo ya entraremos en la parte “entretenida”, abordaremos los fundamentos y esas órdenes básicas que todos debemos dominar en la gestión de nuestros proyectos. Los comandos que veremos serán aquellos más frecuentes, esos que necesitarás para hacer la gran mayoría de las operaciones.

Aprenderemos también a configurar e inicializar un repositorio, comenzar y detener el seguimiento de archivos, preparar (stage) y confirmar (commit) cambios. Configuraremos Git para que ignore ciertos archivos y patrones, cómo deshacer errores rápida y fácilmente, cómo navegar por la historia de tu proyecto y ver cambios entre confirmaciones, y cómo enviar (push) y recibir (pull) de repositorios remotos.

Damos como un hecho que el lector ya tiene instalado Git y domina los términos teóricos y básicos que hemos comentado en nuestro anterior artículo sobre la instalación y configuración inicial de Git.

Trabajando con repositorios locales

Los ejemplos los veremos bajo un espacio de trabajo, digamos que tenemos una carpeta de nombre Project:

…dentro de la cual tendremos a su vez otras carpetas, cada una asociada a un proyecto distinto:

Inicializando el repositorio

Estas carpetas corresponderían a un repositorio local o a varios repositorios, dicho esto vamos a asumir que nuestro proyecto de nombre SomeApp ya existe:

…es una aplicación creada con Swift Package Manager pero que no ha sido inicializada con Git, es decir, que aún no estamos llevando el control de versiones sobre nuestra aplicación, en este punto si modificamos algo no podremos ir al estado anterior.

git init

Pues precisamente esto es lo que haremos con el siguiente comando:

git init

Puedes copiar el comando anterior aquí:

Acabamos de inicializar el proyecto, creando una carpeta en la raíz del mismo, de nombre .git. Si tienen conocimientos de Unix o son lectores de este sitio web ya sabrán que si el nombre de una carpeta inicia con un punto, es que se encuentra oculta, así que para visualizarla pasaremos el parámetro “A” al comando ls:

En la carpeta .git es donde se almacena prácticamente toda la información relacionada con nuestro repositorio así que debemos tener mucho cuidado de no borrarla accidentalmente, básicamente esta es la razón por la cual se encuentra oculta.

Aunque ya hemos inicializado nuestro repositorio aún no estamos dando seguimiento a ningún archivo y esto lo podemos comprobar con el siguiente comando:

git status

Puedes copiar el comando anterior aquí:

Luego de verificar que en efecto no tenemos ningún archivo en nuestro repositorio esto será lo próximo a ejecutar:

git add

Puedes copiar el comando anterior aquí:

Si observan verán que tenemos un fichero oculto, me refiero a .gitignore. Mediante este fichero declaramos ante Git aquellos archivos que deseamos ignorar, esos ficheros que no deseamos gestionar en el tiempo, por ejemplo contenido propio del uso del proyecto y que se autogenera cada vez que lo usamos: archivos de cache, logs… etc.

Confirmando los cambios

En este punto, luego de añadir los ficheros de nuestro proyecto al repositorio Git, lo siguiente sería crear una pauta en el tiempo.

git commit

Para tomar una instantánea del estado actual y esto lo hacemos mediante el comando git commit:

git commit

Puedes copiar el comando anterior aquí:

Aunque quizás puede ser algo obvio les comento sobre el parámetro -m, el cual hace referencia al mensaje que hemos especificado y que viene a describir el motivo del snapshot que estamos creando.

Si en este punto ejecutamos:

…veremos que nos encontramos en el branch master (en la rama master o principal) y también se nos informa que no hay cambios que gestionar, que el árbol de trabajo se encuentra limpio. Básicamente esto lo que nos quiere decir es que desde el último commit ningún fichero ha sufrido cambio alguno.

Creo importante evocar la lógica del lector y razonar sobre el uso del commit, veamos esta funcionalidad de Git no como algo a ejecutar cada vez que modificamos un archivo en plan automático, más bien la tendremos en cuenta cada vez que implementemos una serie de cambios importantes o por ejemplo al final de cada día, esto es decisión de cada persona, solo quería puntualizar que estos eventos sean tomados con cierta cordura para que nuestro historial sea realmente funcional y sobre todo informativo.

El Estado de los Archivos (Ciclo de Vida)

Para continuar con el tutorial debemos de comprender el estado en el que se pueden encontrar los archivos que forman parte de nuestro repositorio, el ciclo de vida de los mismos.

git files states

Digamos que cada archivo en nuestro proyecto de trabajo puede estar en uno de estos dos estados: bajo seguimiento (tracked), o sin seguimiento (untracked). Los archivos bajo seguimiento son aquellos que ya existían en el último commit; estos pueden estar sin modificar (unmodified), modificados (modified), o preparados (staged). Los archivos sin seguimiento son todos los demás, cualquier archivo que no estuviese en el último commit ni tampoco en el área de preparación (staging area).

git status

Para comprender los estados de una mejor manera veamos un ejemplo: añadiremos un archivo nuevo al proyecto con el que hemos estado trabajando y modificaremos otro ya existente:

A este archivo y solamente con la clara intención del ejemplo le agregaré el siguiente código:

Hasta el momento hemos usado el comando git status de manera intuitiva, este nos ayuda a comprobar el estado de nuestro repositorio y los archivos dentro de este. A continuación volveremos a usar este comando, luego de añadir el nuevo archivo:

git status with file customer.swift untracked

En la salida en pantalla se nos informa sobre un archivo al que no se le está dando seguimiento, es decir que estaría como untracked y por ende no forma parte de ninguno de los estado del anterior diagrama. Continuamos modificando el archivo main.swift para hacer uso de la estructura que acabamos de crear:

…y así quedará el archivo luego de editar. Acto seguido verificamos nuevamente:

git status main.swift modified and customer.swift untracked

Podemos observar que ahora Git ha detectado un cambio en el archivo main.swift, que ya existía y se encontraba en el estado unmodified (no modificado) y luego de editarlo pasó al estado de modified (modificado) tal y como podemos observar en el diagrama. También nos comenta que los cambios no están listos o preparados (staged) para una confirmación (commit) hacia el repositorio. En la última sección de archivos sin seguimiento (untracked files) se vuelve a mostrar el nuevo fichero de código fuente que agregamos.

Antes de continuar compilamos y ejecutamos nuestro proyecto:

swift build SomeApp

Si lo que hemos hecho en esta imagen te resulta de alguna manera desconocido o te llama la atención, quizás el aspecto de la terminal o tal vez los comandos que hemos utilizado pues te invito a que leas nuestros artículos donde configuramos nuestro entorno de programación para plataformas Apple y también aquel donde aprendemos a usar el gestor de paquetes de Swift (Swift Package Manager).

Ignorando archivos

A menudo, nos encontraremos con cierta clase de archivos que no deseamos agregar a nuestro repositorio y por ende tampoco queremos que Git nos muestre que estos no se encuentran bajo seguimiento. Generalmente se trata de ficheros generados automáticamente, como archivos de registro o aquellos producidos por el sistema de compilación. En tales casos, podremos crear un archivo oculto .gitignore que liste patrones que coincidan con el nombre de estos ficheros que deseamos ignorar .

Un ejemplo del contenido de un archivo .gitignore pudiera ser algo tan simple como una expresión regular:

…dentro de este archivo (que crea SwiftPM automáticamente) tenemos el clásico fichero oculto .DS_Store que genera macOS, la carpeta .build donde se encuentran los binarios ya compilados de nuestro proyecto, los paquetes y ficheros asociados a Xcode que pueden generarse automáticamente mediante el comando swift.

Las principales reglas que aplican dentro del fichero .gitignore son las siguientes:

  • Las líneas en blanco o aquellas que comiencen con el símbolo de número (“#”) son ignoradas (ideal para añadir un comentario).
  • Los patrones que hayamos especificado en este archivo (ubicado en la raíz del proyecto) tienen un alcance global, y se aplican de manera recursiva a través de toda la estructura de ficheros y carpetas de nuestro proyecto.
  • Podemos evitar un comportamiento recursivo comenzando nuestro patrón con un símbolo de slash (“/”).
  • Podemos declarar un símbolo de slash (“/”) al final de un patrón con el objetivo de especificar una carpeta.
  • También podemos negar un patrón comenzando con el símbolo de exclamación final (“!”).

…claramente el resto de reglas que ya pertenecerían a como escribir expresiones regulares, algo que ya deberíamos de conocer.

Siguiendo estas reglas y analizando el ejemplo que hemos visto, ya entendemos por qué hay tres líneas que comienzan con un símbolo de slash (“/”), y es que como estas carpetas se encuentran en la raíz del proyecto y solamente existe una carpeta con este nombre, pues no es necesario que Git recorra todo el árbol de directorios del proyecto en busca de coincidencias que no encontrará.

Añadiendo archivos al índice

Luego de ver que todo funciona correctamente nos prepararemos para confirmar los cambios efectuados. Recordemos que tenemos dos eventualidades: un fichero nuevo y otro modificado, pues resulta que estos dos estados los procesaremos con un comando que hemos venido usando hasta ahora.

git add

Me refiero a la orden git add, la cual no solo es útil para añadir archivos al área de archivos bajo seguimiento, también nos resulta útil para llevar archivos desde el estado de modified hasta staged, incluso para marcar resuelto o solucionado aquellos archivos que anteriormente se han encontrado en conflicto, y cuando digo conflicto me refiero a un merge conflict (conflicto de fusión) una operación que veremos más adelante.

Creo válida la recomendación que nos dan en la documentación oficial de Git y es que pensemos en git add como esa herramienta que nos permite alistar archivos hacia la próxima confirmación y no solo como: “añade este archivo al proyecto”.

Dicho esto ejecutamos el siguiente comando:

….luego verificamos nuevamente:

git status customer.swift new file and main.swift modified

Ahora ya tenemos a nuestros dos archivos dentro de la sección Changes to be committed (Cambios ha ser confirmados) y esto lo que quiere decir es que ya podemos hacer commit y con esto marcar un hito, tomar un snapshot del progreso actual.

Cambios de último minuto

Precisamente lo que haremos es confirmar nuestros cambios: pero… recién nos percatamos de un cambio que queremos añadir a nuestro código. Vamos a agregar una sobrecarga a nuestro tipo Customer a favor de poder comparar si un objeto es igual (==) a otro o desigual (!=).

Primero editaremos nuestro fichero de código fuente main.swift:

…luego customer.swift:

Ambos archivos han quedado de esta manera, compilamos y ejecutamos:

swift build SomeApp and swift run

Al ver que todo funciona bien y ya seguros de que no hay más cambios que aplicar por el momento pues verificamos nuevamente el estado de nuestro repositorio:

git status changes to be committed and changes not staged for commit

Sorpresa! ahora tenemos los mismos archivos en un estado (Changes to be committed) y en otro (Changes not staged for commit) al mismo tiempo. Lo que sucede es que cuando hacemos git add se toma una instantánea del archivo en ese momento, y se crea una copia de su contenido en el estado nuevo hacia el cual se ha movido (staged). Si sucede algo como lo que hemos simulado, al modificar los archivos estos entran automáticamente en el estado de modified como producto de los nuevos cambios, por ende dentro del repositorio tenemos dos versiones del mismo archivo, aquella que se encontraba lista para confirmar y otra producto de la sobrecarga que tuvimos que aplicar a nuestro tipo Customer.

En este punto podemos hacer dos cosas, la primera: si la versión que se encuentra lista para hacer commit representa un momento importante en el progreso, quizás porque agregamos dependencias nuevas, algunos assets, etc… pues hacemos un commit y luego gestionamos las nuevas versiones actualmente en estado modified haciendo git add. La segunda opción sería hacer git add directamente ya que los nuevos cambios pueden fusionarse perfectamente con la versión anterior ya que no te interesa diferenciar en el historial estos dos momentos.

Visualizando diferencias

Pero, ¿qué sucede si antes de decidir cual de las dos opciones ejecutar queremos ir más allá y comprobar cuales son las diferencias? Pues que es completamente posible y lo podemos lograr con el comando git diff, de esta manera:

…la salida en pantalla sería:

git diff at top

…dada lo extenso de la salida podemos continuar visualizando presionando la tecla de flecha hacia abajo (down arrow key) para ir línea a línea o sencillamente la barra espaciadora para dar saltos de página. La segunda página sería:

git diff at bottom

Creo que la salida en pantalla es bastante intuitiva, ya que más allá de ser nosotros los que hemos escrito el código y aplicamos los cambios, creo que lo más efectivo es el sistema de colores. El color rojo nos informa de que esa línea ha sido removida por la versión siguiente en color verde. Si analizamos la primera imagen nos percatamos de que la diferencia entre las dos línea reside en el carácter de nueva línea (\n) que hemos añadido a favor de tener una salida en pantalla más legible. Luego de estas viene un bloque bastante grande en color verde dándonos a entender que fue añadido ya que no lo precede otro bloque de color rojo como sí ocurre en la segunda imagen, donde se puede observar que cambiamos de newCustomer hacia paco y donde también actualizamos la orden print y agregamos al final otro bloque de código nuevo. Luego de contrastar las diferencias presionando la tecla q podemos salir de este modo de visualización y regresar al prompt del terminal.

Nosotros en este tutorial abogaremos por el último caso que vimos anteriormente, fusionaremos ambos estados para acto seguido hacer commit:

git add customer.swift and main.swift

Como podemos visualizar en la salida en pantalla el diferencial que teníamos se ha fusionado en la versión actual ya lista para confirmar:

git commit

…acto seguido verificamos el estado del repositorio y en efecto ya no tenemos novedades.

Quizás se han dado cuenta, pero aún así me gustaría aclarar que git diff no muestra los cambios desde el último commit, solo aquellos que están en estado unstaged, toma esta referencia sobre los cambios que acabamos de efectuar nos muestra el contraste, una vez que confirmamos las modificaciones ya esto se pierde y si ejecutamos git diff nuevamente no obtendremos una salida, bueno técnicamente sí, pero esta se mostrará vacía.

Obviando el área de Staging

Aunque puede ser increíblemente útil hacer commits exactamente como lo queremos, el área de preparación (Staging) añade un paso de complejidad que en ocaciones no es necesario para nuestro flujo de trabajo. Si este es el caso o es una ocasión particular donde deseamos omitir el área de preparación, podemos utilizar un simple atajo: agregando el parámetro -a al comando git commit, Git procesa automáticamente todos los archivos a los que ya les veníamos dando seguimiento antes de la última confirmación, es decir que los establece a todos en la etapa de Staged permitiendo así omitir el paso asociado a git add.

Eliminando archivos

Si necesitamos remover un archivo de Git, debemos eliminarlo de sus archivos rastreados (más exactamente, eliminarlo del área de preparación (Staging Area)) y luego confirmarlo.

git rm

El comando git rm <file> nos ayuda con esto, y también elimina el archivo del directorio de trabajo para que no lo vea como un archivo sin seguimiento la próxima vez.

Si por el contrario eliminamos el archivo de nuestro directorio de trabajo (en nuestro caso lo hemos movido fuera de este), aparecerá en el área “Cambios no preparados para confirmación” (Changes not staged for commit) de la salida en pantalla tras ejecutar git status:

moving files outside git repository

…para corregir esto ejecutamos el comando:

git rm customer.swift

…acto seguido al comprobar vemos que ha cambiado de color, confirmamos los datos y todo bien.

Moviendo y renombrando archivos

Otra acción que frecuentemente ejecutamos sobre archivos y carpetas es aquella donde los movemos o renombramos. Si movemos un archivo fuera del ámbito del repositorio a los ojos de Git hemos eliminado el archivo ya que este ha perdido toda referencia sobre el mismo, pero ¿qué sucedería si renombramos un fichero de código fuente?

git mv

No ocurriría nada trágico, ya que Git cuenta también con esta opción, el comando git mv nos permite renombrar o mover un fichero dentro del ámbito del repositorio, de esta manera:

git mv customer.swift

Podemos observar como nos ha renombrado el fichero a nivel de sistema de archivos y ya solo nos queda confirmar los cambios con un commit.

Visualizando el historial de confirmaciones

Después de haber creado varias confirmaciones, los más probablemente es que necesitemos mirar hacia atrás para ver la evolución o consultar cierta fecha o dato del commit.

git log

La herramienta más básica y poderosa para hacer esto es el comando git log. Al ejecutar este comando obtenemos una lista de todas las confirmaciones, donde cada una de estas viene acompañada de la información más relevante sobre la misma.

git log at SomeApp

El identificador único, el autor, la fecha y la hora, así como la descripción.

  • El autor obviamente es aquel que ejecutó la confirmación.
  • La fecha y hora hace referencia al momento exacto cuando se ejecutó.
  • La descripción es el mensaje que especificamos mediante el parámetro -m.
  • El identificador de confirmación (commit ID) es un número o hash creado en base SHA-1 a partir de datos propios de la confirmación, tales como: usuario y correo electrónico, fecha, descripción incluso se tiene en cuenta el identificador del commit anterior a este, en caso de existir.

De forma predeterminada (sin argumentos), git log enumera las confirmaciones hechas en el repositorio en orden cronológico inverso, es decir, las confirmaciones más recientes aparecen primero. También contamos con un gran número y variedad de opciones para el comando git log, prácticamente hay un comando para cada necesidad que se nos presente.

Entre las opciones más útiles tenemos el parámetro -p el cual nos muestra las diferencias introducidas en cada confirmación. También puede limitar el número de entradas que se muestran, como por ejemplo al especificar -2 para mostrar solo las dos últimas confirmaciones. Otra que puede también brindarnos información es –stat que nos imprime en pantalla una pequeña estadística donde se incluyen los ficheros modificados y la cantidad de líneas añadidas o eliminadas. Lo mejor de estas opciones es que las podemos concatenar todas si así lo deseamos:

git log -p -2 --stat

Pueden copiar el comando anterior aquí:

Al ejecutar este comando podremos constatar como ahora tenemos mucha más información que antes, contamos con los datos que ya habíamos visto más la salida proveniente de diff producto de la opción -p, por último si proseguimos hacia abajo en esta vista llegamos al final, aquí es donde se encuentra el otro commit (especificamos el parámetro -2).

Otra opción realmente útil que es –pretty. Esta opción cambia el formato de salida en pantalla a partir de algunas configuraciones ya preconstruidas. La configuración online simplifica cada confirmación en una sola línea, lo cual es útil si está analizando o buscando un commit específico entre cientos de otras confirmaciones. Además tenemos las configuraciones short, full y fuller las cuales muestran aproximadamente el mismo formato pero con menos o más información, respectivamente:

…también:

Hay muchas más configuraciones de aplicar sobre la opción –pretty, pero estas las veremos cuando entremos en la categoría de Git Avanzado. Dicho esto sugiero que te suscribas a nuestra lista y así estés al día con todas nuestras publicaciones.

Deshacer acciones

En cualquier etapa de nuestro proyecto sin dudas nos encontraremos con la necesidad de deshacer algo que hemos hecho. Dicho esto, veamos algunas herramientas básicas que nos permitirán deshacer esos cambios que en ocasiones vienen seguidos de un puñetazo en la mesa. Pero no sin antes hacer un llamado de atención:

Tengamos mucho cuidado con aquello que deseamos deshacer y sobre todo en la manera en que pensamos que podemos hacerlo, ya que esta acción puede no ser revertible. Como la propia documentación oficial de Git informa: esta es una de las pocas áreas en Git donde puedes perder algo de trabajo si lo haces mal.

Uno de los casos más comunes donde necesitamos deshacer alguna acción es aquel donde hemos ejecutado un commit demasiado pronto o hemos olvidado de añadir algún archivo que no se encontraba bajo seguimiento, o sencillamente hemos cometido algún error al redactar el mensaje asociado al commit.

git commit –amend

Ahora, si deseamos deshacer una confirmación, primero necesitamos ejecutar todas esas acciones que olvidamos realizar, añadirlas al área de preparación y entonces volver a confirmar, pero esta vez, utilizando la opción –amend.

Supongamos entonces que hemos olvidado añadir cierto comentario al inicio de nuestro fichero customer.swift, lo abrimos y añadimos el comentario:

…salvamos los cambios y acto seguido ejecutamos git status:

…visualizamos el historial de confirmaciones, y específicamente nos enfocamos en el último que ejecutamos y que deseamos deshacer:

Tomaré la idea del mensaje y la modificaré un poco dado el cambio que hemos aplicado:

git commit amend

Puedes copiar el comando anterior aquí:

Si ahora ejecutamos git log veremos como el último commit ha sido sustituido por el que acabamos de crear.

git reset HEAD

En las siguientes dos secciones comentaremos cómo trabajar con nuestra área de preparación (staging area) y los cambios en el directorio de trabajo. Por ejemplo, digamos que hemos cambiado dos archivos y deseamos enviarlos como dos cambios por separado, pero accidentalmente ejecutamos:

…y los añadimos al área de preparación. ¿Cómo eliminar del área de preparación a uno de los dos? Pues el propio comando git status nos recuerda como lograr esto. Nuevamente vamos a imaginar que hemos modificado nuestro archivo README.md y crearemos uno nuevo llamado CONTRIBUTING.md al cual también agregaremos un texto de ejemplo:

…nos pasamos al directorio raíz del proyecto que es donde se encuentran estos archivos y agregamos accidentalmente los dos:

git add readme.md and contributing.md

Como podemos observar en la propia salida en pantalla, nos ayudan con información acerca de casos como estos que estamos analizando. Recordemos que nosotros queremos separar estos dos archivos en dos commit diferentes así que debemos eliminar uno de estos dos archivos del área de preparación, siguiendo el consejo del propio Git ejecutamos:

git reset head

Luego de hacer esto ya podemos ejecutar las respectivas confirmaciones, una para cada uno de estos archivos.

git checkout

Otro caso donde es bastante frecuente deshacer los cambios es cuando luego de haber confirmado los últimos cambios nos percatamos, en ese momento o después, de que las modificaciones sobre cierto archivos no eran las correctas o no fueron del todo acertadas.

Vamos a suponer que hemos modificado mucho dentro del archivo CONTRIBUTING.md, nos hemos enrollado demasiado y aparentemente todo está genial ahora, salvamos el fichero y ejecutamos git status:

…pero de pronto nos interesa retornar a la versión anterior a todas estas modificaciones, pues en la propia salida en pantalla de git status nos ayudan con esto, solamente tendríamos que hacer lo siguiente:

…y con esto ya sería suficiente. Si por alguna razón quisiéramos mantener estos cambios y al mismo tiempo recuperar la versión antigua, creo que deberíamos pensar seriamente en gestionar estos desde varias ramas (branches), pero esto es algo que veremos en un próximo artículo.

Trabajando con Repositorios Remotos

Para poder colaborar en cualquier proyecto en Git, es fundamental una correcta gestión de repositorios remotos. Estos repositorios son versiones de proyectos propios o ajenos que se encuentran alojadas en Internet. Podemos tener varios de ellos, cada uno de los cuales generalmente es de solo lectura o de lectura y escritura para nosotros lo propietarios de estos.

Colaborar con otros implica administrar estos repositorios remotos, extraer (pull) y agregar (push) datos de ellos cada vez que sea necesario compartir el trabajo. La administración de repositorios remotos incluye el dominio sobre tareas tales como: agregar y eliminar repositorios remotos, gestionar ramas (branches) remotas y definirlas como rastreadas (tracked) o no, y más.

Veamos a continuación algunas de estas habilidades de administración remota, las más básicas y de uso diario.

¿Qué es GitHub?

GitHub es un espacio comunitario, una plataforma web que trabaja de la mano con Git donde los desarrolladores de software o cualquier otro creador de contenido, podemos respaldar los repositorios de nuestros proyectos de manera gratuita y pública, aunque también tenemos la posibilidad de tener repositorios privados bajo una cuenta de pago.

GitHub no es solamente ese lugar donde respaldamos nuestro código en la nube, es mucho más, es una red social donde compartimos con la comunidad nuestro código, libro o cualquier otro tipo de contenido. Es el lugar perfecto para trabajar conjuntamente en una idea con un amigo o colega, aunque también podemos invitar a otros usuarios como colaboradores de nuestros proyectos, aceptar sus contribuciones, etc.

También contamos con un sistema de seguimiento de errores / problemas, al mejor estilo de un sistema de tickets, una funcionalidad que todos agradecemos ya que nos permite interactuar directamente con otros usuarios de la plataforma, recibir el feedback tanto de clientes como desarrolladores que han probado nuestro producto / proyecto o que colaboran en él, y desean ofrecer una sugerencia o dar noticia sobre un problema.

Son muchas las características que lo han convertido durante estos años en lo que es hoy, la elección número uno.

Para continuar con este tutorial necesitarás una cuenta en GitHub, por lo que si aún no tienes una te recomiendo que vayas ahora mismo y te des de alta. Es gratis!

¿Qué es Bitbucket?

Aunque GitHub es la plataforma más conocida y utilizada, existen otra a la altura de esta y que también me gustaría mencionar. Aquí es donde entra Bitbucket al mercado, posicionándose como una de las principales alternativas.

Bitbucket ha llamado la atención de muchos por su flexibilidad, y es que al contrario de GitHub permite a los usuarios gratuitos elegir entre utilizar Git o Mercurial como sistema de controlador de versiones al mismo tiempo que les ofrece herramientas para el control de errores (como Jira), integración con Google Analytics, HipChat como software de comunicación entre colaboradores del proyecto al igual que opciones de control de actividad para cada repositorio para que los desarrolladores no tengan que utilizar herramientas externas para estas funciones.

Entre las principales ventajas de Bitbucket sobre GitHub encontramos la disponibilidad de un número ilimitado de repositorios privados para los usuarios gratuitos, de manera que cualquier desarrollador puede subir sus proyectos a la plataforma, establecerlos como privados y no tener que pagar por ello. Pero no todo es******* , las versiones gratuitas de Bitbucket limitan a tan solo 5 colaboradores por proyecto y los usuarios que necesiten un mayor número de estos tendrán que contratar un plan de suscripción.

Subiendo un proyecto a GitHub y a Bitbucket

Ya sea que tengamos una cuenta en GitHub o Bitbucket, lo siguiente sería crear un repositorio nuevo:

GitHub

 

GitHub create new repository

…en la página siguiente el propio GitHub nos ayuda con el siguiente paso, en nuestro caso:

GitHub help us with remote add origin github url

Sin más continuamos con la sugerencia y subimos nuestro repositorio local a GitHub para que cualquier otra persona pueda contribuir:

git push origin master

 

Puedes copiar los comandos anteriores aquí:

En este punto ya tendríamos nuestra aplicación de prueba en GitHub, si vamos a la página del proyecto deberíamos de ver algo similar a lo siguiente:

GitHub SomeApp

Bitbucket

El proceso en Bitbucket es muy similar al de GitHub, veamos:

Bitbucket new repository

 

Si comparamos con la imagen relacionada a este paso en GitHub nos daremos cuenta de las claras diferencias, en cuanto a opciones se refiere. Luego de este paso también obtenemos sugerencias en la pantalla siguiente:

Bitbucket new repository information

Tal y como hicimos con el ejemplo anterior vamos a subir el proyecto a nuestros repositorio en Bitbucket:

git remote add origin bitbucket url

Como podemos observar el comando ejecutando ha fallado, en el mensaje de error se nos informa que ya existe un repositorio remoto identificado con el nombre de origin. Lo que sucede es que al añadir el repositorio remoto en GitHub lo hemos bautizado como origin, y es que tanto GitHub como Bitbucket utilizan este nombre como identificador por defecto.

git remote

Para resolver este problema primero tenemos que conocer un poco más sobre git remote, y aunque los comandos anteriores se explican por si mismos, creo que es necesario una explicación por más básicos que luzcan.

Recordemos que estos tutoriales están enfocados en desarrolladores de todos los niveles, así que expliquemos paso por paso lo que hemos hecho.

Mediante el primer comando git remote gestionamos todo lo referente a repositorios remotos, con este comando podemos añadir, renombrar, eliminar, establecer ramas, entre otras acciones que podremos ejecutar sobre estos.

En el caso anterior luego del parámetro add establecemos el nombre con el cual deseamos asociar nuestro repositorio remoto, tras esto especificamos la dirección de este repositorio mediante la URL. En otras palabras: origin es el nombre con el cual se identificará a este repositorio remoto dentro de nuestra configuración local.

Dicho esto, la solución al problema que tuvimos es, claramente, añadir el repositorio en Bitbucket bajo otro nombre, pero pensándolo bien lo ideal sería renombrar el repositorio remoto asociado con GitHub con un nombre más descriptivo y no tan genérico.

git remote rename

Antes que nada, vamos a listar los repositorios remotos que tenemos configurados haciendo uso del comando git remote, y para obtener más información ejecutamos git remote -v a favor de visualizar la dirección URL asociada al repositorio. Luego de esto hacemos uso de git remote rename especificando primero el nombre actual y por último el nuevo nombre:

git remote rename origin github

…por último mostramos nuevamente los repositorios configurados en pos de verificar que el nombre se ha actualizado correctamente.

Así que ahora agregaremos nuevamente el repositorio asociado a Bitbucket pero modificaremos el comando a favor de agregarlo con un nombre más descriptivo tal y como hemos hecho con GitHub:

git remote add bitbucket

…acto seguido listamos los repositorios y comprobamos que se ha agregado correctamente, al mismo tiempo que los nombres especificados nos ayudan a distinguir fácilmente entre los repositorios configurados.

git push

Luego de establecer con git remote los repositorios remotos con los cuales vamos a trabajar, llega el momento de git push. Con push podemos publicar nuestras confirmaciones locales hacia GitHub o cualquier otro servidor remoto o servicio de este tipo. Hagámoslo nuevamente pero esta vez hacia Bitbucket:

git push bitbucket master

Lo primero que hemos hecho es listar los nombres asociados a los repositorios remotos y acto seguido hacemos un git push especificando el nombre del repositorio sobre el cual deseamos ejecutar esta acción, escribimos nuestra contraseña y el proceso comienza.

Puedes copiar el comando anterior aquí:

Claramente tener configurado varios repositorios remotos que apuntan hacia servicios distintos no es algo muy frecuente o necesario, lo muestro solo con el afán de que puedan ver cuan flexible es Git.

git remote remove

Dicho esto pues vamos a eliminar el repositorio remoto que hace referencia a Bitbucket y para esto hacemos uso del comando git remote remove:

…y luego podemos listar nuevamente los repositorio para constatar que ahora solamente tenemos a GitHub.

Clonando un repositorio remoto

Ahora supongamos que llegamos al trabajo donde usamos otro ordenador o quizás otro compañero que va a colaborar con nosotros en el proyecto necesita descargar lo que hemos hecho hasta el momento.

git clone

Esto lo podemos lograr mediante el comando git clone, de esta manera:

git clone origin github SomeAppRemote

En la imagen podemos observar como hemos pasado el parámetros –origin donde especificamos el nombre con el cual identificaremos el repositorio remoto, luego pasamos la dirección URL y por último especificamos la carpeta donde se almacenarán los datos del proyecto. A esta carpeta le hemos otorgado un nombre distinto para que no entre en conflicto con la carpeta original.

Puedes copiar el comando anterior aquí:

Luego de obtener el proyecto desde el repositorio remoto nos cambiamos a la carpeta que acabamos de crear y ejecutamos algunas verificaciones.

git remote -v

Con este comando que hemos venido usando mostramos los repositorios remotos configurados al igual que su dirección URL asociada. El parámetro -v (–verbose) nos ayuda con el segmento asociado a la dirección URL, pero aún así esta no es toda la información referente al repositorio remoto.

git remote show

Si deseamos obtener más información podemos ayudarnos con el comando git remote show, mediante el cual podemos conocer también la dirección URL, la rama HEAD, la rama remota (remote branch) a la cual estamos dando seguimiento: