Несколько раз в прошлом у нас возникала проблема, когда разработчики (явно или фактически) выполняли git merge -s ours
, когда они не должны были этого делать, коммиты были потеряны, и мы обнаружили это намного позже, когда очистка намного сложнее и требует больше времени. Тесты не провалились, потому что сами коммиты, которые добавили тесты, были молча отменены вместе с кодом, который они тестировали.
Что я хотел бы сделать, так это найти или создать инструмент, который резюмирует слияние, производя вывод, подобный следующему, при обычном слиянии:
Lines Left(2b3c4d) Right(3c4d5e)
Common with base 970 930
Unique wrt base 20 50
Unique wrt other 15 45
Unique wrt merge 15 45
Common with merge 995 985
Но в случае, когда слияние было выполнено неправильно, отменяя многие изменения, или когда было выполнено git merge -s ours
, это может привести к появлению примерно такого отчета:
Lines Left(2b3c4d) Right(3c4d5e)
Common with base 970 930
Unique wrt base 20 50
Unique wrt other 15 45
Unique wrt merge 15 0 !!
Common with merge 990 935
Warning: 100% of changes from 3c4d5e are missing from merge commit!
Если бы этот отчет запускался для каждой фиксации, мы могли бы помечать (с помощью задания jenkins) каждый раз, когда слияние было немного вонючим.
До сих пор я играл с git diff --stat
, git diff --name-status
и git diff --summary
, но пока ни один из них не дал мне того, что я хочу.
Лучшее, что я могу сделать до сих пор, приведет к чему-то вроде следующего для обычного слияния:
base..left base..right left..merge right..merge
f67c4..a9eb4 f67c4..5b592 a9eb4..cb209 5b592..cb209
a | 1 + 1 +
b | 1 + 1 +
base | 1 + 1 + 1 + 1 +
changed 2 2 2 2
insertions(+) 2 2 2 2
deletions(-) 0 0 0 0
и для слияния ours
:
base..left base..right left..merge right..merge
f67c4..a9eb4 f67c4..5b592 a9eb4..95637 5b592..95637
a | 1 + 1 -
b | 1 + 1 +
base | 1 + 1 + 2 +-
changed 2 2 0 3
insertions(+) 2 2 0 2
deletions(-) 0 0 0 2
Обратите внимание, что я не только хочу обнаружить -s ours
слияние, я также хочу поймать ситуацию, когда некоторые, но не все изменения находятся в результирующем слиянии. Это более общий случай обнаружения ошибочных слияний, чем просто проверка одной конкретной причины потерянных изменений.
Кроме того, кажется, что это происходит только тогда, когда в слиянии возникают конфликты, поэтому любой метод, который требует повторного автоматического запуска слияния, также должен автоматически разрешать эти конфликты.
Наконец, я хотел бы иметь возможность запускать эту сводную утилиту в грязном репо, не сохраняя сначала все мои изменения, отсюда и мои текущие эксперименты с git diff
.
Любые предложения относительно того, как я могу получить информацию такого рода более непосредственно, чем сценарий с большим количеством синтаксического анализа и переформатирования, будут оценены.
Ближайшие существующие вопросы, которые я могу найти к этому: Обнаружение слияния, сделанного '-s ours' (но единственный ответ там не помогает) и "git merge -s ours" и как показать разницу (но есть ответов вообще нет).
-s ours
слияние — запустить сравнение обоих родителей коммита слияния. Если один diff пустой, а родители различны, это верный признак того, что было выполнено-s ours
(или эквивалентное). Например, вы можете перебрать$(git show --pretty=%P $commit)
и предупредитьif ! git diff -s --exit-code $parent..$commit
. - person user4815162342   schedule 20.01.2015git diff --stat
дляbase..left
,base..right
,left..merge
иright..merge
. Кроме того, я не хочу предполагать слияние-s ours
между прочим, я также хочу поймать ситуацию, когда некоторые, но не все изменения находятся в результирующем слиянии. Я обновил свой вопрос, чтобы сделать оба более понятными. - person Mark Booth   schedule 20.01.2015git checkout <left>; git merge -s recursive -X ours <right>; git diff <merge>
и сравнить его сgit checkout <right>; git merge -s recursive -X ours <left>; git diff <merge>
, чтобы найти уникальное и обычное. - person Mark Booth   schedule 20.01.2015git diff
покажет вам, как они были разрешены. - person Tavian Barnes   schedule 20.01.2015