Привет, Мир!
Данная статья — перевод статьи — Split a commit in two with Git, так что, если хотите прочитать ее на английском — добро пожаловать к первоисточнику. Перевод я постарался сделать максимально понятным и слегка облагородил его изображениями, для лучшего восприятия. Приятного чтения!
Когда-нибудь задумывались о том, чтобы сделать два коммита из одного?
Может быть несколько причин по которым вы хотели бы разделить коммит на несколько:
- это может сделать историю изменений читабельнее
- вы пытаетесь реорганизовать некоторые коммиты и это создает неприятные конфликты
- просто потому что
Соединить два коммита в один легко: поищите информацию о сквошинге (squash commits). Хоть я и относительно неплохо разбираюсь в гите, я не знал как сделать обратное (разделить коммит на несколько) — до сегодняшнего дня.
TLDR;
Давайте посмотрим на последовательность перед тем как объяснять ее:
git rebase -i <oldsha1> # <oldsha1> здесь — хэш коммита, до которого мы будем изменять нашу историю
# отмечаем с помощью edit нужные нам коммиты (заменить ‘pick’ перед коммитомgit reset HEAD^git add ...git commit -m "первый коммит"git add ...git commit -m "второй коммит"
...git add ...git commit -m "Nый коммит"git rebase --continue
Что же мы сделали?
Детальное объяснение
Интерактивное перебазирование (interactive rebase)
Команда git rebase -i <oldsha1> открывает список коммитов начная с oldsha1 до последнего коммита в ветке. Вы можете:
- переопределить их порядок,
- изменить сообщение коммита,
- объединить два коммита вместе (squash),
- отредактировать коммит,
и многое другое
Мы используем редактирование (edit) в нашем случае, потому что мы хотим изменить коммит (разделить его на двое). Просто замените pick на edit на строке коммита, который вы хотите разделить. Когда вы сохраните и закроете этот «файл», вы будете на коммите, помеченном edit, либо другой коммандой.

Отменить текущий коммит
Если вы выполните команду git status, вы увидите, что гит «поставил» вас сразу после коммита. Что мы хотим, так это отменить этот коммит и сделать другие изменения (возможно просто разделить коммит на несколько).

git log покажет что самый последний коммит — тот что был помечен с помощью editИменно для этого и нужна команда git reset HEAD^: она возвращает нас в состояние ДО коммита и оставляет изменения сделанные в коде. HEAD^ значит — коммит в HEAD минус 1, что и будет состоянием до нашего коммита, помеченного с помощью edit.
Создайте два или несколько коммитов
Дальше просто используйте гит как обычно — изменяйте файлы, добавляйте файлы и делайте коммиты.

git reset HEAD^ я сделал четыре коммитаЗавершите интерактивное перебазирование
Убедитесь, что завершили интерактивное перебазирование вызвав команду git rebase --continue. Внимание! убедитесь что у вас не осталось неотредактированных файлов перед вызовом этой команды.
После того как эта команда отработает все ваши изменения отразятся на истории коммитов.

git rebase --continue состояние возвращается в конец, при этом все примененные в перебазировании изменения остаются на местеЕще несколько советов
Редактирование коммитов можно сделать еще мощнее, если вы знаете как добавить изменения части файла, вместо целого файла.
Магический инструмент для этого git add -p path/to/myfile. Минус этого инструмента в том, что он использует командную строку и может быть непонятен/неприятен внешне/другая причина (нужное подчеркнуть) если вы не очень хорошо работаете с консолью. Автор статьи рекомендует использовать UI-инструменты для этого
Другой интересный совет для людей, которые работают над ветками, сделанными от мастер векти (или любой другой). Вы можете использовать команду rebase c названием ветки вместо oldsha1 коммита — git rebase -i master. Эта команда выдаст список коммитов между мастер веткой и вашей веткой.
Заключение
Как видим, интерактивное перебазирование довольно мощный инструмент, и если вместе с ним применять другие инструменты git’а, то мы можем творить чудеса с историей коммитов.
Данная статья помогла мне в работе, надеюсь ее перевод поможет вам! Удачи, и никогда не останавливайтесь в улучшении своих навыков!
Больше статей в моем блоге. Чтобы быть в курсе событий, подписывайтесь на мои профили в социальных сетях — там я выкладываю анонсы статей и сами статьи.
