Проблемы слияния в mercurial из-за неправильной базы слияния: что происходит?

У меня есть репозиторий, в котором две ревизии (14321 и 14319) имеют общий родитель (14318) — оба набора изменений являются прямыми дочерними элементами 14318. Тем не менее, запрос набора ревизий ancestor(14321, 14319) нет возвращает 14318, но вместо этого возвращает гораздо более старый набор изменений. Что происходит?

Скриншот в TortoiseHg:

Диаграмма, показывающая нечетные результаты предка запроса (14321, 14319)

Предыстория: недавно я столкнулся со странными конфликтами слияния, которые, как оказалось, были вызваны попыткой Mercurial повторно применить изменения, которые уже были слиты. Я смог отследить это до странного выбора базы слияния, из-за которого обе головы включали одни и те же изменения, но я не понимаю, почему это произошло и как я могу предотвратить это в будущем (я выбрал DVCS отчасти, чтобы избежать такие проблемы в первую очередь...)


person Eamon Nerbonne    schedule 13.02.2013    source источник


Ответы (3)


На картинке видно, что есть не один, а два общих предка. Таким образом, это похоже на случай перекрестного слияния, когда проблемы слияния возникают из-за выбора того или иного общего предка.

Использованная литература:

Есть предложение по новому алгоритму слияния (https://www.mercurial-scm.org/wiki/ConsensusMerge). Однако после спринта Mercurial 2.3 эта тема застряла.

Чтобы уменьшить количество подобных проблем, я предлагаю вам установить топологию клиент-сервер, чтобы разработчики сливались только с официальным репозиторием. Возможно, перебазирование также может помочь.

Крест-накрест слияние выглядит примерно так:

   B --- D
  / \   / \
 /   \ /   \ 
A     X     F 
 \   / \   /
  \ /   \ /
   C --- E

В вашем случае это было:

           B
-----------o----               } stable/production
      C     \   \       F
------o------o---\------o      } default
       \     D    \    /
        -----------o---        } feature
                   E

A = ?
B = 14318
C = 14294
D = 14319
E = 14321
F = ?

Для производства F есть две возможные схемы: B-D-E-F и C-D-E-F. Компания Mercurial выбрала последнее.

Вы могли бы избежать пересечения, если бы не объединили производственную и функциональную ветки. Исправление могло быть распространено на ветку функций через ветку по умолчанию. Журнал будет:

           B
-----------o               } stable/production
      C     \       F
------o------o------o      } default
       \    D \    /
        -------o---        } feature
               E
person andref    schedule 13.02.2013
comment
Мы (почти всегда) используем топологию клиент-сервер - я не понимаю, как это помогает? По сути, это слияние трех веток: есть производственная ветка с одним набором изменений исправлений (14318): обе другие ветки хотят этого. Поэтому они объединяют его: ветвь по умолчанию делает это в 14319, а ветвь функций делает это с 14321. Но когда ветки функций и ветвей по умолчанию объединяются, вы получаете что-то вроде приведенного выше снимка экрана. - person Eamon Nerbonne; 15.02.2013
comment
Да, это хорошее предложение. Конечно, на самом деле все немного сложнее; Я интерпретировал имена веток так, чтобы они имели смысл, когда на самом деле большинство коммитов были анонимными заголовками, а позже один из них превратился в исправление. Итак, для нашей группы проблема заключалась в том, что коммиты были в местах, где их быть не должно, и наши ветки были названы сбивчиво (в ретроспективе) - но это немного выходит за рамки? Спасибо за обновление, так оно определенно намного полезнее! - person Eamon Nerbonne; 19.02.2013

Для неправильного определения базы в случае общего предка наборов слияний один слабое место известно:

может быть неправильно, если какой-либо из слияний содержит не связанные с слиянием редактировать

person Lazy Badger    schedule 14.02.2013

Я предполагаю, что предком является 14294. Поскольку оба ваших новых коммита являются слияниями, у вас теперь более одного предка, что делает выбор неоднозначным.

К сожалению, невозможно сказать mercurial, какой из потенциальных предков использовать.

person Rudi    schedule 13.02.2013
comment
Неправильно... ancestor() является самым большим общим предком двух наборов изменений согласно справке - person Lazy Badger; 13.02.2013
comment
@LazyBadger: Да, вы правы, но похоже, что их понятие «Величайший» используется исключительно в смысле DAG, а 14294 и 14318 не имеют прямого отношения. Конечно, использование 14294 по-прежнему является плохой догадкой, так как оно старше как во времени, так и намного дальше в смысле расстояния по графу, но это понятная ошибка алгоритма. - person Eamon Nerbonne; 14.02.2013
comment
@EamonNerbonne - нет. Лучшее означает последнее - person Lazy Badger; 14.02.2013
comment
@LazyBadger: это противоречит снимку экрана в вопросе - ясно, что лучший не обязательно означает последний. - person Eamon Nerbonne; 15.02.2013
comment
И что самое последнее в каком смысле? Отметка времени согласно набору изменений? Номер ревизии? - person Eamon Nerbonne; 15.02.2013