¿Cómo puedo mover HEAD a una ubicación anterior? (Cabeza separada) y deshacer confirma

git git-checkout git-reset git-revert git-reflog


En Git, estaba tratando de hacer una squash commit fusionándome en otra rama y luego restableciendo HEAD al lugar anterior a través de:

git reset origin/master

Pero necesito salir de esto.¿Cómo puedo mover la cabeza de nuevo a la ubicación anterior?

Tengo el fragmento SHA-1 ( 23b6772 ) del commit al que necesito moverlo. ¿Cómo puedo volver a este commit?




Answer 1 CodeWizard


Antes de responder, agreguemos algunos antecedentes, explicando qué es este HEAD .

First of all what is HEAD?

HEAD es simplemente una referencia a la confirmación actual (más reciente) en la rama actual.
Solo puede haber un solo HEAD en un momento dado (excluyendo git worktree ).

El contenido de HEAD se almacena dentro de .git/HEAD y contiene los 40 bytes SHA-1 de la confirmación actual.


detached HEAD

Si no está en la última confirmación, lo que significa que HEAD apunta a una confirmación previa en el historial, se llama detached HEAD .

Enter image description here

En la línea de comando, se verá así: SHA-1 en lugar del nombre de la rama ya que HEAD no apunta a la punta de la rama actual:

Enter image description here

Enter image description here


Unas cuantas opciones sobre cómo recuperarse de un desprendimiento de la cabeza:


git checkout

git checkout <commit_id>
git checkout -b <new branch> <commit_id>
git checkout HEAD~X // x is the number of commits t go back

Esto hará que la nueva rama apunte al compromiso deseado.
Este comando se registrará en un compromiso dado.
En este punto,puedes crear una rama y empezar a trabajar a partir de este punto.

# Checkout a given commit.
# Doing so will result in a `detached HEAD` which mean that the `HEAD`
# is not pointing to the latest so you will need to checkout branch
# in order to be able to update the code.
git checkout <commit-id>

# Create a new branch forked to the given commit
git checkout -b <branch name>

git reflog

Siempre puedes usar el reflog también.
git reflog mostrará cualquier cambio que haya actualizado el HEAD y al verificar la entrada de reflog deseada, el HEAD volverá a esta confirmación.

Cada vez que se modifique el HEAD habrá una nueva entrada en el reflog

git reflog
git checkout HEAD@{...}

Esto te hará volver a tu compromiso deseado

Enter image description here


git reset --hard <commit_id>

"Mueve" tu cabeza de vuelta al compromiso deseado.

# This will destroy any local modifications.
# Don't do it if you have uncommitted work you want to keep.
git reset --hard 0d1d7fc32

# Alternatively, if there's work to keep:
git stash
git reset --hard 0d1d7fc32
git stash pop
# This saves the modifications, then reapplies that patch after resetting.
# You could get merge conflicts if you've modified things which were
# changed since the commit you reset to.
  • Nota: ( desde Git 2.7 ) también puede usar git rebase --no-autostash también.

git revert <sha-1>

"Deshacer" el compromiso dado o el rango de compromiso.
El comando de reinicio "deshará" cualquier cambio hecho en la confirmación dada.
Un nuevo compromiso con el parche de deshacer será cometido mientras que el compromiso original permanecerá en la historia también.

# Add a new commit with the undo of the original one.
# The <sha-1> can be any commit(s) or commit range
git revert <sha-1>

Este esquema ilustra qué comando hace qué.
Como puede ver allí, reset && checkout modifica el HEAD .

Enter image description here




Answer 2 amuliar


Do

git reset 23b6772

Para ver si estás en la posición correcta:

git status

Verás algo

En el maestro de la rama Su rama está detrás de "origen/maestro" por 17 compromisos,y puede ser adelantado.

Luego reescriba la historia en su control remoto para reflejar el cambio:

git push --force-with-lease // a useful command @oktober mentions in comments



Answer 3 Kay V


La solución más rápida posible (sólo 1 paso)

Use git checkout -

Verá Switched to branch <branch_name> . Confirme que es la rama que desea.


Breve explicación: este comando moverá HEAD nuevamente a su última posición. Vea la nota sobre los resultados al final de esta respuesta.


Mnemotécnico: este enfoque es muy parecido al uso de cd - para volver al directorio visitado anteriormente. La sintaxis y los casos aplicables coinciden bastante bien (por ejemplo, es útil cuando realmente desea que HEAD regrese a donde estaba).


Solución más metódica (2 pasos,pero memorable)

El acercamiento rápido resuelve la pregunta de la OP.Pero qué pasa si tu situación es ligeramente diferente:digamos que has reiniciado a Bash y luego te encuentras con la CABEZA desprendida.En ese caso,aquí hay dos pasos simples y fáciles de recordar.

1.Elija la rama que necesite

Usa git branch -v

Ves una lista de las sucursales locales existentes.Toma el nombre de la sucursal que se ajusta a tus necesidades.

2.Mueve la cabeza hacia ella

Utilice git checkout <branch_name>

Verá Switched to branch <branch_name> . ¡Éxito!


Outcomes

Con cualquiera de los métodos, ahora puede continuar agregando y comprometiendo su trabajo como antes: sus próximos cambios se rastrearán en <branch_name> .

Tenga en cuenta que tanto git checkout - como git checkout <branch_name> le darán instrucciones adicionales si ha realizado cambios mientras HEAD estaba desconectado.




Answer 4 antak


La pregunta puede leerse como:

Estaba en estado separado con HEAD en 23b6772 y escribí git reset origin/master (porque quería aplastar). Ahora que he cambiado de opinión, ¿cómo vuelvo a HEAD estando en 23b6772 ?

La respuesta directa es: git reset 23b6772

Pero respondí a esta pregunta porque me cansé de escribir (copiar y pegar) hashes de confirmación o su abreviatura cada vez que quería hacer referencia a la anterior HEAD y Google para ver si había algún tipo de taquigrafía.

¡Resulta que sí!

git reset - (o en mi caso git cherry-pick - )

Que por cierto era lo mismo que cd - para volver al directorio actual anterior en * nix! Así que hurra, aprendí dos cosas de un tiro.




Answer 5 Deepak Kumar


Cuando ejecuta el comando git checkout commit_id , luego HEAD se desconecta de 13ca5593d(say commit-id) y la rama estará disponible por más tiempo.

Vuelve a la ubicación anterior,ejecuta el comando paso a paso...

  1. git pull origin branch_name (digamos master)
  2. git checkout branch_name
  3. git pull origin branch_name

Volverás a la ubicación anterior con una confirmación actualizada del repositorio remoto.