Git - установка родителя фиксации без переустановки
Я использовал git-svn
для создания зеркала git репозитория SVN. Структура внутри SVN была немного нестандартной, поэтому git создала ветвь, которая не имеет общей фиксации с ветвью master
.
A---B---C topic
D---E---F---G master
Я знаю, что commit A
основан на commit E
, и я довольно уверен, что исправил проблемы, вызывающие git, чтобы не распознавать этот факт (используя filter-branch
). То, что я хочу сделать, это повторно присоединить topic
к ветке master
, установив E
в качестве родителя A
:
A---B---C topic
/
D---E---F---G master
git-rebase
, похоже, не работает для меня, потому что diff для commit A
перечисляет создание большого количества файлов, которые уже существуют в master
, что приводит к огромному количеству конфликтов.
Из моего понимания git просто установка E
, поскольку родительский элемент A
должен быть достаточным для решения всех проблем.
Это возможно? Если да, то как я могу это сделать?
Ответы
Ответ 1
Посмотрите на трансплантаты (файл трансплантата можно найти в .git/info/grafts
). Формат довольно прост:
<commit sha1> <parent1 sha1> <parent2 sha1> … <parentN sha1>
Это означает, что git считает, что у фиксации есть разные родители, чем есть на самом деле. Используйте фильтр-ветвь, чтобы сделать трансплантаты постоянными (так что файл графтов можно удалить):
git filter-branch --tag-name-filter cat -- --all
Обратите внимание, что эта перезаписывает историю в репозитории, поэтому ее нельзя использовать в общих репозиториях!
Если вы хотите только переписать историю коммитов, которые были перенесены на главную ветвь, например, используйте следующую команду:
git filter-branch --tag-name-filter cat -- master..
Ответ 2
Основываясь на ваших диаграммах (хотя меня беспокоит то, что вы подразумеваете под "Я довольно уверен, что исправил проблемы, вызывающие git, чтобы не распознавать этот факт (используя filter-branch
)." ) вы должны сделать что-то вроде следующего.
# checkout A
git checkout A
# Reset the branch pointer to E so that E is the parent of the next commit
# --soft ensures that the index stays the same
git reset --soft E
# Remake the commit with the E as the parent, re-using the old commit metadata
git commit -C [email protected]{1}
# Rebase the topic branch onto the modified A commit (current HEAD)
git rebase --onto HEAD A topic
Ответ 3
Все, что вам нужно, это:
git rebase --root --onto master^^ topic^^ topic
параметр root позволяет включать A.
UPDATE:
Добавьте параметр --preserve-merges
, если вы хотите сохранить разветвление и слияние части, которую вы перегружаете.