Las actualizaciones fueron rechazadas porque la punta de su rama actual está detrás

154

Soy nuevo en Git, así que siéntete libre de tratarme como un novato.

Nuestro flujo de trabajo es tal. Tenemos una sucursal llamada a la devque puedo llegar origin/dev. Cuando hacemos cambios, creamos una rama de desarrollo:

git checkout -b FixForBug origin / dev

Ahora tengo una rama llamada FixForBugque está rastreando (creo que esa es la palabra correcta) origin/dev. Por lo tanto, si hago una git pull, traerá nuevos cambios, lo origin/devque es genial. Ahora, cuando termino con mi solución, empujo a una rama remota llamada lo mismo.

Primero origin/develimino cualquier cambio y hago una nueva versión:

git pull --rebase

Luego empujo los cambios a una rama remota del mismo nombre:

git push origin FixForBug

Ahora, hay una rama en el servidor remoto y puedo crear una solicitud de extracción para que ese cambio sea aprobado y fusionado nuevamente en la rama de desarrollo. Yo no siempre meter nada a origin/devmí mismo. Supongo que esto es un flujo de trabajo bastante común.

La primera vez que hago un git push, funciona bien y crea la rama remota. Sin embargo, si presiono por segunda vez (digamos que durante la revisión de código, alguien señala un problema), aparece el siguiente error:

error: falló al empujar algunas referencias a ' https://github.limeade.info/Limeade/product.git ' sugerencia: Las actualizaciones fueron rechazadas porque la punta de su rama actual está detrás de la sugerencia: su contraparte remota. Integre los cambios remotos (por ejemplo, pista: 'git pull ...') antes de presionar nuevamente. pista: vea la 'Nota sobre avance rápido' en 'git push --help' para más detalles.

Sin embargo, si hago un git statusmensaje, dice que estoy por delante de origin/dev1 commit (lo cual tiene sentido) y si sigo la pista y ejecuto git pull, dice que todo está actualizado. Creo que esto se debe a que estoy presionando a una rama diferente a mi rama aguas arriba. Puedo solucionar este problema ejecutando:

git push -f origin FixForBug

En ese caso, empujará los cambios a la rama remota, diciendo (actualización forzada) y todo parece estar bien en la rama remota.

Mis preguntas:

¿Por qué se -frequiere en este escenario? Por lo general, cuando estás forzando algo, es porque estabas haciendo algo mal o al menos en contra de la práctica estándar. ¿Estoy bien haciendo esto, o arruinará algo en la rama remota o creará una molestia para quien eventualmente tenga que fusionar mis cosas en dev?

Mike Christensen
fuente
2
Parece que el mensaje que está recibiendo dice que la rama remota FixForBug está por delante de su rama local FixForBug. Debe extraer los cambios de esa rama remota y fusionarlos en su rama local antes de presionar.
mhatch
44
@hatchhat - Entonces, ¿básicamente correr git pull origin FixForBugantes de presionar para eso? Ok, eso tiene sentido. ¡Siéntase libre de agregar como respuesta!
Mike Christensen

Respuestas:

199

El -f es realmente necesaria debido al rebase. Cada vez que realice un rebase, necesitaría hacer un empuje forzado porque la rama remota no se puede reenviar rápidamente a su confirmación. Se podría siempre quiere asegurarse de que lo haga un tirón antes de empujar, pero si no lo hace igual que a fuerza de empuje de dev maestra o para el caso, se puede crear una nueva rama de empuje para a continuación, combinar o hacer una PR .

Keif Kraken
fuente
2
¡Gracias por esta respuesta tan útil! :)
AIM_BLB
1
¿Podría aclarar el punto "Siempre querrá asegurarse de hacer un tirón antes de empujar"? Está claro por qué se requiere "push -f" después de un rebase de la rama local. En este caso, ¿no se deshacerá el rebase del local haciendo un tirón con el control remoto antes de presionar?
Haripkannan
51

Para asegurarse de que su bifurcación local FixForBug no esté por delante de la bifurcación remota FixForBug, extraiga y combine los cambios antes de presionar.

git pull origin FixForBug
git push origin FixForBug
mhatch
fuente
2
OP declaró que ya hicieron un tirón y trataron de empujar. Su respuesta no se aplica a la pregunta de OP.
Patrick
1
Siempre es mejor evitar un empuje forzado. ¡Gracias por compartir esto!
Ann Kilzer
16

Si desea evitar tener que usar -f, puede usar solo

git pull

en vez de

git pull --rebase

El no rebase buscará los cambios origin/devy los fusionará en su FixForBugrama. Entonces, podrás correr

git push origin FixForBug

sin utilizar -f.

