Dangit, Git!?!

Git es dificil: estropearlo es facil y darse cuenta de como corregir tus errores es imposible. La documentaion de Git sufre del problema del huevo y la gallina, no podes buscar cómo corregir tu error, a menos de que sepas el nombre de lo que tenes que saber para poder arreglarla.

Aca hay algunas horribles situaciones con las que me encontre y como, eventualmente, pude resolverlas en español simple.

Dangit, hice algo terriblemente mal, por favor dime que git tiene una maquina del tiempo mágica!?!

git reflog
# verás una lista de todo lo que
# haz hecho en git, en todas las ramas!
# cada uno tiene un index HEAD@{index}
# busca el comando anterior al que rompio todo
git reset HEAD@{index}
# maquina del tiempo mágica

Puedes usar esto para recuperar cosas que borraste accidentalmente, o simplemente para borrar cosas que intentaste hacer que rompieron el repo, o para recuperate de un mal merge, o simplemente para volver a un momento donde las cosas funcionaba. Yo uso reflog MUCHISIMO. Mega agradecimiento para las muchiiiiismas personas que sugirieron que lo agregue.

Dangit, hice commit e inmediatamente me di cuenta que tenia que hacer un pequeño cambio!

# realizar cambios
git add . # o agregue archivos individuales
git commit --amend --no-edit
# ahora tu último commit contiene los cambios!
# ADVERTENCIA: nunca arregles commits públicos

Esto suele pasarme cuando hago commit y luego corro tests/linters... y mátame, me olvide de poner un espacio antes de un signo igual. También podrías realizar el cambio como un nuevo commit y luego hacer rebase -i para realizar un squash the ambos cambios juntos, pero esta manera es un millon de veces más rápido.

Advertencia: Nunca deberías arreglar commits que han sido subidos a ramas públicas/compartidas. Solo arregla commits que existan en tu copia local o la vas a pasar mal.

Dangit, necesito cambiar el mensaje en mi último commit!

git commit --amend
# sigue las indicaciones para cambiar el mensaje

Estúpidos formatos de mensajes de commits.

Dangit, accidentalmente hice commit de algo a master que debía haber sido en una nueva rama!

# crea una nueva rama desde master
git branch nombre-de-rama
# borra el último commit de la rama master
git reset HEAD~ --hard
git checkout nombre-de-rama
# tu commit ahora vive en al nueva rama :)

Nota: esto no funciona si ya haz realizado el push a una rama pública/compartida, y si haz intentado otra cosa antes, podrías necesitar hacer git reset HEAD@{number-of-commits-back} en vez de HEAD~. Tristeza infinita. También, mucuuuuuchas personas sugirieron una increible manera de hacer esto más corto que no la sabía. Gracias a todos.

Dangit, accidentalmente hice commit a la rama equivocada!

# deshaz el útlimo commit, pero deja los cambio disponibles
git reset HEAD~ --soft
git stash
# muevete a la rama correcta
git checkout nombre-de-la-rama-correcta
git stash pop
git add . # or add individual files
git commit -m "your message here";
# ahora tus cambios están en la rama correcta

Mucha gente sugirió usar cherry-pick para esta situacion, asi que, usa la que más sentido te haga!

git checkout nombre-de-la-rama-correcta
# coge el último commit de master
git cherry-pick master
# borralo de master
git checkout master
git reset HEAD~ --hard

Dangit, trate de realizar un diff pero no pasó nada?!

Si sabes que hiciste cambios a tus archivos, pero diff está vacío, probablemente hiciste add de tus archivos y necesitas un flag especial.

git diff --staged

Archivos abajo ¯\_(ツ)_/¯ (si, se que esto es una funcionalidad, no un error, pero es desconcertante y poco obvio la primera vez que te sucede!)

Dangit, necesito deshacer un commit de hace 5 comits!

# encuentra el commit que necesitas deshacer
git log
# usa las flechas para moverte para arriba y abajo en la historia
# una vez que encontraste el commit, guarda su hash
git revert [hash guardado]
# git va a crear un nuevo commit que deshace ese commit
# sigue las indicaciones para editar el mensaje del commit
# o simplemente guarda y haz el commit

Al parecer, no necesitas buscar y copiar-pegar el contenido del viejo archivo al actual para deshacer los cambios! Si hiciste commit de un bug, puedes deshacer el commit de una con revert

También puedes revertir un solo archivo en vez de todo un commit! Pero, por supuesto, haciendo honor a la filosofia git, es un maldito comando totalmente distinto.

Dangit, necesito deshacer los cambio de un archivo!

# busca el hash del commit anterior de cuando se cambio el archivo
git log
# usa las flechas para moverte para arriba y abajo en la historia
# una vez que encontraste el commit, guarda su hash
git checkout [hash guardado] -- path/to/file
# la version anterior del archivo estará en tu index
git commit -m "Waw, no tienes que hacer copiar-pegar para deshacer"

Cuando me di cuenta de esto fue INCREIBLE. INCREBILE. IN-CRE-I-BLE. Pero en serio, en que planeta checkout -- hace sentido que sea la mejor manera de deshacer un archivo? :shakes-fist-at-linus-torvalds:

Olvida este ruido, me doy por vencido.

cd ..
sudo rm -r stupid-git-repo-dir
git clone https://some.github.url/stupid-git-repo-dir.git
cd stupid-git-repo-dir

Gracias a Eric V. por esta. Todas las quejas por el uso de sudo en este chiste pueden ser dirigidas a él.

En serio, si tu rama está tan rota que necesitas reiniciar el estado de tu repo al mismo que el repo remoto en una manera aprobada por git, prueba esto, pero ten en cuenta que son acciones destructivas e irrecuperables!

# recupera el último estado del origen
git fetch origin
git checkout master
git reset --hard origin/master
# elimina los archivos y directorios sin seguimiento
git clean -d --force
# repite checkout/reset/clean para cada rama rota

*Descargo: Este sitio no está pensado para ser una referencia exhaustiva. Y si, hay otras manera de hacer las mismas cosas de una forma teoricamente más puras, pero yo llegue a estos pasos por prueba y error y muchos insultos, y tuve esta loca idea de compartirlas con una sana dosis de ligereza. Tómalo o déjalo como quieras!

Muchas gracias a todos los que voluntarios que tradujeron este sitio a otros idiomas, la rompen! Moritz Stückler (de) · Daniil Golubev (ru) · Łukasz Wójcik (pl) · fedemcmac (it) · Michel (fr) · Andriy Sultanov (ua) · Meiko Hori (ja) · Alex Tzimas (gr) · Franco Fantini (es) · Catalina Focsa (ro) · Davi Alexandre (pt_BR) . Con la ayuda adicional de Iain Murray · Frank Taillandier · David Fyffe · Lucas Larson

Si quieres ayudar a traducir a otros idiomas, envia tu PR a GitHub