Mover múltiples commits (con fusiones intermedias) fuera del master en una twig separada

Usando git, quiero mover todos los cambios creados por mis propios commits locales (ace45b0 y 2d4ac36) a una única confirmación en una twig separada y eliminar esos commits de master. ¿Puedo hacer esto?

7ff6336 (HEAD -> master, origin/master, origin/HEAD) Merged remote master before pushing 2d4ac36 Made some local changes bb60891 Merged upstream master into local master b7a4d2e (upstream/master) Merge 271eb1a into upstream master 271eb1a Commit in another fork ace45b0 Made some local changes 959d04b head when I first cloned. 

Creo que estoy detrás de este resultado final:

 origin/master myNewBranch bb60891 HEAD <hash after applying ace45b0 & 2d4ac36> HEAD b7a4d2e bb60891 271eb1a 959d04b 

Un enfoque sería seleccionar con myNewBranch los dos commits de master en myNewBranch , luego myNewBranch a una única confirmación en myNewBranch . Finalmente, puede eliminar los dos commits originales de master ya sea haciendo un git revert (simple y seguro), o posiblemente a través de una rebase interactiva donde realmente borre los commits de master .

Primero, elige los dos commits en myNewBranch :

 git checkout myNewBranch git cherry-pick ace45b0 git cherry-pick 2d4ac36 

Tenga en count que puede get conflictos de combinación con cada selección, y si es así, tendrá que lidiar con ellos.

Hay varias opciones para aplastar estas dos nuevas confirmaciones en una única confirmación. Una rebase interactiva es tal vez la más poderosa, pero es un trabajo pesado, y dado que los dos commits que desea aplastar son HEAD o inmediatamente antes de HEAD, hay una opción mucho más simple. Podemos intentar realizar un restablecimiento myNewBranch a dos confirmaciones previas en la twig myNewBranch :

 git reset --soft HEAD~2 

Esto moverá el puntero HEAD a la confirmación antes de la primera de las dos confirmaciones de selección. No actualizará la etapa o el directory de trabajo, lo que significa que los cambios que estos commits introdujeron ahora se escenificarán. Ahora todo lo que tienes que hacer es hacer una confirmación:

 git commit -m 'brought in two commits from local changes' 

Ahora para limpiar la twig master , lo más probable es que la mejor opción sea revertir los dos commits, por ej.

 git checkout master git revert 2d4ac36 git revert ace45b0 

Esto agregará dos nuevos commits encima de master que cancelarán funcionalmente lo que estaban haciendo los dos commits. Esta opción es segura si su twig master es publicada y compartida por alguien que no sea usted mismo, porque en realidad no reescribe el historial, solo agrega nuevas confirmaciones.

Si nadie más comparte el master entonces tienes otra opción aquí. Podría hacer una rebase interactiva de la twig master y eliminar las dos confirmaciones. Si puede tolerar el riesgo asociado con esto, puede intentar lo siguiente:

 git rebase -i HEAD~7 

Esto abrirá una window que muestra las 7 confirmaciones más recientes de HEAD, de mayor a más reciente:

 959d04b head when I first cloned. ace45b0 Made some local changes 271eb1a Commit in another fork b7a4d2e (upstream/master) Merge 271eb1a into upstream master bb60891 Merged upstream master into local master 2d4ac36 Made some local changes 7ff6336 Merged remote master before pushing 

Ahora borre las líneas que contienen los dos commits que no desea, dejándolo con esto:

 959d04b head when I first cloned. 271eb1a Commit in another fork b7a4d2e (upstream/master) Merge 271eb1a into upstream master bb60891 Merged upstream master into local master 7ff6336 Merged remote master before pushing 

Ahora guarde las windows ( :wq si está usando Vim) y salga. El debería comenzar la rebase. Una vez más, podría encontrarse con conflictos de fusión a medida que Git reproduzca los compromisos anteriores sobre una nueva base. Una vez que haya terminado la rebase, su twig master estará completamente desprovista de las dos confirmaciones originales. De nuevo, esta es solo una muy buena opción si el master no fuera compartido por nadie más, ya que requiere reescribir el historial, a less que la opción git revert .