Комментарии (1)
Ответ сгенерирован нейросетью и может содержать ошибки
Как изменится история комитов при rebase
Rebase — это одна из наиболее важных операций в Git, которая кардинально меняет историю коммитов. Давайте разберёмся детально, что происходит при этой операции.
Базовое понимание rebase
Rebase переписывает историю коммитов, перемещая серию коммитов на новое основание (base). Это сильно отличается от merge, который создаёт коммит слияния.
Представь ситуацию:
До rebase:
master: A --- B --- C
\
feature: D --- E --- F
После rebase:
master: A --- B --- C
\
feature: D' --- E' --- F'
Как видишь, коммиты D, E, F полностью переписаны — получены новые хэши (D', E', F'), потому что изменился их parent коммит.
Что именно меняется при rebase
1. Хэши коммитов
При rebase каждый коммит получает новый хэш, потому что в его метаданные входит хэш родительского коммита:
# Упрощённое представление хэша коммита
hash = SHA1(
tree_hash +
parent_hash + # Изменилось при rebase!
author_timestamp +
message
)
2. Родительские коммиты
Каждый коммит переписывается с новым родителем — вместо B становится C:
# До rebase
git log feature --oneline
F # parent: E
E # parent: D
D # parent: B
# После rebase на C
git log feature --oneline
F' # parent: E'
E' # parent: D'
D' # parent: C (было B)
3. Порядок и последовательность коммитов
Порядок коммитов в ветке остаётся прежним, но они физически переместились на новое основание. Это очень важно — rebase НЕ меняет логический порядок коммитов, только их положение на графе.
Интерактивный rebase (git rebase -i)
Это мощный инструмент для переписания истории:
# Переписывание последних 3 коммитов
git rebase -i HEAD~3
В интерактивном режиме ты можешь:
# pick — оставить коммит как есть
pick D "Add feature X"
# reword — оставить коммит, но изменить сообщение
reword E "Fix bug in feature X"
# squash — объединить с предыдущим коммитом
squash F "Cleanup"
# drop — удалить коммит
drop D "WIP: not ready"
# fixup — как squash, но без объединения сообщений
fixup F "Fix typo"
Rebase с разрешением конфликтов
При rebase часто возникают конфликты:
# Начинаем rebase
git rebase origin/master
# Если есть конфликты:
# 1. Разрешаешь конфликты в файлах
# 2. Добавляешь файлы
git add .
# 3. Продолжаешь rebase
git rebase --continue
# Или отменяешь операцию
git rebase --abort
Последствия rebase
Плюсы:
- Линейная история — история коммитов остаётся прямолинейной и простой для чтения
- Чистые PR — базированные на актуальной ветке, без merge-коммитов
- Легче отследить баги — с помощью
git bisectв линейной истории
Минусы:
- Переписываешь историю — опасно для shared веток (master, main)
- Сложнее отследить слияния — теряется информация о том, как ветки взаимодействовали
- Force push требуется — после rebase нужен
git push --force-with-lease
Ключевое правило
НИКОГДА не делай rebase на shared ветках (master, main, develop). Если ты перепишешь историю, у других разработчиков будут очень неприятные конфликты при pull.
# Плохо — никогда так не делай!
git checkout master
git rebase origin/develop
git push --force
# Хорошо — rebase на feature-ветках
git checkout feature/my-feature
git rebase origin/master
git push --force-with-lease
Когда использовать rebase vs merge
# Используй MERGE для:
# - Слияния feature-веток в master
# - Сохранения полной истории слияния
# - Shared веток (master, develop)
git merge feature/my-feature
# Используй REBASE для:
# - Актуализации feature-ветки перед PR
# - Очистки локальной истории
# - Интерактивного редактирования коммитов
git rebase origin/master