Что говорится в итоговом сообщении, когда вы нажимаете «Разрешить отдельный конфликт»? Если ваши слияния из Current -> Experimental были выполнены без серьезной ручной работы, это должно быть что-то вроде «X источник, 0 цель, Y оба, 0 конфликтуют». Другими словами, в целевом (текущем) файле нет блоков содержимого, которых нет в копии исходной ветки (экспериментальный). Вы можете смело использовать кнопку AutoMerge All.
Примечание. AutoMerge должен быть безопасным в любом случае. Он оптимизирован для консервативного подхода к ранним предупреждениям, а не для того, чтобы разрешить все случаи. Но я понимаю, что многие из нас, в том числе и я, любят запускать инструмент слияния, когда возникают какие-либо вопросы. В описанном сценарии, ИМО, даже самые пугливые могут отдыхать спокойно.
Почему вообще возникает конфликт? А что, если итоговое сообщение не настолько банально? Рад, что вы спросили :) Короткий ответ - потому что вычисление, которое определяет общего предка («базу») связанных файлов, сильно зависит от того, как были разрешены предыдущие конфликты слияния между ними. Простой пример:
- создать два филиала, A и B.
- вносить правки в A \ foo.cs и B \ foo.cs в отдельных частях файла
- объединить A -> B
- AutoMerge конфликт
- слить B -> A
TFS должна пометить эту последовательность событий как конфликтующую. Ближайший общий предок между B \ foo.cs; 4 и A \ foo.cs; 2 находится на шаге 1, и с тех пор обе стороны, очевидно, изменились.
Заманчиво сказать, что A и B синхронизированы после шага 4. (Точнее: общим предком для слияния шага 5 является версия №2). Несомненно, успешное слияние контента подразумевает, что B \ foo.cs содержит все изменения, внесенные на сегодняшний день? К сожалению, есть ряд причин, по которым вы не можете этого предполагать:
Общее: не все конфликты можно объединить с помощью AutoMerged. Вам нужны критерии, применимые к обоим сценариям.
Корректность: даже если AutoMerge завершается успешно, он не всегда генерирует действительный код. Классический пример возникает, когда два человека добавляют одно и то же поле в разные части определения класса.
Гибкость: у каждого пользователя системы управления версиями есть свои любимые инструменты слияния. И им нужна возможность продолжить разработку / тестирование между первоначальным решением Resolve [«когда-нибудь нужно как-нибудь объединить содержимое»] и окончательной проверкой [«здесь, это работает»].
Архитектура: в централизованной системе, такой как TFS, сервер просто не может доверять ничему, кроме своей собственной базы данных + требований проверки API. Пока входные данные соответствуют спецификации, серверу не следует пытаться различать, как выполнялись различные типы слияния контента. (Если вы думаете, что сценарии до сих пор легко различимы, подумайте: что, если в движке AutoMerge есть ошибка? Что, если мошеннический клиент вызывает веб-службу напрямую с произвольным содержимым файла? Здесь только поверхностно ... серверы должны быть скептически настроены по какой-то причине!) Все, что он может безопасно вычислить, - это вы отправили мне результирующий файл, который не соответствует исходному или целевому.
Собрав эти требования вместе, вы получите дизайн, который объединяет наши действия на шаге 4 в довольно широкую категорию, которая также включает ручные слияния, возникающие в результате перекрывающихся правок, слияния контента [автоматически или нет], предоставляемые сторонними инструментами, и файлы вручную. отредактировал постфактум. В терминологии TFS это разрешение AcceptMerge. Будучи записанными как таковые, Правила слияния (TM) должны предполагать худшее в погоне за исторической целостностью и безопасностью будущих операций. В процессе ваши семантические намерения для Шага 4 («полностью включить в B каждое изменение, которое было внесено в A в # 2») были упрощены до нескольких байтов чистой логики («дать B следующее новое содержимое + кредит за обработку # 2 "). К сожалению, это «просто» проблема UX / образования. Люди сильно злятся, когда Правила слияния делают неверные предположения, которые приводят к поломке кода и потере данных. Напротив, все, что вам нужно сделать, это нажать кнопку.
FWIW, у этой истории есть много других концовок. Если вы выбрали «Копировать из исходной ветки» [aka AcceptTheirs] на шаге 4, на шаге 5 не возникнет конфликта. То же самое, если вы выбрали разрешение AcceptMerge, но случайно зафиксировали файл с тем же хешем MD5, что и A \ foo.cs; 2 . Если вместо этого вы выберете Keep Target [aka AcceptYours], последующие последствия снова изменятся, хотя я не могу вспомнить детали прямо сейчас. Все вышеперечисленное становится довольно сложным, когда вы добавляете другие типы изменений (особенно Rename), объединяете ветки, которые гораздо более несинхронизированы, чем в моем примере, вишня выбирает определенные диапазоны версий и обрабатывает сироты позже и т. Д.
РЕДАКТИРОВАТЬ: по воле судьбы кто-то другой задал точно такой же вопрос на форуме MSDN. Как обычно, я написал им еще один длинный ответ, который оказался совершенно другим! (хотя, очевидно, затрагивая те же ключевые моменты) Надеюсь, это поможет: http://social.msdn.microsoft.com/Forums/en-US/tfsversioncontrol/thread/e567b8ed-fc66-4b2b-a330-7c7d3a93cf1a
person
Richard Berg
schedule
18.09.2009