Greg Hewgill
fuente
3
Rebase es parte de nuestro flujo de trabajo aquí. Me gritarán si no lo hago.
Mike Christensen
1
@MikeChristensen: Bien, entonces sigue el procedimiento documentado, por supuesto. Según lo que describa, deberá usarlo -fporque está reemplazando las confirmaciones en el repositorio ascendente con diferentes que tienen un historial diferente (rebase). Si usara un producto como Gerrit, entonces es compatible con este tipo de flujo de trabajo de revisión de código sin necesidad de usarlo -fal presionar. Utilizamos Gerrit en el trabajo de esta manera y funciona muy bien.
Greg Hewgill
12

the tip of your current branch is behind its remote counterpartsignifica que ha habido cambios en la rama remota que no tiene localmente. y git te dice que importes nuevos cambios REMOTEy los fusiones con tu código y luego los pushremotas.

Puede usar este comando para forzar cambios en el servidor con repo local ().

git push -f origin master

con -fetiqueta anulará Remote Brach codecon su código.

Talha Rafique
fuente
6

El comando que utilicé con Azure DevOps cuando encontré el mensaje "las actualizaciones fueron rechazadas porque la punta de su rama actual está detrás" era / es este comando:

maestro de origen git pull

(o puede comenzar con una nueva carpeta y hacer un Clon) ..

Esta respuesta no aborda la pregunta planteada, específicamente, Keif ha respondido esto anteriormente, pero responde el texto del título / título de la pregunta y esta será una pregunta común para los usuarios de Azure DevOps.

Noté un comentario: "¡Siempre querrás asegurarte de hacer un tirón antes de presionar" en respuesta de Keif arriba!

También he usado la herramienta Git Gui además de la herramienta de línea de comandos Git.

(No estaba seguro de cómo hacer el equivalente del comando de línea de comando "git pull origin master" dentro de Git Gui, así que volví a la línea de comando para hacer esto).

Este es un diagrama que muestra varios comandos git para varias acciones que tal vez desee realizar:

ingrese la descripción de la imagen aquí

Allan F
fuente
4

Esto me acaba de pasar.

  • Hice una solicitud de extracción a nuestro maestro ayer.
  • Mi colega lo estaba revisando hoy y vio que no estaba sincronizado con nuestra rama maestra, por lo que con la intención de ayudarme, fusionó el maestro con mi rama.
  • No sabía que él hizo eso.
  • Luego fusioné el maestro localmente, intenté empujarlo, pero falló. ¿Por qué? ¡Debido a que mi colega se fusionó con master creó una confirmación adicional que no tenía localmente !

Solución: Despliegue mi propia rama para obtener esa confirmación adicional. Luego empújalo de nuevo a mi rama remota.

literalmente lo que hice en mi rama fue:

git pull
git push
Miel
fuente
3

Así es como resolví mi problema

Supongamos que la rama ascendente es la que bifurcó y el origen es su repositorio y desea enviar un MR / PR a la rama ascendente.

Ya tienes, digamos unos 4 commits y estás obteniendo Updates were rejected because the tip of your current branch is behind.

Aquí esta lo que hice

Primero, aplasta tus 4 commits

git rebase -i HEAD~4

Obtendrá una lista de confirmaciones con pickescrito en ellas. (abierto en un editor)

ejemplo

pick fda59df commit 1
pick x536897 commit 2
pick c01a668 commit 3
pick c011a77 commit 4

a

pick fda59df commit 1
squash x536897 commit 2
squash c01a668 commit 3
squash c011a77 commit 4

Después de eso, puede guardar su confirmación combinada

próximo

Tendrás que esconder tu commit

Así es cómo

git reset --soft HEAD~1
git stash

ahora rebase con su rama aguas arriba

git fetch upstream beta && git rebase upstream/beta

Ahora haga estallar su confirmación oculta

git stash pop

cometer estos cambios y empujarlos

git add -A
git commit -m "[foo] - foobar commit"
git push origin fix/#123 -f
Deepesh Nair
fuente
2

Debe ser debido a commit está por delante de su empuje actual.

1) origen de git pull "nombre de la rama que desea empujar"

2) git rebase

Si git rebase es exitoso, entonces bueno. De lo contrario, debe resolver todos los conflictos de fusión localmente y mantenerlo continuo hasta que el cambio de base con control remoto sea exitoso.

3) git rebase - continuar

kris
fuente
0

Tuve este problema al intentar presionar después de un cambio de base a través de Visual Studio Code, mi problema se resolvió simplemente copiando el comando desde la ventana de salida de git y ejecutándolo desde la ventana de terminal en Visual Studio Code.

En mi caso, el comando era algo así como:

git push origin NameOfMyBranch:NameOfMyBranch

HoloLady
fuente