При объединении ветки темы "B" в "A" с помощью git merge
возникают конфликты. Я знаю, что все конфликты могут быть решены с помощью версии в "B".
Я в курсе git merge -s ours
. Но я хочу что-то вроде git merge -s theirs
.
Почему его не существует? Как я могу достичь того же результата после конфликтующего слияния с существующими git
командами? ( git checkout
каждый распакованный файл из B)
ОБНОВЛЕНИЕ: «Решение» простого отказа от чего-либо из ветви A (точка фиксации слияния до версии B дерева) не является тем, что я ищу.
git merge -s their
.git merge -s theirs
(что может быть легко достигнуто сgit merge -s ours
помощью временной ветки), поскольку -s наша полностью игнорирует изменения ветви слияния-от ...theirs
в дополнение кours
??? Это признак одной из проблем проектирования и проектирования высокого уровня в Git: несогласованность.Ответы:
Добавьте
-X
опцию вtheirs
. Например:Все слится желаемым образом.
Единственное, что я видел, вызывает проблемы, если файлы были удалены из BranchB. Они появляются как конфликты, если удаление выполнено чем-то другим, кроме git.
Исправить легко. Просто запустите
git rm
с именем любых файлов, которые были удалены:После этого
-X theirs
должна работать как положено.Конечно, выполнение фактического удаления с помощью
git rm
команды предотвратит конфликт в первую очередь.Примечание . Также существует более длинный вариант формы.
Чтобы использовать его, замените:
с:
источник
theirs
». -Xtheirs - вариант стратегии, применяемый к рекурсивной стратегии . Это означает, что рекурсивная стратегия по-прежнему объединит все, что может, и в случае конфликтов вернется к «своей» логике. Хотя это то, что нужно в большинстве случаев, как описано выше, это не то же самое, что «просто взять все из ветви B как есть». В любом случае, он выполняет реальное слияние.Возможное и проверенное решение для объединения ветки B в нашу проверенную ветку A:
Чтобы автоматизировать это, вы можете заключить его в скрипт, используя в качестве аргументов branchA и branchB.
Это решение сохраняет первого и второго родителя коммита слияния, как и следовало ожидать
git merge -s theirs branchB
.источник
git reset --soft branchA
?git reset --hard
изменения, на которыеbranchA
указывает фиксация .Более старые версии git позволяли вам использовать «их» стратегию слияния:
Но с тех пор это было удалено, как объяснено в этом сообщении Джунио Хамано (сопровождающий Git). Как отмечено в ссылке, вместо этого вы должны сделать это:
Остерегайтесь, однако, что это отличается от фактического слияния. Ваше решение, вероятно, является вариантом, который вы действительно ищете.
источник
git reset --hard origin
решение для их слияния стиля? Если бы я хотел объединить BranchB с BranchA (как в ответе Алана У. Смита), как бы я это сделал, используяreset
метод?git reset --hard
, чтобы «объединить их». Конечно,git reset --hard
не создает никакого коммита слияния или коммитов в этом отношении. Он считает, что мы не должны использовать слияние для замены чего-либо в HEAD чем-то другим. Я не обязательно согласен, хотя.theirs
было удалено, потому что обоснование было неполным. Не удалось учесть те случаи, когда код хорош, просто восходящий поток поддерживается на другой философской основе, поэтому в этом смысле он «плохой», так что каждый хочет быть в курсе восходящего потока, но в то же время сохраните хорошие исправления кода [у git & msysgit есть некоторые из этого 'конфликта' из-за философии их различных целевых платформ]theirs
потому что я случайно изменил некоторые файлы в двух отдельных ветвях и хотел отменить изменения одного без необходимости делать это вручную для каждого файла.Не совсем ясно, каков ваш желаемый результат, поэтому существует некоторая путаница в отношении «правильного» способа сделать это в ответах и их комментариях. Я пытаюсь дать обзор и вижу следующие три варианта:
Попробуйте объединить и использовать B для конфликтов
Это не «их версия для
git merge -s ours
», а «их версия дляgit merge -X ours
» (что сокращенноgit merge -s recursive -X ours
):Вот что делает, например , ответ Алана У. Смита .
Использовать только контент из B
Это создает коммит слияния для обеих веток, но отбрасывает все изменения
branchA
и только сохраняет содержимоеbranchB
.Обратите внимание, что слияние совершает первый родительский элемент теперь
branchB
и только от второгоbranchA
. Вот что делает, например , ответ Gandalf458 .Используйте контент только из B и сохраняйте правильный родительский порядок
Это настоящая "их версия для
git merge -s ours
". Он имеет то же содержание, что и в предыдущем варианте (т. Е. Только изbranchB
), но порядок родителей правильный, т. Е. Первый родительbranchA
и второйbranchB
.Это то, что делает ответ Пола Пладийса (не требуя временной ветки).
источник
git checkout branchA; git merge -s ours --no-commit branchB; git read-tree -um @ branchB; git commit
read-tree
, к которой средний пользователь git может не привыкнуть (по крайней мере, я не так ;-)). Решения в ответе используют только высокоуровневые («фарфоровые») команды, которые должны знать большинство пользователей git. Я предпочитаю их, но тем не менее спасибо за вашу версию!…commit --amend…
), будет «потерян». Я планирую добавить некоторые графические объяснения к этому ответу, как только у меня будет время, чтобы сделать их… ;-)С тех пор я использовал ответ от Поля Пладийса. Я обнаружил, что вы можете сделать "нормальное" слияние, конфликты происходят, так что вы делаете
разрешить конфликт с помощью ревизии из другой ветки. Если вы сделаете это для каждого файла, у вас будет то же поведение, которое вы ожидаете от
Во всяком случае, усилия больше, чем было бы со стратегией слияния! (Это было протестировано с git версии 1.8.0)
источник
git ls-files --modified | xargs git add
я хотел сделать это для добавления с обеих сторон слияния: /git ls-files --modified
так что я думаю, что это также жизнеспособное решение.git config --global alias.unresolved '!git status --short|egrep "^([DAU])\1"'
-X
и в чем разница между-X
и-s
? не могу найти ни одного документа.Я решил свою проблему, используя
источник
Я предполагаю, что вы создали ветку от master и теперь хотите объединиться с master, переопределяя все старые вещи в master. Это именно то, что я хотел сделать, когда наткнулся на этот пост.
Делайте именно то, что вы хотите сделать, за исключением того, что сначала объедините одну ветку с другой. Я только что сделал это, и это сработало отлично.
Затем извлеките мастер и объедините в нем свою ветку (теперь все пройдет гладко):
источник
Если вы находитесь на ветке А, сделайте:
Протестировано на git версии 1.7.8
источник
Чтобы действительно правильно выполнить слияние, которое принимает только вход из ветви, которую вы объединяете, вы можете сделать
git merge --strategy=ours ref-to-be-merged
git diff --binary ref-to-be-merged | git apply --reverse --index
git commit --amend
В любом сценарии, о котором я знаю, не будет конфликтов, вам не нужно создавать дополнительные ветви, и это действует как обычный коммит слияния.
Однако это не очень хорошо работает с подмодулями.
источник
Хотя я упоминаю в « git command для создания одной ветви как другую », как имитировать
git merge -s theirs
, обратите внимание, что Git 2.15 (Q4 2017) теперь более понятен:Посмотреть коммит c25d98b (25 сентября 2017 г.) Junio C Hamano (
gitster
) .(Объединено Junio C Hamano -
gitster
- в коммите 4da3e23 , 28 сентября 2017 г.)-Xtheirs
является вариантом стратегии применительно к рекурсивным стратегии. Это означает, что рекурсивная стратегия по-прежнему объединит все, что может, и будет использоватьtheirs
«логику» только в случае конфликтов.Это дебаты на уместность или нет
theirs
стратегии слияния были недавно возвращены в этой теме в сентябре 2017 года .Это признает старые (2008) темы
Упоминается псевдоним:
Ярослав Хальченко пытается отстаивать эту стратегию еще раз, но Хунио С. Хамано добавляет :
Джунио добавляет, как прокомментировал Майк Битон :
источник
git merge -s ours <their-ref>
фактически он говорит: «пометить коммиты, сделанные до <its-ref> на их ветке, как коммиты, которые следует постоянно игнорировать» «; и это важно, потому что, если вы впоследствии объединитесь с более поздними состояниями их ветви, их более поздние изменения будут внесены без внесенных игнорируемых изменений.См . Широко цитируемый ответ Хунио Хамано : если вы собираетесь отказаться от зафиксированного контента, просто откажитесь от коммитов или, во всяком случае, не допускайте его в основную историю. Зачем беспокоить всех в будущем, читая сообщения коммитов от коммитов, которым нечего предложить?
Но иногда возникают административные требования или, возможно, какая-то другая причина. Для тех ситуаций, когда вам действительно нужно записывать коммиты, которые ничего не вносят, вы хотите:
(правка: вау, мне раньше удалось ошибиться. Это работает.)
источник
Этот использует дерево чтения команды git plumbing, но сокращает общий рабочий процесс.
источник
Это объединит ваш новый филиал с существующим базовым.
источник
git commit --amend
в конец вашего примера, иначе пользователи могут увидеть коммит слияния сgit log
и предположить, что операция завершена.Я думаю, что вы на самом деле хотите:
Это кажется неуклюжим, но это должно работать. Единственное, что мне действительно не нравится в этом решении, это то, что история git будет сбивать с толку ... Но, по крайней мере, история будет полностью сохранена, и вам не нужно будет делать что-то особенное для удаленных файлов.
источник
Эквивалент (сохраняющий родительский порядок) «git merge -s itss branchB»
Перед слиянием:
!!! Убедитесь, что вы в чистоте!
Сделать слияние:
Что мы сделали ? Мы создали новый коммит, у которого два родителя - наш и их, а коннект коммита - BranchB - их
После слияния:
Точнее:
источник
Этот ответ дал Пол Пладийс. Я просто взял его команды и сделал псевдоним для удобства.
Отредактируйте ваш .gitconfig и добавьте следующее:
Затем вы можете "git merge -ssis A", выполнив:
источник
Я только недавно должен был сделать это для двух отдельных репозиториев, которые имеют общую историю. Я начал с:
Org/repository1 master
Org/repository2 master
Я хотел, чтобы все изменения
repository2 master
были примененыrepository1 master
, принимая все изменения, которые вносит репозиторий2. С точки зрения git, это должна быть стратегия, которая называется-s theirs
НО, которой не существует. Будьте осторожны, потому что-X theirs
названо так, как будто это то, что вы хотите, но это НЕ то же самое (об этом даже говорится на странице руководства).Я решил это, чтобы пойти
repository2
и создать новую веткуrepo1-merge
. В той ветке я бегалgit pull git@gitlab.com:Org/repository1 -s ours
и она сливается нормально без проблем. Я тогда толкаю это к пульту.Затем я возвращаюсь
repository1
и создаю новую веткуrepo2-merge
. В этой ветке я бегуgit pull git@gitlab.com:Org/repository2 repo1-merge
которая будет завершена с проблемами.Наконец, вам нужно будет либо выполнить запрос на слияние,
repository1
чтобы сделать его новым мастером, либо просто оставить его как ветвь.источник
Простой и интуитивно понятный (на мой взгляд) двухэтапный способ сделать это
с последующим
(который отмечает две ветви как объединенные)
Единственным недостатком является то, что он не удаляет файлы, которые были удалены в BranchB из вашей текущей ветви. Простая разница между двумя ветками позже покажет, есть ли такие файлы.
Этот подход также дает понять из журнала изменений после того, что было сделано - и что было задумано.
источник