git stash: esconder cambios

El stash es una potente herramienta que trae Git para apartar temporalmente modificaciones hechas al directorio de trabajo, facilitando operaciones como cambios de rama, commits parciales, o pruebas unitarias de código a medio integrar.

El stash permite tomar algunos cambios pendientes de aplicar en un repositorio de Git, y apartarlos para hacerlos desaparecer temporalmente. De este modo, podemos limpiar nuestro espacio de trabajo, pero sin perder lo que hayamos hecho hasta el momento, que puede ser rescatado posteriormente.

Resulta útil, por lo tanto, en los siguientes supuestos:

  • Estás trabajando en un código de una rama, pero de repente tienes necesidad urgente de cambiar de rama para atender otra cosa.
  • Te interesa apartar algunos cambios que no quieres introducir en el próximo commit (aunque recuerda que tienes otras formas más simples como el parámetro -p/--patch.
  • Quieres ocultar temporalmente unos cambios para que no afecten la próxima compilación de un programa o la próxima ejecución del comando de unit testing.

Empujar todo al stash

Para todas estas tareas puedo simplemente ejecutar git stash, y sin mediar palabra, esconderá las modificaciones para que dejen de estar ahí. Cuando hagas git status ya no las verás. Eso no significa que hayan desaparecido, únicamente están apartadas en el stash.

Para ver todas las cosas que hay en el stash, siempre podrás usar el comando git stash list. Este comando te enumerará, a cambio por línea, todo lo que hayas metido en el stash.

stash@{0}: WIP on trunk: b3eca13
stash@{1}: WIP on trunk: b3eca13

Cada una de estas líneas se corresponde con una modificación enviada al stash. Lo primero que viene (stash@{0}) es su identificador. Esto es usado luego para poder referirse a ese cambio concreto cuando haya varios y queramos aclarar cuál. En cuanto al resto, nos indica la rama de la que procede el cambio, y un comentario, que por defecto será el hash del commit del que se retiró esto.

Es verdad que la salida de git stash list no es muy descriptiva, pero podemos cambiar esto si a la hora de enviar algo al stash le ponemos un comentario que indique qué hay en ese parche. Para poner este comentario, hazlo justo cuando vayas a enviar algo al stash usando el siguiente comando en su lugar:

git stash save [qué es todo esto]

Lo que pongas tras save será el comentario que veas cuando luego listes los elementos del stash.

Traerse las cosas del stash

Una vez que quieras recuperar las cosas del stash, puedes extraerlas rápidamente mediante el comando git stash pop. Este comando lo que hace es recuperar el último elemento que se haya enviado al stash, y tratar de rescatarlo para volver a ponerlo en el repositorio.

Esto resulta conveniente porque a menudo el cambio que más recientemente se haya mandado al stash es el que querremos volver a aplicar. Así los podremos desaplicar en orden inverso al orden en el que los hemos metido, y el riesgo de conflictos es menor.

En cualquier caso, también tenemos el comando git stash apply, que permite aplicar directamente alguno de los items que hay en el stash. Todo lo que tienes que hacer es poner git stash apply, y con eso aplicará por defecto el cambio más reciente, pero si quieres especificar cuál quieres aplicar en este momento, todo lo que tienes que hacer es agregar el identificador del stash (el que veíamos antes en el list, con la forma stash@{0}), como argumento después de apply:

git stash apply stash@{2}

Examinar el contenido de un stash

Si el mensaje de comentario que pones con save no te parece lo suficiente descriptivo, puedes usar el comando git stash show para ver el contenido de un parche mandado al stash.

Cuando digo parche, es literal, ya que lo que se manda al stash es el mismo diff que veríamos al ejecutar un comando como git diff.

Para ver uno de estos parches utiliza la siguiente invocación: git stash show seguido del identificador del stash a ver. Por ejemplo:

git stash show stash@{2}

Limpiar el stash

Usar git stash pop para sacar algo del stash lo borrará del stash.

Sin embargo, git stash apply no hará el mismo efecto. Además, a veces git stash pop tampoco lo hará. Si durante el proceso de extracción con pop se producen conflictos (porque se hayan hecho cambios en las líneas que modifica lo mandado al stash, y ya no se pueda volver a sacar de forma limpia), tampoco lo borrará del stash.

O a veces puede ocurrir que se te olvide que enviaste algo al stash, y lo empieces a hacer de nuevo. Con el tiempo, el stash acumulará parches que han quedado en el olvido.

Puedes borrar uno de estos parches si usas el subcomando git stash drop. Por defecto, si únicamente usas git stash drop borrarás el elemento más reciente enviado al stash, pero puedes especificar cuál quieres borrar si se lo indicas como parámetro. Por ejemplo:

git stash drop stash@{4}

También puedes borrar todo el stash usando el comando

git stash clear

Ten en cuenta en cualquier caso que esta es una operación destructiva y que podrías perder la posibilidad de recuperarlo si luego descubres que no debiste hacer eso, así que ve con cuidado.

Lista de reproducción
  1. 1
    ¿Qué es Git?
    4 minutos
  2. 2
    Cómo instalar Git
    9 minutos
  3. 3
    Creando tu primer commit
    9 minutos
  4. 4
    Qué es el staging area
    10 minutos
  5. 5
    Cómo deshacer modificaciones de archivos
    7 minutos
  6. 6
    Cómo deshacer un commit con reset
    7 minutos
  7. 7
    Cómo revertir un commit con revert
    7 minutos
  8. 8
    Introducción a las ramas
    6 minutos
  9. 9
    Cómo crear y modificar ramas
    6 minutos
  10. 10
    Commits bajo el workflow Feature Branch
    6 minutos
  11. 11
    Cómo fusionar ramas con merge
    6 minutos
  12. 12
    Fusiones conflictivas
    9 minutos
  13. 13
    Cómo construir alias
    7 minutos
  14. 14
    Más sobre conflictos
    9 minutos
  15. 15
    Etiquetas
    7 minutos
  16. 16
    Tags anotados
    9 minutos
  17. 17
    git stash: esconder cambios
    6 minutos
  18. 18
    Introducción a remotos
    5 minutos
  19. 19
    Pusheando a un remoto
    6 minutos
  20. 20
    Clonando y haciendo pull
    6 minutos
  21. 21
    Fetch y pull rebases
    8 minutos
  22. 22
    Rebase
    7 minutos
  23. 23
    Rebase interactivo
    6 minutos
  24. 24
    Master, main y otros nombres de rama
    9 minutos
  25. 25
    git switch
    9 minutos
  26. 26
    git-restore
    10 minutos
  27. 27
    git-grep
    11 minutos
  28. 28
    Gitignore
    11 minutos
  29. 29
    El flag --patch
    9 minutos
  30. 30
    git-apply y parches en bruto (advanced)
    9 minutos
  31. 31
    Merge octopus (advanced)
    9 minutos
  32. 32
    Conventional commits
    12 minutos
  33. 33
    Merge and squash (GitLab / GitHub...)
    6 minutos
  34. 34
    git merge --squash
    7 minutos
  35. 35
    git-bisect
    8 minutos
  36. 36
    git-blame
    6 minutos
  37. 37
    git-reflog
    10 minutos
  38. 38
    Git para la Bash
    11 minutos
  39. 39
    Submódulos (parte 1)
    7 minutos
  40. 40
    Submódulos (parte 2)
    10 minutos
  41. 41
    Otros clientes Git (último episodio)
    9 minutos