В git, в чем разница между слиянием --squash и rebase? - PullRequest
312 голосов
/ 11 марта 2010

Я новичок в git и пытаюсь понять разницу между сквошем и ребазом. Насколько я понимаю, вы выполняете сквош, когда делаете ребаз.

Ответы [ 3 ]

321 голосов
/ 11 марта 2010

И git merge --squash, и git rebase --interactive могут создавать "сдавленный" коммит.
Но они служат разным целям.

создаст сдавленный коммит в ветви назначения, без пометки каких-либо отношений слияния.
(Примечание: он не производит коммит сразу: вам нужен дополнительный git commit -m "squash branch")
Это полезно, если вы хотите полностью отбросить ветку-источник, начиная с (схема взята из ТА вопрос ):

 git checkout stable

      X                   stable
     /                   
a---b---c---d---e---f---g tmp

до:

git merge --squash tmp
git commit -m "squash tmp"

      X-------------------G stable
     /                   
a---b---c---d---e---f---g tmp

и затем удаление tmp ветки.

Примечание: git merge имеет опцию --commit , но, начиная с Git 2.23 (Q3 2019), вы не можете использовать его с git merge --squash.

См. коммит 1d14d0c (24 мая 2019 г.) Вишал Верма (reloadbrain) .
(Объединено с Junio ​​C Hamano - gitster - в коммит 6e0b1c6 , 17 июня 2019 г.)

merge: отказать --commit с --squash

Ранее, когда было указано --squash, 'option_commit' молча отброшен. Это могло удивить пользователя, который пытался переопределить Поведение сквоша без фиксации с использованием --commit в явном виде.

git/git builtin/merge.c#cmd_merge() теперь включает в себя:

if (option_commit > 0)
    die(_("You cannot combine --squash with --commit."));

воспроизводит некоторые или все ваши коммиты на новой базе, позволяя вам раздавить (или совсем недавно «исправить», см. Этот ТА вопрос ), перейдя непосредственно к:

git checkout tmp
git rebase -i stable

      stable
      X-------------------G tmp
     /                     
a---b

Если вы решите раздавить все коммиты tmp (но, в отличие от merge --squash, вы можете выбрать переигрывание одних и подавление других).

Итак, различия:

  • merge не затрагивает вашу ветку-источник (tmp здесь) и создает один коммит в нужном вам месте.
  • rebase позволяет продолжать работу в той же ветке источника (все еще tmp) с:
    • новая база
    • чище история
119 голосов
/ 21 апреля 2017

Объединить коммиты: сохраняет все коммиты в вашей ветке и чередует их с коммитами в базовой ветке enter image description here

Merge Squash: сохраняет изменения, но пропускает отдельные коммиты из истории. enter image description here

Rebase: перемещает всю ветвь объекта, чтобы она начиналась на кончике мастер-ветви, эффективно объединяя все новые коммиты в master

enter image description here

Подробнее о здесь

74 голосов
/ 11 марта 2010

Merge squash объединяет дерево (последовательность коммитов) в один коммит. То есть давит все изменения, сделанные в n , фиксируются в одном коммите.

Перебазирование - это повторное базирование, то есть выбор новой базы (родительского коммита) для дерева. Может быть, ртутный термин для этого более понятен: они называют это трансплантацией, потому что это просто: выбор нового основания (родительского коммита, корня) для дерева.

При интерактивном перебазировании вам предоставляется возможность либо раздавить, выбрать, отредактировать или пропустить коммиты, которые вы собираетесь перебазировать.

Надеюсь, это было ясно!

...