Cómo seleccionar varias confirmaciones


Tengo dos ramas. Commit a es la cabeza de uno, mientras que el otro tiene b, c, d, e y f encima de a. Quiero mover c, d, e y f a primera rama sin cometer b. Usando cherry pick es fácil: checkout first branch cherry-elige uno por uno c a f y rebase la segunda rama en la primera. Pero hay alguna manera de elegir todo c-f ¿en un comando?

Aquí está una descripción visual del escenario (gracias JJD):

introduzca la descripción de la imagen aquí

Author: JJD, 2009-11-04

9 answers

Git 1.7.2 introdujo la habilidad de cherrypick un rango de commits. De las notas de la versión :

Git cherry-pick " aprendió a elegir un rango de confirmaciones (e. g. "cherry-pick A..B " y "cherry-pick st stdin"), también lo hizo " git revert"; estos no admiten el control de secuenciación más agradable "rebase [-i]" tiene, sin embargo.


Incluyendo comentarios importantes (créditos a los respectivos autores)

Nota 1: En el " cherry-pick A..B " forma, A debe ser mayor que B. Si son la orden incorrecta el comando fallará silenciosamente. - damian

Nota 2: Además, esto no elegirá A, sino todo después de A hasta e incluyendo B. – J. B. Rainsberger

Nota 3: Para incluir un solo tipo git cherry-elige Un^..B-sschaef

 859
Author: Eric Darchis,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-10-28 18:00:16

La forma más sencilla de hacerlo es con la opción onto a rebase. Supongamos que la rama de los cuales la corriente acabados en a se llama ingresar y esta es la rama que desea mover c-f en.

# checkout mybranch
git checkout mybranch

# reset it to f (currently includes a)
git reset --hard f

# rebase every commit after b and transplant it onto a
git rebase --onto a b
 86
Author: CB Bailey,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-11-04 08:13:13

O el monoplaza solicitado:

git rebase --onto a b f
 70
Author: wolfc,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-05-25 15:12:16

Puedes usar una combinación serial de git rebase y git branch para aplicar un grupo de commits a otra rama. As already posted by wolfc the first command actually copies the commits. Sin embargo, el cambio no es visible hasta que agregue un nombre de rama a la confirmación más importante del grupo.

por Favor, abra la imagen en una nueva pestaña ...

Flujo

Para resumir los comandos en forma de texto:

  1. Abrir gitk como un independiente proceso usando el comando: gitk --all &.
  2. Ejecutar git rebase --onto a b f.
  3. Presione F5en gitk. Nada cambia. Pero no HEAD está marcado.
  4. Corre git branch selection
  5. Presione F5en gitk. Aparece la nueva rama con sus commits.

Esto debería aclarar las cosas:

  • Commit a es el nuevo destino raíz del grupo.
  • Commit b es el commit antes del primer commit del grupo (exclusivo).
  • Commit f es el último commit del grupo (inclusive).

Después, podrías usar git checkout feature && git reset --hard b para borrar las confirmaciones c hasta f de la rama feature.

Además de esta respuesta, escribí una entrada de blog que describe los comandos en otro escenario que debería ayudar a usarlo en general.

 51
Author: JJD,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 11:33:24

Aplicar los comentarios de J. B. Rainsberger y sschaef para responder específicamente a la pregunta... Para usar un rango cherry-pick en este ejemplo:

git checkout a
git cherry-pick b..f

O

git checkout a
git cherry-pick c^..f
 23
Author: Andy,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-07-26 18:25:40
git rev-list --reverse b..f | xargs -n 1 git cherry-pick
 18
Author: Dustin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2009-11-04 03:59:07
git format-patch --full-index --binary --stdout range... | git am -3
 4
Author: Roger Wang,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-06-16 13:02:48

Si tiene revisiones selectivas para fusionar, por ejemplo A, C, F,J de A,B,C,D,E,F,G,H,I, J commits, simplemente use el comando siguiente:

Git cherry-elige un C F J

 2
Author: Shrikant W,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-02-20 10:00:36

En realidad, la forma más sencilla de hacerlo podría ser

  1. guardar la base de fusión entre las dos ramas MERGE_BASE=$(git merge-base branch-a branch-b)
  2. avance rápido o rebase la rama más antigua en la rama más nueva
  3. Rebase la rama resultante sobre sí misma, comenzando en la base de fusión desde el paso 1, y elimine manualmente las confirmaciones que no se desean:

    git rebase ${SAVED_MERGE_BASE} -i
    

    Alternativamente, si solo hay unas pocas confirmaciones nuevas, omita el paso 1 y simplemente use

    git rebase HEAD^^^^^^^ -i
    

    En el primer paso, usando suficiente ^ para pasar la base de fusión.

Verás algo como esto en la rebase interactiva:

pick 3139276 commit a
pick c1b421d commit b
pick 7204ee5 commit c
pick 6ae9419 commit d
pick 0152077 commit e
pick 2656623 commit f

Luego elimine las líneas b (y cualquier otra que desee)

 1
Author: ealfonso,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-06-04 06:36:28