Модуль 5: Перебазирование (Rebase) — «золотая» тема
Rebase позволяет переписать историю, сделав её линейной. Это мощный инструмент, который требует дисциплины.
Сильная сторона rebase — в том, что он помогает рассказывать историю так, будто она писалась «без лишних ответвлений». Это упрощает чтение лога и поиск причин изменений, но повышает требования к аккуратности.
5.1 Rebase vs Merge
- Merge сохраняет историю ветвления, создаёт merge‑коммит
- Rebase переносит ваши коммиты поверх другой базы, выпрямляя историю
Минус rebase: переписывает хеши — не делайте rebase на публичных ветках.
Думайте о rebase как о «переозвучке» сюжета: содержание остаётся, но линия повествования выпрямляется. Делайте это там, где вы контролируете аудиторию — в своих ветках до публикации.
5.2 Интерактивный rebase
# Перенести текущую ветку поверх main
git fetch origin
git rebase origin/main
# Интерактивный rebase последних N коммитов
git rebase -i HEAD~5
# Доступные операции в редакторе:
# pick — использовать коммит как есть
# reword — изменить сообщение
# edit — остановиться и изменить коммит
# squash — объединить с предыдущим
# drop — удалить коммит
Интерактивный режим — это редактор истории: вы можете переименовывать, объединять и переставлять коммиты так, чтобы итог читался логично. Договоритесь в команде о правилах «уборки» и придерживайтесь их.
5.3 Конфликты при rebase
# Разрешите конфликт в файлах, затем:
git add path/to/file
# продолжить rebase
git rebase --continue
# пропустить проблемный коммит
git rebase --skip
# прервать rebase
git rebase --abort
5.4 Важные правила
- Не делайте rebase веток, опубликованных и используемых другими
- Перед rebase обновляйте базу:
git fetch
- Для синхронизации локальной ветки с удалённой предпочитайте
git pull --rebase
Правило простое: переписывайте только «своё» и только до публикации. После того как коммиты стали основой чужой работы, история превращается в контракт.
5.5 Практика: «почистить» историю перед merge
- Сделайте несколько логичных коммитов
- Объедините «мусорные» коммиты через
squash
- Переименуйте сообщения через
reword
по стилю Conventional Commits - Проверьте историю:
git log --oneline
Цель «уборки» — не переписать прошлое ради эстетики, а сделать историю полезной: читатель должен быстро понять замысел и ход мысли автора изменений.
5.6 autosquash и --fixup
--autosquash
автоматически переупорядочит коммиты fixup!
/squash!
при интерактивном rebase, ускоряя «уборку» истории. Пара --fixup
/--squash
при коммите помечает цель слияния.
5.7 Сохранение ветвлений: --rebase-merges
Опция позволяет переписывать историю с сохранением структуры merge‑коммитов, что полезно в сложных ветвлениях.
5.8 Автообновление ссылок: --update-refs
Автоматически обновляет связанные ссылки (например, локальные ветки/refs), уменьшая риск расхождений после rebase.
5.9 Публичная история и reflog
Переписывание общедоступных веток опасно: ломает ссылки у коллег. reflog
сохраняет локальные перемещения HEAD
, что помогает «откатить» неудачный rebase. Однако reflog — локален и имеет сроки хранения.
5.10 Rebase в монорепозиториях
В монорепо rebase может влиять на множество подпроектов. Используйте частичные выборки, sparse-checkout
, аккуратно управляйте зависимостями и соблюдайте командные политики.