Как я могу объединить два коммита в один, если я уже начал rebase?
Я пытаюсь объединить 2 коммита в 1, поэтому я следовал "squashing commits with rebase" от git ready.
я побежал
git rebase --interactive HEAD~2
в появившемся редакторе, я меняю pick to squash а затем save-quit, но перебазировать не удается с ошибкой
не может 'сквош' без предшествующего совершению
теперь, когда мое рабочее дерево достигло этого состояния, у меня возникли проблемы с восстановлением. Команда git rebase --interactive HEAD~2 не с
интерактивная перебазировка уже началась
и git rebase --continue выдает
не может 'сквош' без предшествующего совершению
11 ответов:
резюме
сообщение об ошибке
не может 'сквош' без предшествующего совершению
означает, что вы, вероятно, пытались " раздавить вниз."ГИТ всегда патиссоны новый коммит в старой совершения или "вверх", как показано в интерактивном списке rebase todo, то есть в фиксацию на предыдущей строке. Изменение команды в самой первой строке списка задач на
squashвсегда будет производить эту ошибку как есть ничего для первого коммита, чтобы раздавить В.Исправления
сначала вернитесь туда, где вы начали с
$ git rebase --abortскажите, что ваша история
$ git log --pretty=oneline a931ac7c808e2471b22b5bd20f0cad046b1c5d0d c b76d157d507e819d7511132bdb5a80dd421d854f b df239176e1a2ffac927d8b496ea00d5488481db5 aто есть a был первым коммитом, затем b и, наконец, c. после совершения c мы решили раздавить b и c вместе:
(Примечание: Работает
git logтрубит свой выход в пейджер,lessпо умолчанию на большинстве платформ. Для выхода из пейджера и вернуться к в командной строке нажмите кнопкуqключ.)под управлением
git rebase --interactive HEAD~2дает вам редактор сpick b76d157 b pick a931ac7 c # Rebase df23917..a931ac7 onto df23917 # # Commands: # p, pick = use commit # r, reword = use commit, but edit the commit message # e, edit = use commit, but stop for amending # s, squash = use commit, but meld into previous commit # f, fixup = like "squash", but discard this commit's log message # # If you remove a line here THAT COMMIT WILL BE LOST. # However, if you remove everything, the rebase will be aborted. #(обратите внимание, что этот список в обратном порядке по сравнению с выходом
git log.)изменение b
pickдоsquashприведет к ошибке, которую вы видели, но если вместо этого вы раздавите c в b (более новая фиксация в более старую или "раздавливание вверх"), изменив список задач наpick b76d157 b squash a931ac7 cи сохранить-выход из вашего Редактор, вы получите другой редактор, содержимое которого
# This is a combination of 2 commits. # The first commit's message is: b # This is the 2nd commit message: cкогда вы сохраняете и выходите, содержимое отредактированного файла становится сообщением фиксации новой комбинированной фиксации:
$ git log --pretty=oneline 18fd73d3ce748f2a58d1b566c03dd9dafe0b6b4f b and c df239176e1a2ffac927d8b496ea00d5488481db5 aПримечание О Переписывании Истории
интерактивная ребаза переписывает историю. Попытка нажать на пульт, который содержит старую историю, потерпит неудачу, потому что это не быстрая перемотка вперед.
если ветвь, которую вы перебазировали, является ветвью темы или функции , в котором вы работаете сами ничего страшного. При нажатии на другой репозиторий потребуется
--forceопция, или альтернативно вы можете быть в состоянии, в зависимости от разрешений удаленного репозитория, сначала удалить старую ветвь, а затем нажать перебазированную версию. Примеры тех команд, которые потенциально уничтожат работу, выходят за рамки этого ответа.уже опубликованные переписывание истории на ветке, в которой вы работаете с другими людьми без очень хорошая причина, такая как утечка пароля или других конфиденциальных деталей заставляет работать на ваших сотрудников и является антисоциальным и будет раздражать других разработчиков. Элемент "восстановление из раздела" Перемещение "вверх" в
git rebaseдокументация объясняет, с дополнительным акцентом.Rebasing (или любая другая форма перезаписи) ветвь, на которой другие основывали работу, - это плохая идея: любой, кто ниже по течению, вынужден вручную исправлять свою историю. В этом разделе объясняется, как сделать исправление с точки зрения нисходящего потока. реальное исправление, однако, будет заключаться в том, чтобы избежать перебазирования вверх по течению в первую очередь....
Если есть несколько коммитов, вы можете использовать
git rebase -iчтобы раздавить два коммита в один.Если есть только два коммита, которые вы хотите объединить, и они являются "самыми последними двумя", для объединения двух коммитов в один можно использовать следующие команды:
git reset --soft "HEAD^" git commit --amend
Rebase: вам это не понадобится:
простой способ для наиболее частого сценария.
в большинстве случаев:
на самом деле, если все, что вы хотите, это просто просто объединить несколько последних коммитов в один но не нужно
drop,rewordи другие работы по перебазированию.вы можете просто сделать:
git reset --soft "HEAD~n"
- предполагая, что
~nэто количество коммитов для мягко un-commit (т. е.~1,~2,...)затем используйте следующую команду для изменения сообщения фиксации.
git commit --amendчто довольно то же самое, что и большой диапазон
squashиpick.и он работает для n коммитов, но не только для двух коммитов, как указано выше.
сначала вы должны проверить, сколько совершает у вас есть:
git logесть два состояния:
что есть только два коммита:
например:
commit A commit B(в этом случае вы не можете использовать git rebase для этого) вам нужно сделать следующее.
$ git reset --soft HEAD^1 $ git commit --amendдругой заключается в том, что существует более двух коммитов; вы хотите объединить коммит C и D.
например:
commit A commit B commit C commit D(под этим условие, вы можете использовать git rebase)
git rebase -i Bи чем использовать "сквош" делать. Остальное разжижается очень легко. Если вы все еще не знаете, пожалуйста, прочитайте http://zerodie.github.io/blog/2012/01/19/git-rebase-i/
предполагая, что вы были в своей собственной ветке темы. Если вы хотите объединить последние 2 коммита в один и выглядеть как герой, отделите коммит непосредственно перед тем, как вы сделали последние два коммита.
git checkout -b temp_branch HEAD^2затем сквош совершает другую ветвь в этой новой ветви:
git merge branch_with_two_commits --squashэто внесет изменения, но не зафиксирует их. Так что просто совершите их, и все готово.
git commit -m "my message"Теперь вы можете объединить эту новую ветку обратно в основную ветку.
вы можете отменить перебазирование с помощью
git rebase --abortи когда вы снова запускаете интерактивную команду rebase, ' squash; commit должен быть ниже фиксации pick в списке
Я часто использую git reset --mixed чтобы вернуть базовую версию перед несколькими коммитами, которые вы хотите объединить, тогда я сделаю новую фиксацию, таким образом, вы можете позволить вашей фиксации самой новой, убедитесь, что ваша версия-это голова после того, как вы нажмете на сервер.
commit ac72a4308ba70cc42aace47509a5e Author: <[email protected]> Date: Tue Jun 11 10:23:07 2013 +0500 Added algorithms for Cosine-similarity commit 77df2a40e53136c7a2d58fd847372 Author: <[email protected]> Date: Tue Jun 11 13:02:14 2013 -0700 Set stage for similar objects commit 249cf9392da197573a17c8426c282 Author: Ralph <[email protected]> Date: Thu Jun 13 16:44:12 2013 -0700 Fixed a bug in space world automationесли я хочу объединить два коммита head в один, сначала я использую:
git reset --mixed 249cf9392da197573a17c8426c282"249cf9392da197573a17c8426c282" была третья версия, также ваша базовая версия перед слиянием, после этого я делаю новый совершают :
git add . git commit -m 'some commit message'Это все, надеюсь, это еще один способ для всех.
к вашему сведению, от
git reset --help:--mixed Resets the index but not the working tree (i.e., the changed files are preserved but not marked for commit) and reports what has not been updated. This is the default action.
$ git rebase --abortзапустите этот код в любое время, если вы хотите отменить git rebase
$ git rebase -i HEAD~2для повторного применения последних двух коммитов. Эта команда откроет редактор кода
- [ последний коммит будет внизу ]. Изменить последнее совершите сквош(ы). Так сквош сольется с предыдущим коммитом.
- затем нажмите клавишу esc и введите: wq для сохранения и закрытия
после :wq вы будете находиться в активном режиме перебазирования
Примечание: вы получите другой редактор, если нет предупреждений / сообщений об ошибках, если есть ошибка или предупреждение другой редактор не будет отображаться, вы можете прервать выполнение
$ git rebase --abortЕсли вы видите ошибку или предупреждение еще просто продолжить, запустив$ git rebase --continueвы увидите сообщение о фиксации 2. Выберите один или напишите свое собственное сообщение фиксации, сохраните и закройте [:wq]
Примечание. 2: возможно, вам придется принудительно перенести изменения в удаленное РЕПО, если вы запустите команду rebase
$ git push -f
$ git push -f origin master
если ваша главная ветвь
git logвыглядит примерно так:commit ac72a4308ba70cc42aace47509a5e Author: <[email protected]> Date: Tue Jun 11 10:23:07 2013 +0500 Added algorithms for Cosine-similarity commit 77df2a40e53136c7a2d58fd847372 Author: <[email protected]> Date: Tue Jun 11 13:02:14 2013 -0700 Set stage for similar objects commit 249cf9392da197573a17c8426c282 Author: Ralph <[email protected]> Date: Thu Jun 13 16:44:12 2013 -0700 Fixed a bug in space world automationи вы хотите объединить два верхних коммита, просто выполните следующие простые шаги:
- во-первых, чтобы быть на безопасной стороне проверки второй последний фиксации в отдельной ветке. Вы можете назвать ветку чем угодно.
git checkout 77df2a40e53136c7a2d58fd847372 -b merged-commits- теперь, просто вишня-выберите свои изменения из последнего фиксации в эту новую ветку как:
git cherry-pick -n -x ac72a4308ba70cc42aace47509a5e. (Разрешить конфликты, если они возникают)- так что теперь, ваш изменения в последнем коммите есть в вашем втором последнем коммите. Но вам все равно нужно совершить, поэтому сначала добавьте изменения, которые вы просто выбрали, а затем выполните
git commit --amend.вот и все. Вы можете нажать эту объединенную версию в ветке "merged-commits", если хотите.
кроме того, теперь вы можете отказаться от двух коммитов спина к спине в своей главной ветви. Просто обновите свою главную ветку как:
git checkout master git reset --hard origin/master (CAUTION: This command will remove any local changes to your master branch) git pull
С
git cherry-pickдля почти всего, для меня это естественно сделать даже здесь.учитывая, что у меня есть
branchXпроверено и есть два коммита на кончике его, из которых я хочу создать один коммит, объединяющий их содержимое, я делаю это:git checkout HEAD^ // Checkout the privious commit git cherry-pick --no-commit branchX // Cherry pick the content of the second commit git commit --amend // Create a new commit with their combined contentесли я хочу обновить
branchXа также (и я полагаю, что это обратная сторона этого метода) я также должен:git checkout branchX git reset --hard <the_new_commit>
Если вы хотите объединить два последних коммита и просто использовать сообщение старого коммита, вы можете автоматизировать процесс с помощью
expect.Я предполагаю, что:
- вы используете vi в качестве редактора
- ваши коммиты состоят из одной строки каждый
Я тестировал с
git version 2.14.3 (Apple Git-98).
#!/usr/bin/env expect spawn git rebase -i HEAD~2 # down, delete word, insert 's' (for squash), Escape, save and quit send "jdwis 3:wq\r" expect "# This is a" # down 4, delete 3 lines, save and quit send "4j3d\r:wq\r" interact
Comments