Пользователь
0,0
рейтинг
7 февраля 2013 в 21:45

Разработка → Сходство и различие между Mercurial и Git из песочницы

По роду своей деятельности я нередко становлюсь свидетелем «священных войн» между коллегами-программистами на тему, какую же систему контроля версий выбрать для того или иного проекта. Роль системы контроля версий особо остро ощущается в случаях разработки и поддержки проектов с длинной историей. Вариантов инструментов много, но я хочу сконцентрироваться на двух, на мой взгляд, наиболее перспективных: Mercurial и Git. Далее попробуем рассмотреть возможности обеих систем с позиции их внутреннего устройства.

Немного истории


Толчком к созданию обеих систем, как Mercurial, так Git, послужило одно событие 2005 года. Всё дело было в том, что в упомянутом 2005 году ядро системы Linux потеряло возможность бесплатного использования системы контроля версий BitKeeper. После пользования BitKeeper в течение трёх лет разработчики ядра привыкли к его распределённому рабочему процессу. Автоматизированная работа с патчами сильно упрощала процесс учёта и слияния изменений, а наличие истории за продолжительный период времени позволяло проводить регрессию.

Другой немаловажной частью процесса разработки ядра Linux стала иерархическая организация разработчиков. В вершине иерархии стоял Диктатор и много Лейтенантов, отвечавших за отдельные подсистемы ядра. Каждый Лейтенант принимал или отклонял отдельные изменения в пределах своей подсистемы. Линус, в свою очередь, затягивал их изменения и публиковал их в официальном хранилище ядра Linux. Любой инструмент, вышедший на замену BitKeeper, должен был реализовывать такой процесс.

Третьим критичным требованием к будущей системе была скорость работы с большим количеством изменений и файлов. Ядро Linux — это очень большой проект, принимающий тысячи отдельных изменений от тысяч различных людей.

Среди множества инструментов подходящего не нашлось. Практически одновременно Мэт Макол (Matt Mackall) и Линус Торвальдс (Linus Torvalds) выпускают свои системы контроля версий: Mercurial и Git соответственно. В основу обеих систем легли идеи появившегося двумя годами ранее проекта Monotone.

Cходство


Обе системы контроля версий имеют ряд общих черт:
  • ревизии ассоциируются с контрольными суммами;
  • история имеет вид направленного ациклического графа;
  • поддерживаются высокоуровневые функции, в т.ч. бисекция, ветвление и выборочные фиксации.

Отличия


Несмотря на общность идей и высокоуровневого функционала, реализации систем на низком уровне в значительной степени отличны.

Хранение истории

И Git, и Mercurial идентифицируют версии файлов по их контрольной сумме. Контрольные суммы отдельных файлов объединяются в манифесты. В Git манифесты называются деревьями, в которых одни деревья могут указывать на другие. Манифесты непосредственно связаны с ревизиями/фиксациями.

Mercurial для улучшения производительности пользуется специальным механизмом хранения Revlog. Каждому файлу, помещенному в хранилище, сопоставляется два других: индекс и файл с данными. Файлы с данными содержат слепки и дельта-слепки, которые создаются только когда количество отдельных изменений файла превышает некоторое пороговое значение. Индекс служит инструментом эффективного доступа к файлу с данными. Дельты, полученные в результате изменения файлов под контролем версий, добавляются только в файлы с данными. Для того, чтобы правки из разных мест файла объединить в одну ревизию, используется индекс. Ревизии отдельных файлов складываются манифесты, а из манифестов — фиксации. Этот метод зарекомендовал себя весьма эффективным в деле создания, поиска и вычисления различий в файлах. Также к достоинствам метода можно отнести компактность по отношению к месту на диске и достаточно эффективный протокол передачи изменений по сети.

В основе модели хранения Git лежат большие объектные бинарные файлы (BLOB). Каждая новая ревизия файла — это полная копия файла, чем достигается быстрое сохранение ревизий. Копии файлов сжимаются, но, всё равно, имеют место большие объёмы дублирования. Разработчики Git применили методы упаковки данных для снижения требований к объёму хранилища. По существу они создали нечто похожее на Revlog для указанного момента времени. Полученные в результате упаковки пакеты отличаются от Revlog’а, но преследуют ту же цель — сохранить данные, эффективно расходуя дисковое пространство. В виду того, что Git сохраняет слепки файлов, а не инкремент, фиксации могут легко создаваться и уничтожаться. Если при анализе требуется посмотреть разницу между двумя различными фиксациями, то в Git разность (diff) вычисляется динамически.

Ветвление

Ветвление — очень важная часть систем управления конфигураций, т.к. оно позволяет проводить параллельную разработку новой функциональности, сохраняя стабильность старой. Поддержка ветвления присутствует как в Git, так и в Mercurial. Отличия формата хранения истории нашли своё отражение и в реализации ветвления. Для Mercurial ветка — это некая отметка, которая прикрепляется к фиксации навсегда. Эта отметка глобальна и уникальна. Любой человек, затягивающий изменения из удалённого хранилища, увидит все ветки в своём хранилище и все фиксации в каждой из них. Для Mercurial ветки — это публичное место разработки вне основного ствола. Имена веток публикуются среди всех участников, поэтому в качестве имен обычно используют устойчивые во времени номера версий.

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

Практические аспекты использования


Различия в реализациях Git и Mercurial можно проиллюстрировать на примерах.

Mercurial позволяет легко фиксировать изменения, проталкивать и вытягивать их с поддержкой всей предыдущей истории. Git не заботится о поддержке всей предыдущей истории, он только фиксирует изменения и создаёт указатели на них. Для Git не имеет значения предыдущая история и на что раньше ссылались указатели, важно то, что актуально в текущий момент. Существует даже инструмент, гарантирующий сохранность локальной истории при вытягивании изменений из внешнего хранилища — fast-forward merge. Если этот механизм включен, то Git будет сообщать об изменениях, которые не могут быть улажены без продвижения по истории вперёд. Данные ошибки можно не принимать во внимание, если поступившие изменения ожидались.

При выполнении отката фиксации или затягивания со слиянием Git просто меняет указатель ветки на предыдущую фиксацию. В действительности в любой момент времени, когда требуется откатиться в некоторое предыдущее состояние, Git ищет в логе соответствующую контрольную сумму и сообщает какая фиксация ей соответствует. Как только что-то зафиксируется в Git, то всегда можно к этому состоянию вернуться. Для Mercurial существуют случаи, когда невозможно полностью вернуться в исходное состояние. Т.к. Mercurial для решения какой-либо проблемы создает фиксацию, то в некоторых случаях затруднительно переместиться назад с учётом свежего изменения.

Для решения различных проблем в Mercurial существуют расширения. Каждое расширение решает свои проблемы хорошо, если существует само по себе. Существует даже некоторые расширения, обеспечивающие сходную функциональность, но разными способами.

Для примера рассмотрим работу с отложенной историей. Допустим, нам необходимо записать изменения из рабочей копии без фиксации в хранилище. Git предлагает использовать stash. Stash — это фиксация или ветка, которые не сохраняются в обычном месте. Stash не показывается, когда выводится список веток, но всеми инструментами он трактуется как ветка. Если аналогичная функциональность требуется Mercurial, то можно использовать расширения attic или shelve. Оба этих расширения хранят «отложенную» историю в качестве файлов в хранилище, которые могут быть при необходимости зафиксированы. Каждое расширение решает проблему немного по-своему, поэтому имеет место несогласованность форматов.

Другой пример, команда git commit --amend. Если нужно изменить самую последнюю фиксацию, например, добавить что-нибудь забытое или изменить комментарий, то команда git commit --amend создаст полностью новый набор файловых объектов, деревьев и объектов фиксации. После этого обновляется указатель ветки. Если далее потребуется откатить изменения, то необходимо только вернуть указатель на предыдущую фиксацию командой git reset --hard HEAD@{1}. Чтобы повторить это в Mercurial потребуется откатить фиксацию, затем создать новую, далее импортируем содержимое последней фиксации при помощи расширения queue, дополняем её и делаем новую фиксацию.

Следует заметить, что ни одно из перечисленных выше дополнений не использует возможности формата хранения Mercurial, и таким образом они существуют исключительно как самостоятельная надстройка над ним.

Выводы


В последнем разделе этой статьи хотел бы высказать собственное мнение по выбору системы контроля версий. И Mercurial, и Git хороши в своих сегментах.

Например, для целей ведения коммерческого программного проекта мне больше импонирует Mercurial.
  • Строгая работа с историей в Mercurial гарантирует возможность учёта и поиска первоначального источника ошибки.
  • После слияния с веткой в Git мы рискуем получить гига-патч, в котором где-то будет скрываться ошибка.
  • Глобальные ветки также дают возможность контроля за работой коллег при регулярной синхронизации с центральным хранилищем.

Для хранения бинарных файлов, например, электронной библиотеки, Git подходит лучше. По сравнению с Mercurial он не ориентирован на расчет дельты файлов, что для бинарного содержимого не очень эффективно. Сами файлы меняются редко, а основные операции с ними — это перемещение и добавление. По моим собственным наблюдениям папка хранилища Git с историей моей библиотеки сопоставима по размерам с рабочей копией с окрестностью примерно 10%.

Источники знаний


  1. Основной источник
  2. Описание формата Mercurial
  3. Описание формата Git
  4. Общая справочная информация из Wikipedia

@unlocker
карма
21,0
рейтинг 0,0
Реклама помогает поддерживать и развивать наши сервисы

Подробнее
Спецпроект

Самое читаемое Разработка

Комментарии (403)

  • +2
    Так что же всё-таки лучше? :)
    • НЛО прилетело и опубликовало эту надпись здесь
      • +25
        А чего не CVS?
        • НЛО прилетело и опубликовало эту надпись здесь
          • +11
            Visual SourceSafe!
            • +5
              ftp!
              • +1
                telnet, чо уж…
                • +2
                  echo $'USER vasya\nPASS qwerty\nPASV\nSTOR...' >/dev/tcp/$host/21 тогда уже, господа извращенцы.
                • +2
                  Дискеты в шкафу
                  • +1
                    Бобины.
                    • +1
                      Зубилом по камню.
                      • +23
                        Вилами по воде
                        • +3
                          Главное — бекап не забыть сделать
                          • +1
                            На перфоленту.
                            • +12
                              Переписать код в тетрадку!
                              • +2
                                С воды, по которой писано вилами, я правильно понял?

                                Ребята, you made my day!
                              • 0
                                Главное потом скомпилировать и запустить из тетрадки.
          • 0
            Ага. Как раз занимался переносом истории из StarTeam 6.0 в git. Удовольствие то ещё :)
            • 0
              Да весь ST — одно сплошное «удовольствие».
          • +1
            Кто-то его ещё использует? Разработка через страдание.
        • +1
          accurev наше всё Ж)
      • +1
        Если бинарные файлы хранить, то про SVN согласен, а если текстовые, то нет. Для текстовых все же Hg, Git лучше )
        • 0
          А зачем бинарные в СВН хранить?
          • +1
            К примеру MP3, они редко меняются и не компилируются. При таких ситуациях можно поступить двумя способами:
            1) Положить файл на какую-либо шару, а в каком-либо сборочном скрипте указать где его брать
            2) Положить непосредственно в CVS

            Второй способ лучше:
            1) Знаете какой из «умных людей» удалил столь нужный файл!
            2) Нет такой ситуации, когда Вы не знаете при решении какой задачи потребовался этот файл?
            3) Админам, как правило проще бэкапить

            Банально: about.png это текстовой файл? ;)
            • –1
              Нет, вы не поняли. Зачем в Svn, а не в Git?
              • +4
                А вы работали с большими репозиториями git? :-) Гит не тянет больших репозиториев, зачастую просто падает или дико тормозит. Большие — это в несколько гигов на самом деле.
                А кроме того, никто не умеет нормально мержить бинарники, да и возможность вытащить часть репозитория очень полезна бывает.
                Так что код — в git (или hg), а данные -в svn!
                • +3
                  Про бинарники — у гита есть annex, у hg — largefiles. Отлично работают оба, правда надо запомнить пару допкоманд
                  • 0
                    Ну есть ещё и git media, я и сам нечто подобное реализововывал. Но это уже примочки, со всеми их минусами. Да и вытянуть быстро кусок репозитория из git-a проблематично.
                    Так что не убедили :-)
                • +1
                  Вот кому надо статьи про Git и Mercurial писать )
                  • +3
                    Вы мне льстите, и я ничего не знаю про mercurial.
                    Вообще у меня была идея написать «феерическое расставление точек на git» по поводу практики работы с ним в продакшене софтверных компаний, но не хватает знаний.
              • 0
                Потому-что GIT будет локально хранить весь репозиторий, что увеличивает необходимое пространство минимум вдвое.
        • 0
          Да ладна! Бинарники в SVN? Почитайте, SVN не следит за целостностью данных. Вы можете положить туда бинарник, а через год вытащить его оттуда битым. У меня на практике бились картинки и шрифты. Так что бинарные файлы так же лучше хранить в Git или Hg.
          • +1
            Пруф?
            Конечно есть там чексуммы.
            • –2
              Не пользуюсь SVN уже года три-четыре. Чексуммы есть, однако он их не проверяет, когда выгружает файлы. О том что файл битый узнаешь позже. Да и стоит ли сравнивать надежность хранения данных у централизованной и децентрализованной системы?
              • +2
                Пруф что не проверяет?

                Битый файл мог быть у вас потому что вы его туда отправили битым (битая память?). В противном случае можно было с нескольких попыток получить целый файл.

                А поповоду надёжности — попробуйте забэкапить git репозиторий в файлы, инкрементальным бэкапом, все бранчи.

                (в файлы — это в смысле — при условии что целевой бэкап будет где-нибудь на S3 храниться, и прав на удаление/изменение файлов не будет, только на добавление — ведь именно так нужно настраивать права чтобы какой-нибудь злоумышленник не стёр и бэкап при компрометации машины)
                • 0
                  Пруф что не проверяет?

                  Ну да, проект был задеплоен год назад с битыми файлами. Если бы это был единичный случай, то ладно. С гитом за 4 года таких проблем не было.

                  Любой клон гита — это уже бекап. Для того, чтобы забекапить на том же S3 достаточно синхронизировать все ветки. И если история не будет переписываться, то файлы будут только добавляться.
                  • 0
                    Ну это не показатель что файлы были битые, может баг в svn в вашей ОС/версии, может проблема с железом.
                    Любой клон гита — да тоже бэкап.

                    А вот бэкап копированием папки git — после git gc всё будет перезаписываться. К тому же чтобы он был в 100% случаев консистентным тоже нужно постараться вроде как.

                    Сделать такой бэкап с помощью git bundle — это нужно постараться. И писать это не на bash. И желательно с unit тестами. При этом метки бранчей-тэгов не будут «инкрементальными» (впрочем они не много места занимают)
                    • +1
                      Гит крякает, если файл поврежден. У него механизм хранения данных такой. Он файлы внутри папки .git называет согласно их контрольной суммы.

                      Бренчи и теги практически ничего не весят, это метаданные. А инкрементальными бекап можно получить если, например, пушить на север бекапа по крону (или наоборот пулить с сервера бекапа). Причем без параметра --force он ничего не перезапишет. И еще советую почитать про параметр --mirror.

                      git bundle удобен для разового переноса. В принципе это создание данных для push перед отправкой на сервер.
                      • +3
                        Бекап на самом деле запросто реализуется — открываете архивируемый репозиторий наружу и делаете на другом конце git clone --mirror --bare — и потом только фетчите ветки.
                        • +1
                          В принципе я это и пытался объяснить :)
                          • 0
                            Пытались то пытались, но это было всё совершенно не по теме что я поднял, а другие способы бэкапа.
                        • 0
                          В условиях было — бэкап в файлы. На другом конце пассивная информация, в ней нельзя запустить гит.
                          • 0
                            Если есть способ примонтировать с помощью fuse, то как раз по теме. Выполняйте пуш.
                          • 0
                            Не совсем понял, видимо, что вы хотите бэкапить? Репозиторий с версиями? Тогда используйте описанный способ. Как вы хотите сохранять версионность, не запуская систему контроля версий-загадка для меня.
                            Если же вы хотите бекапить просто набор файлов некоторого снапшота: git archive --help
                            • 0
                              Point был в том что в SVN — svndump может делать инкрементальные бэкапы, который можно восстановть в полноценный репозиторий, причём место назначение бэкапов может быть что угодно — лента, флэшка, Amazon Glacier, медленный FTP, удалённый сервер (доступный по протоколам передачи файлов) без права стирания/перезаписи файлов.

                              Git bundle же может делать аналогичное только если 1 бранч. (если много бранчей то это очень сложно).

                              p.s.
                              про другие способы бэкапов git'а я знаю, спасибо.
                              • 0
                                Git bundle же может делать аналогичное только если 1 бранч. (если много бранчей то это очень сложно).

                                Поищите в справке параметр --all и сложность отпадет.

                                Другие способы бекапа — pull/push в удаленный bare репозиторий. Если на удаленном сервере не стоит git, то папку с репозиториями можно монтировать в файловую систему с помощью fuse и запускать нужную операцию гита на локальном сервере.
                              • 0
                                Для примера, у меня есть реп, которые я таскаю на galaxy s3. Ничего сверхважного, скрипты, но храню я их там в гите. Хоть на андроид и есть клиенты и серверы гита, но я их не использую. Данные вынимаю и сохраняю с помощью стационарного гит клиента.
                    • 0
                      И, кстати, если при работе крона будет ошибка (не может выполнить push/pull), это будет означать, что коммиты переписывались. И либо это ошибка фс, либо кто-то намеренно их переписал. В любом случае факт модификации будет отловлен.
                • 0
                  Про проверку целостности — где то читал, где уже не помню. Про битые файлы — реальный факт, проблема была с очень большим репозиторием (4 гигобайта). И в сети тоже это обсуждалось. Быстрый поиск в гугле результатов не дал.
        • +5
          Для бинарных файлов у HG есть специальное расширение largefiles.
          Оно встроено начиная с версии 2.0.

          • 0
            Спасибо, не знал! ;) А еще можете посоветовать нормальный не монстроподобный issue-трекер из тех что пробовали(если пробовали) и который понравился?
            • 0
              А issue-трекер у bitbucket пробовали?) Он даже слишком простой.
              • 0
                Извините что не уточнил нюанс. Мне нужно на локальной папки, т.к. проект веду без использования внешнего интернет-сервиса. Обхожусь только локальной папкой ".hg" расположенной в TrueCrypt контейнере :) Устал использовать TaskCoach. Пока у меня все выглядит так: после удаления\дабавления\изменения задач я делаю hg ci -m «added new task». Это как-то уже напрягает (
                • 0
                  Если под винду, посмотрите ToDoList.
                  • 0
                    Чем от будет отличаться от упомянутого мною TaskCoach? Ответ: Ничем!
                    • 0
                      Ну я же не знаю, что именно вас утомило в использовании TaskCoach. Вы бы описали, чем вас TaskCoach не устраивает и какие у вас требования к issue-трекеру вообще.
                      • 0
                        Ок. Опишу один use-case по добавлению задачи, как это сейчас выглядит у меня:
                        1) Открыть в TaskCoach docs\projects.tsk
                        2) Добавить задачу
                        3) Cохранить
                        4) В виду того что файл docs\projects.tsk изменился выполняем команду в консоли: hg ci -m «added new task»

                        Если закрываем задачу, тоже самое. Если изменяем приоритеты — тоже самое.

                        Я бы хотел что-нибудь похожее на такой use-case:
                        1) hg task-add «Зарефактори ClassName.super_method()»
                        2) hg ci -m «added new task»

                        еще лучше чтобы п.1 и п.2 в одном.

                        Если надо посмотреть что есть:
                        hg task-list
                        выводится список имеющихся не закрытых задач

                        Если надо закрыть задачу, то:
                        hg task-close номер_задачи

                        Это пример того что я хочу.
                        • +2
                          Может это подойдет.
                          • 0
                            Посмотрю. Спасибо!
                • 0
                  BugsEverywhere попробуйте. Интересная штука.
            • 0
              redmine
    • 0
      Лично я в свое время выбрал для себя Git, так как он более распространен. Хотя на всякий пожарный и Mercurial освоил.
      • НЛО прилетело и опубликовало эту надпись здесь
        • 0
          Я тоже начал со Ртути, т.к. ГуглоКод, а потом перешёл на Гит, т.к. ГитХаб
          • +2
            А я на гитхаб коммичу через hg.
  • +1
    Ничего не лучше, кому что нравится то и используют.
    Не хватало ещё и холивара по поводу Git VS Mercurial :D
  • 0
    Интересно, возможно ли в Mercurial переключать ветки в рамках одной рабочей копии репозитория?
    Для проектов на C++, где время сборки может быть большим это иногда важно.
    • 0
      Если я вас правильно понял, то можно просто создать новую директорию и в ней симлинк на ваш .git
      Ну а дальше git checkout ваш_бранч, или использовать тот же самый бранч, это уже как нравится
      • 0
        С git как раз пониматно. Сделал git checkout, пофиксил/смёрджил/запушил, сделал назад checkout. Интересно, можно ли так в mercurial, или там обязательно клонировать в отдельный каталог.
        • +1
          С hg все аналогично. Сделал hg up branch1, пофиксил/померджил, сделал hg up branch2.
      • 0
        Зачем такие сложности? Достаточно сделать клон из уже имеющейся папке. В файловых системах, где поддерживаются жесткие ссылки (ntfs, ext) — будут задействованы именно они, при дублировании папки .git. По окончанию работы — удалить клон.
        • 0
          Если мне нужно исправить пару файлов в большом проекте (и ветки близки, как в случае hotfix и new feature development), то клон в новое место приведёт к тому, что бинарники «протухнут», и придётся делать полную пересборку. Переключение в одной копии позволит сделать быструю инкрементальную досборку.
        • 0
          Можно сделать и клон, но на сколько я понял как раз не хотелось делать клон. Возможно я что то не так понял.
          Тем не менее, при работе склоном нужно будет делать push в оригинал, и потом с оригинала на сервер, конечно мы так же можем поправить и конфиг, но тогда надо будет кидать комиты через сервер, что нам точно не нужно.

          С симлинком, можно работать даже с одной версией и отправлять на сервер из любой папки. И Stage файлы будут видны в обоих, так же как и комиты, без лишних pull/push, но с checkout и ресет…

          Тут уж очень сильно зависит от того что нужно делать. А там хоть клон, хоть симлинк, да хоть полная копия .git
    • –2
      Можно
      • 0
        Ну напишите человеку как? Возможно это пригодится, так же кому то еще.
    • +3
      hg update {revision} (он же hg up, hg checkout, hg co); где {revision} может быть в том числе и веткой.
    • 0
      А можете немного поподробнее объяснить, что вы имели в виду?
      • +1
        Думаю мне уже ответили. Имелось ввиду возможность параллельной работы над разными ветками в одной рабочей копии. Если две ветки не сильно разошлись, то переключение из одной в другую изменит только малое количество файлов (важно чтобы timestamps при этом не менялись), и инкрементальная сборка проекта останется быстрой.Похоже это можно сделать и в git, и в mercurial.
    • 0
      переключиться на другую
      > hg up <branch-name>

      посмотреть бранчи:
      > hg branches

      дать имя бранчу:
      > hg branch <new-branch-name>

      закрыть бранч:
      > hg ci --close-branch -m «branch is close»

      мержим текущий бранч с другим:
      > hg merge <branch-name>
      не забудем тут же закомитить мерж:
      > hg ci -m «branches merge»

      тута:
      -m «это указание сообщения коммита»
  • –10
    Зато git написал лично Линус Торвальдс!
  • –17
    Не понимаю чем может не устраивать git. Единственное объяснение выбора в пользу другой CVS я вижу только в незнании git
    • –1
      А как в нем изменить сообщение (например, исправить очепятку в тексте) у древнего коммита, который был давным давно запушен? ;)
      • +2
        Это киллер-фича mercurial?
        • +5
          Это киллер-фича Subversion.
      • +4
        rebase.
        • +1
          rebase — не катит, так как все комиты буду заново пересозданы.

          В случае же, если проект на столько критичен, что нужно волноваться об одной опечатке в описании, возможно есть смысл иметь модерацию комитов перед мержем в основную ветку. Это так же позволить повысить качество кода, и иметь комиты только по делу.
          • 0
            rebase — не катит, так как все комиты буду заново пересозданы.
            Ну иначе-то никак. А юзеру нужно.
            • +2
              То есть вы готовы запороть всю историю и иерархию комитов, ради одной опечатки?
              • +5
                Я — нет. А сферическому юзеру в вакууме может быть очень нужно
                • +4
                  Зачет. Однако здешние обитованцы не заценили юмора…
              • +3
                Описание изменения и его родители используются для вычисления хэша что в git, что в mercurial. Соответственно изменить сообщение, не «запоров» историю (точнее, не пересчитав хэши всех потомков) невозможно.
                • +1
                  О том и речь. Здесь только премодерация комитов может помочь.
              • +1
                vovkab, а что, rebase действительно запорет всю историю и патриархию? Свят-свят.
        • 0
          > rebase — не катит, так как все комиты буду заново пересозданы.

          Предположим что это не критично, как это сделать? Просто когда я искал способ это сделать, то единственным рабочим решением оказалось использовать git filter-branch, в котором проверять хеш коммита и заменять текст. Буду рад увидеть лучшее решение :)
          • +1
            Если это локальная ветка и данные еще не в паблике, то конечно же через rebase.
            Вот тут подробнее: git-scm.com/book/ch6-4.html
      • +3
        Создать ещё один коммит, это ж система контроля версий ёбанаврот!
    • +24
      Зато объяснений в пользу выбора Git целых два:
      1. Мода/популярность
      2. незнание других DVCS
      • –25
        А в пользу Mercurial только один (и кстати вы не первый кто в этом признается): «Не осилил Git»
        • +13
          Ну действительно, разве могут быть у нормального человека рациональные аргументы против Git.
        • +31
          Нет. У git нет API, позволяющего нормальную интеграцию с чем‐либо (делать каждый раз fork-exec и читать выхлоп из pipe — это очень медленно, как в смысле скорости разработки так и скорости исполнения. Даже несмотря на то, что интеграция пишется на языке, который успешно прячет fork-exec).

          У git нет огромного количества хуков (например, preoutgoing, все pre-{command}, …).

          У git нелогичное распределение функциональность по командам: checkout создаёт ветки или обновляет дерево, push отправляет изменения или удаляет их на том конце, diff может показывать изменения между ревизиями, а может — status, причём сам status этого не умеет…

          У git иногда плохая обработка аргументов командной строки (pull принимает сначала аргументы для merge, затем для fetch).

          У git плохая документация — она настолько подробна, что отыскать нужное зачастую не представляется возможным. Вместе с неочевидным распределением функциональности по командам это создаёт проблемы.

          Аналог revsets у git обладает куда как меньшими возможностями.

          Многие команды git, показывающие список ревизий, не имеют возможности настройки формата вывода.

          У часто используемых команд вроде push/pull есть ненужные обязательные аргументы: «git push origin :branch».

          У git нет аналога «hg incoming».

          У git нет удобного аналога «hg grep».

          Большую часть претензий можно игнорировать или терпеть. Но не первые две.
          • +1
            У git нет API, позволяющего нормальную интеграцию с чем‐либо
            строго говоря, есть — libgit2 называется. Но разрабатывается оно независимо от апстрима.
            • +3
              Ещё и dulwich. Я знаю и использую libgit2. Но стабильного релиза ещё нет (правда, обещали, что следующий релиз — 1.* и со стабильным API, но сроки неизвестны), а binding’и к python (pygit2) не обладают всеми возможностями даже libgit2, сама libgit2 не обладает всеми возможностями git.

              Кроме того, это независимый проект. Если человек использует git, то консольный клиент у него окажется почти наверняка, а вот libgit2 — нет. А вот с mercurial и bazaar не так — если он есть, то почти наверняка установлен «нормально», т.е. доступен для импорта в python. К subversion тоже зачастую прилагается C‐шная библиотека (официальная!). К git не прилагается ничего.
            • 0
              А еще есть JGit (дада, на Java).
          • 0
            У часто используемых команд вроде push/pull есть ненужные обязательные аргументы: «git push origin :branch»

            SYNOPSIS git push [--all | --mirror | --tags] [-n | --dry-run] [--receive-pack=<git-receive-pack>] [--repo=<repository>] [-f | --force] [--prune] [-v | --verbose] [-u | --set-upstream] [<repository> [<refspec>...]]

            У меня работает именно так, как в описании, то есть ни repository, ни refspec не являются обязательными, у них есть значения по умолчанию.
            Но лично я их чаще всего в явном виде прописываю, чтобы самому себе точно показать что и куда я push'у, например.
            • +1
              %  git add
              Nothing specified, nothing added.
              Maybe you wanted to say 'git add .'?
              .
              • 0
                Ага, я тоже после ртути поначалу плевался. А еще staging считал жутко неудобной никому не нужной хренью. :)
                Но потом заметил, что перестал случайно добавлять всякую ерунду в коммиты, и плеваться закончил.
                • 0
                  перестал случайно добавлять всякую ерунду в коммиты
                  post hoc ergo propter hoc, что ли?
                  • +1
                    Для этого надо что-то доказывать, а я просто рассказываю свой опыт и мнение.
                    • +2
                      Ну тогда и я расскажу. Лично мне staging area помогает раз, редко два раза в месяц. Остальное время путается под ногами. А ерунда не коммитится и так.
                • +1
                  Неудобно и ненужно. У меня просто vim открывает diff при фиксации изменений в соседнем окне и я делаю review. Никакая staging area никак не повлияет на возможность добавить скопом все изменения без review и тестирования, она только раздражает необходимостью писать на одну команду больше.
                  • 0
                    я может что-то не понимаю, но почему не использовать git commit -a
                    • +3
                      «git commit -a» не делает addremove. Но это не важно. «Неудобно» относится к тому, что возможность наличия чего‐то в staging area необходимо учитывать. Например, при добавлении нового файла в репозиторий с помощью «git add» «git diff» не покажет никаких изменений. Причина мне понятна, но необходимость помнить о ней неудобна.
                      • 0
                        А. я вас пониял. Я просто привык, возможно, это действительно неудобно.
                • +1
                  Концепции staging в ядре меркуриал нет, но из коробки есть расширение mq, которое даёт вам staging и даже более крутой (многослойный)!
                  pqr7.wordpress.com/2011/01/07/a-git-users-guide-to-mercurial-queues/
                  • 0
                    В 2.1 появились фазы. В 2.5 появилась эволюционирующая история.
            • 0
              А теперь удалите ветку, не указав, откуда вы её хотите удалить. Я не про возможность не указать оба или последний из этих аргументов. Я про невозможность не указать только первый, указав второй.
          • 0
            А вот интересно, у hg есть API?
            Или имеется в виду python-hglib, который запускает в фоне процесс hg и парсит его текстовый вывод?
              • +1
                Ну так про что и речь.
                Просто интересно, почему cli для hg — это хорошо, а вот для git (для которого помимо прочего есть и libgit2, и jgit) — это уже плохо?
                • +2
                  Для обоих CLI-only плохо. Другой вопрос, что апстрим Mercurial запилил хотя бы command server, показав тем самым, что они хотя бы подозревают, что Mercurial может использоваться в качестве бэкенда. В отличие от апстрима Git, которые не доводит libgit до юзабельного снаружи состояния принципиально.
                  • 0
                    А чем же libgit2 (и куча готовых биндингов к нему) плох?
                    • +1
                      А ничем не плох. Таким должен был быть libgit, но вряд ли уже когда-нибудь будет.
            • +2
              API официально нет, но на самом деле оно есть. На нём пишутся расширения, и оно на самом деле достаточно стабильно, чтобы его использовать. Просто не забывайте следить за изменениями и прогонять тесты после релиза.

              А cli для hg — точно так же плохо, как для git. Те, кому надо написать интеграцию с mercurial просто забивают на совет его не использовать.
              • 0
                Правда, я начал писать эту интеграцию когда command server ещё не было. Если бы он уже был, решение было бы, возможно, иным.
              • 0
                API расширений — это одно, API для внешнего использования (из IDE например) — это другое.
                • +1
                  Первое прекрасно служит в качестве второго. Замечу, что нужная мне часть почти не менялась с mercurial-1.3. Предположительно и с mercurial-1.2, но в Vim нет sys.stdout.closed, поэтому я всегда получаю AttributeError, когда пытаюсь использовать последний.

                  Никто не занимается сломом API «из любви к исскусству», поэтому просто не лезьте в дебри, следите за изменениями и получите нормальную поддержку всех версий, в том числе тех, когда Command Server не существовал. С бонусом в виде отсутствия затрат на IPC или даже жутких затрат на fork/exec.

                  На самом деле, расширения ломаются даже чаще — им нужны бо́льшие дебри.
          • +1
            git checkout не создаёт ветки. git checkout -b — это всего лишь shortcut на несколько команд.
            git push отправляет/обновляет только состояние веток (указатель) в remote. Удаление указателя — это тоже обновление.
            git status — (из мана) Displays paths that have differences between the index file and the current HEAD commit. Никто и не говорил, что должны показываться изменения в файлах, только изменённые файлы. И это ожидаемо: «Гит, скажи мне какие файлы поменялись»
            git diff — как и ожидается из названия показывает эту самую разницу. «Гит, покажи мне сделанные изменения»

            про push/pull и необязательные аргументы вам ответили. Git децентрализованная система, стало быть remotes у вас может быть несколько. Если вы делаете форк на гитхабе, потом локально редактируете, то наверняка захотите добавить upstream репозиторий для подтягивания изменений к себе. указывать явно репозитоий (origin) — это уже хорошая привычка.

            hg incoming — честно, не работал с mercurial, но полагаю что речь идёт про git fetch.
            Каждый будет хвалить тот инструмент, в котором он лучше разобрался. Это и закономерно, чем лучше разбираешься — тем более успешный опыт, тем круче кажется сам инструмент.

            Единственная проблема (проблема ли?) git — он не поощраяет и не прощает работу по принципу «ну я ща начну работать, мне вот срочно надо, а потом как-нибудь выучу». Разберись, а потом пользуйся и радуйся. Кстати, с линуксами то же самое.

            ПС. Фраза на проекте была: «я уже всё запушил, а потом закоммитал то, что нужно. Забирайте».
            • +2
              Никого не волнует, создаёт ли git checkout -b ветки, вызывает для этого git branch или скачивает vim (с +python), python, pygit2 и libgit2 и по этой цепочке делает своё дело. Вызовом git checkout -b создаются ветки? Да. Значит git checkout создаёт ветки.

              git status не умеет --name-status. В особенности для произвольных ревизий. Хотя, если подумать, то с разницей в информации и формате в выводе, он и не должен уметь. Просто status в git объединяет hg resolve --list и hg status. В mercurial hg status от diff --name-status ушёл недалеко и то только для текущего дерева (для двух ревизий — фактически полные аналоги).

              Обычно у меня одно место куда я делаю push. И другое одно, откуда делаю pull. git — не единственная система, имеющая remotes или аналог. Мне удобно не писать куда я хочу сделать push/pull. С mercurial я не пишу. Что‐то мне подсказывает, что, используй я bazaar, я бы тоже не писал. Почему вообще в git так радикально не любят -o/--option в нескольких ключевых местах? hg push origin --bookmark upstream сразу даёт понятие о том, что и куда вы толкаете. git push origin upstream — нет. Насколько мне известно, mercurial использует только однотипные аргументы без -o/--option: два файла тут встретиться могут, ревизия и файл — никогда.

              hg incoming ничего не загружает в репозиторий. Это не git fetch. При этом коммиты можно просмотреть полностью, вплоть до diff’ов. Конечно, в последнем случае они физически загружаются (и ещё раз при hg pull). Но в репозиторий не попадают. Если я сделаю git fetch, то мне придётся думать, как удалить ненужные изменения. А потом ещё придётся самостоятельно делать fast‐forward для нужных. Может здесь и есть команда вроде hg rollback, но я её не знаю.

              А про линуксы мне говорить не надо. Я просто ничего не уча установил себе Ubuntu. Именно по этому принципу¹. Потом почти так же² пересел на Gentoo, в процессе правда читая handbook.

              Кроме того, как я сказал, замечания не фатальные. За исключение API и hook’ов. А также справки для инопланетян и необходимости знания кишок. Подтянется libgit2, будет гораздо лучше, я и сейчас её начинаю использовать.

              Проблемы из третьего предложения (справка и кишки) меня уже слабо волнуют. Но это причина, по которой я не буду советовать git ни одному из новичков. Тем более, что git позволяет новичку отстрелить себе ногу с максимальной эффективностью: удалить всё и у себя, и на том конце. Неизменяемая история после git меня уже слегка раздражает, но 1. над этим работают и 2. это давало уверенность в том, что фатально я ничего не напорчу. (Давало: сейчас такую уверенность даёт опыт работы с обеими системами.)

              ¹ В Windows по совершенно непонятным причинам через несколько дней после установки начинал тормозить интернет. В Ubuntu он не тормозил. Вторая часть мотивации: linux — это не так как у всех, а потому круто (как несложно догадаться, решение принималось ещё в школе). Ни одного linux‐гуру вокруг не было, только такие же разговоры от других школьников, которые его где‐то видели. «Совершенно непонятные причины» также замечательно характеризуют уровень компьютерного знания.
              ² Только на этот раз было не «надо», а «интересно». И вторая часть ещё никуда не делась. Ну и проблемы от неопытности я себе тоже создал. Не такие большие, как были в Windows, и не причина перейти на что‐то радикально новое, но тоже не сахар.
            • +1
              git checkout -b — это всего лишь shortcut на несколько команд
              Это Же Совсем Другое Дело!
              git push отправляет/обновляет только состояние веток (указатель) в remote
              Ну конечно. А git send-pack, значит, юзер отдельно командует.
              указывать явно репозитоий (origin) — это уже хорошая привычка.
              Зачем указывать, если можно не указывать?
              честно, не работал с mercurial, но полагаю что речь идёт про git fetch
              Полагаете абсолютно неверно. Речь о команде, бледным подобием которой является git request-pull. Забавно, что «не читал, но осуждаю» от одептов git даже не воспринимается
              как что-то из ряда вон выходящее.
              Каждый будет хвалить тот инструмент, в котором он лучше разобрался.
              Как же быть, если я разобрался в обоих примерно одинаково (неплохо)?
              git — он не поощраяет и не прощает работу по принципу «ну я ща начну работать, мне вот срочно надо, а потом как-нибудь выучу»
              Вы уверены, что это именно вы используете git? Точно не наоборот?
      • 0
        Мода/популярность

        Между прочим при прочих равных это не такой плохой аргумент в IT
        • +8
          Не плохой. Будь у git ещё, к примеру, нормальный UI, а не просто внутренности наружу — этот аргумент можно было бы даже воспринимать всерьёз.
          • –15
            О теперь про UI, удивительно как похожи все аргументы приверженцев Hg :)
            Git не нужен UI как таковой, потому что все делается достаточно просто, быстро, удобно и безопасно из консоли.
            UI может требоваться в двух случаях merge/diff — для этого есть миллион утиит которые прекрасно подключаются к Git и Mercurial впрочем тоже.
            И чтобы посмотреть/поискать по дереву, с этим отлично справляется gitk (хотя есть еще десяток проектов разнйо степени стрёмности)
            • +6
              как похожи все аргументы приверженцев Hg
              Как будто это что-то плохое.
              все делается достаточно просто, быстро, удобно и безопасно из консоли
              Bullsh эээ… bingo!
            • +1
              С каких это пор «command-line interface» перестал быть «user interface»? Спрашивали же не «graphical user interface» (aka GUI). Хотя претензии мне здесь не совсем понятны: CLI, конечно, местами нелогичен, но не настолько, чтобы это было проблемой. Если бы была нормальная документация конечно.

              А «внутренности наружу» — скорее всего имеются ввиду огромное число команд вроде «git unpack-file», предназначенных исключительно для использования их в скриптах.
              • +8
                Имеется в виду то, что потроха Git (object, ref, blob, tree) торчат отовсюду. Даже прямо с порога:
                %  git
                usage: git [--version] [--exec-path[=<path>]] [--html-path] [--man-path] [--info-path]
                …skip…
                   push       Update remote refs along with associated objects
                …skip…
                «Это математик, Ватсон».
            • +1
              Мы на работе уже сколько лет как работаем на гите и есть два человека в команде, которые терпеть не могут вид консоли, не хотят запоминать команды и вообще.
              Удивительно, как похожи контр-аргументы гитфанов :).
              • +1
                Пользователи windows? Я бы тоже не смог терпеть вид консоли.
                • +2
                  Ага, лично я плохо понимаю, почему они не могут перейти на линупс как уже давно сделала вся остальная команда, но это их личное дело.
                  Ну и вот, собсна, проблема нормального GUI не решена. Ближе всего SmartGit, но он платный, а никто им покупать его не стремится. Бесплатных GUI, хотя бы близко приближающихся к Mac'овскому SourceTree походу в природе не существует. (Тут должна быть вставлена картинка «WHY?»)
                  • 0
                    Раз уж пошло обсуждение гитовских GUI, а вы пользуетесь линуксом, то чем вы в нём пользуетесь?
                    Под маком есть прекрасный Tower (если денег не жалко) и чуть менее прекрасный SourceTree. А вот под линуксом меня от имеющихся интерфейсов аж передёргивает.
                    • 0
                      Лично я на коммерческих проектах пользуюсь то gitg то rabbitvcs. Убоги оба, но как-то юзабельны. На бесплатных — SmartGit — он чуть лучше, но до SourceTree все равно не дотягивает. Ну и лично у меня нет проблем с консолью :).
                    • +2
                      Я, если честно, не представляю человека, который пользуется линуксом и обламывается работать с git через консоль :-)
                      • +1
                        Как бы там ни было, я тоже человек и хочу sourcetree под линукс.
                        • 0
                          Спору нет, смотреть дерево удобнее в красивом gui. Меня спасают две вещи:
                          cit config alias.tree = log --graph --pretty=format:'%C(bold yellow)%h%Creset %s %C(bold blue) %an%C(bold cyan)%d %C(bold black)-> %cr%Cgreen'
                          и отсутствие необходимость смотреть дерево. :-)
                          • 0
                            Ну так в гуях много чего приятно делать — например выбирать файлы для коммита, ревертить случайно поменянные файлы… Не поймите меня неправильно — это умеют все клиенты. Но SourceTree пользоваться удобно, а другими — нет.
                          • 0
                            Фиговатый у вас пример-то :)

                            Одна длинная строка — и все отображение развалилось…
                            • +1
                              У меня эран широкий и хук на длину сообщения. Но вообще да, надо поправить как-нибудь.
                              • 0
                                А еще видите там вон такую горизонтальную псевдографическую полоску? Она вообще к чему? Это и без разрыва-то небось неочевидно… Ну и главное — такую сложную алхимию я бы не написал — а в гуях это сделано за меня…
                              • 0
                                А еще вот вообще трэш и угар:
                                • 0
                                  Да, похоже вам мой конфиг не подойдет :)
                                  Но мне как-то хватало, уж не знаю почему. Возможно из-за того, что у меня нет таких ветвлений. Или я не говорю --all. :-)
                                  • 0
                                    Да тут на самом деле интересная штука — один из коллег любит делать пространные комментарии к коммитам, за что его уж совсем никак винить нельзя, кроме того так получалось, что на последнем рассмотренном куске не было еще фичебранчей — он тупо раз за разом коммитил все в одну ветку. Причем коммитил он чаще других — у него были десятки относительно небольших задач. Вот и получается — одна ветка только изкоммитов, все остальные — просто прямые (их не так уж много — мастер плюс еще какие-то побочные).
                                    Но вот оказывается, что нельзя достаточно полно посмотреть на обычном экране дерево в хоть сколько-то сравнимой с гуи форме.
                                    Вот как оно выглядит в gitg:

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

                                    насчет all — тупо скопировал команду из вашего альяса.
                                    • 0
                                      Я имел в виду, что либо у вас много длинных параллельных веток в локальном репозитории, либо вы добавили git tree --all. С ветками прояснилось, так что извините.

                                      Я не спорю, что красивый gui полезен для просмотра и повседневной работы разработчика/менеджера, но для меня он не очень важен, а вот многие вещи, которые есть в командной строке (filter-branch например) я использую относительно часто. Так что так выходит, что мне GUI не нужен.
                                      • 0
                                        Но вот первый скрин уже был при фичебранчах — но все равно разработчиков несколько и у каждого свой фичебранч.
                                        • 0
                                          запустите gitg --all (если он такой же, как gitk), может ветки спрятались
                                    • +1
                                      один из коллег любит делать пространные комментарии к коммитам, за что его уж совсем никак винить нельзя
                                      Посоветуйте своему коллеге в первой строке комментария писать очень коротко о чём этот коммит вообще, а пространный комментарий начинать со второй строки.
                                      • 0
                                        Ну не всех просто взять и переучить, к сожалению.
                                      • 0
                                        Принято с третьей. А вторая строка тогда должна быть пустой.

                                        Ну и вполне можно не вылезать за 120 символов на строку, например. Хотя для первой строки принято не более 49 символов писать.
                        • 0
                          Напишите в atlassian. :-)
                      • 0
                        Ну, вот я такой, например. Собственно, под линуксом я и пользуюсь консолью (и немного gitg), но после работы с хорошим GUI обратно в консоль не хочется. Возможно, вы просто не пробовали.
            • +4
              Именно консольный UI у git ужасен.
            • +7
              Git не нужен UI как таковой, потому что все делается достаточно просто, быстро, удобно и безопасно из консоли.


              Являсь сторонником git и достаточно ярым почитателем консоли (мержу, например, исключительно с использованием vim), отмечу, что следующие вещи делать без GUI жутко неудобно:
              1. Рассматривать дерево истории
              2. Брать в commit лишь часть локальных изменений файла
              3. Просматривать аннотацию (кто, какие изменения и в каких версиях внес)
              4. Смотреть дифф при большом количестве изменений или когда необходимо знать контекст изменения в широком смысле (то бишь полазить по файлу, чтобы понять, а что тут что)
              • 0
                > мержу, например, исключительно с использованием vim

                капелька оффтопа: а вы можете на толковые гайды для совсем ничего не знающих о виме ссылки дать? Гуглом пользоваться умею, но хочется именно правильный материал — сам, ввиду отсутствия знаний, оценить адекватность не смогу.
                • +4
                  С самим vim идет vimtutor, для начала — прекрасная вещь.
                  Это по сути запущенный vim с текстовым файлом (правда, на английском, надеюсь, что не проблема), в котором тебе рассказывают, что к чему, и ставят задания, которые в нем же и выполняешь.
                  Базовые навыки осваиваются на ура.

                  Еще есть вот это: www.google.ru/search?q=vim+graphical+cheat+sheet&hl=ru&newwindow=1&client=safari&tbo=u&rls=en&tbm=isch&source=univ&sa=X&ei=69kUUY-kL-Gq4ASd3YCIAw&ved=0CDwQsAQ&biw=1279&bih=904

                  А потом уже хелп самого vim для более тонкой настройки.
                  Прошу учитывать, что я не гуру vim, я не пишу для него плагины, например, и не делаю из него ide, как некоторые.
                  Для меня это просто достаточно удобный текстовый редактор — не более.
                  Хотя код под линуксом я пишу исключительно в нем.
              • 0
                Попробуйте плагин для вим — github.com/tpope/vim-fugitive
                Он как раз решает все проблемы перечисленные вами :)
                • 0
                  Спасибо! Посмотрел видео о нем (не все, обрывками) — работа с аннотацией очень понравилась.
                  Попробую при случае.
                • 0
                  А как он решает задачу «Брать в commit лишь часть локальных изменений файла»? Насколько я знаю, AuRecord всё ещё не имеет аналогов. Fugitive, правда, позволяет писать в staging area, но я слабо представляю, насколько это удобно использовать для данной задачи.
                  • 0
                    Очень удобно — тоже через diffsplit справа открывается рабочая копия, слева оригинал.
                    Переносите изменения налево, сохраняете и получаете это в staging.
                    • 0
                      А можно конкретные команды? Пока это выглядит как AuRecord, но без окна с состоянием внизу. Окно же нужно:
                      1. Показывает состояние рабочей копии и какие файлы будут включены в изменение (первая колонка: не включён/включён частично/включён полностью/не включён, но редактировался для частичного включения)
                      2. Позволяет выбрать файлы для полного включения (в т.ч. неизвестные и удалённые, они будут добавлены или забыты). Причём выбрать скопом
                      3. Позволяет отменить изменения, предназначенные для частичного внесения или переоткрыть их заново
                      4. Хранит всю историю включений/изменений текущей сессии. То есть, делая undo/redo в окне состояния вы можете отменить или восстановить сделанные частичные изменения (правда гранулярность пока ниже: сохраняется только последнее состояние перед следующим изменением, произведённым в окне состояния; история правок внутри файла не сохраняется).

                      Можно узнать, как со всем этим справиться в fugitive?
                      • 0
                        Окно с состоянием тоже есть, но для того чтобы не отвечать на все вопросы по отдельности советую таки сходить по ссылке и посмотреть скринкасты. В них показан весь основной функционал
                        • 0
                          Видео традиционно не работает (зато работает звук, что странно). Английскую речь без субтитров, как всегда, сложнее понять. Скачанный OGV в mplayer не работает также (QT работает). Ненавижу скринкасты, хотя этот неплох, если вы смогли его запустить.

                          Хотя кое‐что прояснилось: 1, 2, 3 есть (хотя и с замечаниями). 4 нету. Похоже, если есть staging area, то fugitive удобнее (4 не особо нужно) в этом отношении.
                      • 0
                        Если соблазнились, то сразу предупреждаю: дополнение предназначено в первую очередь для работы с mercurial. Всё остальное протестировано хуже. Кроме того, одним из основных предназначений дополнения является унификация работы в различных системах контроля версий. Т.е. в aurum вы работаете так, как будто staging area не существует, а все состояния файлов приводятся к 8 состояниям, используемым mercurial.
                        • 0
                          Кроме того, одним из основных предназначений дополнения является унификация работы в различных системах контроля версий.

                          Вот здесь думаю вы не правы:
                          у каждой системы контроля версий свои особенности и свой «дзен». Пытаясь унифицировать их все к одному интерфейсу вы тем самым ограничиваете их функционал, кроме того в отдельных случаях это может быть не возможно, либо ввести пользователя в заблуждение
                          (к примеру команда pull в Git и Hg делает разные вещи).
                          Поэтому я считаю что стоит придерживаться юникс подхода к таким плагинам — Write programs that do one thing and do it well.
                          Я лучше поставлю 3 отдельных плагина для разных систем контроля версий для того чтобы максимально использовать возможности каждой.
                          • 0
                            (к примеру команда pull в Git и Hg делает разные вещи).
                            Ага. Поэтому AuPull делает «hg pull --update», «svn update», «bzr pull» и до сих пор проваливается на некоторых реальных репозиториях git, так как я не знаю, как это правильно починить — ещё один пункт, из‐за которого я не люблю git.

                            Впрочем, pull/push (в основном только pull) — это единственные команды, которые доставляют мне проблемы при таком подходе, и то проблемы только с git — здесь он слишком не похож на остальных. log, commit, status, record, diff, annotate, hyperlink (:Gbrowse!), junk (remove/forget), track (add), name (tag/bookmark/branch), update, vimdiff, file (cat-file) проблем не доставляют абсолютно, а разница между VCS обычно не слишком значительна. Ещё есть grep, который имеет разное значение у mercurial и у всех остальных, но он не доставляет проблем, а только делает :AuGrep несколько несогласованной.
                  • 0
                    В mercurial есть crecord для таких финтов. Только вроде бы он отдельно идёт, не в поставке.
                    • 0
                      Последний (и единственный) раз, когда я его смотрел, у него были проблемы с русским языком в файлах. Русский у меня сейчас только на моих старых проектах, но и на новых часто встречаются юникодные символы (в основном апострофы, кавычки (а не ASCII‐убожество), маркеры для складок (использую «▶,▲» вместо «{{{,}}}»)). И ещё мне чего‐то не понравилось в интерфейсе (не помню, что именно). Напомните, в Crecord можно работать с изменениями в произвольном порядке?
                      • 0
                        Да, с юникодом проблемы были, а может и есть — я уже с год не обновлялся. А что значит в произвольном порядке? Что попросите, то и коммитнет. Порядка там вообще нет :)
                        • 0
                          Я имею ввиду, можно ли сначала посмотреть (и отметить) изменения в одном файле из конца списка, потом в другом из начала, потом отметить полностью какие‐то файлы в середине, затем вернуться к первому, и, возможно, переотметить.
                          • 0
                            Эмм. Такое ощущение, что вы его не видели вовсе. Конечно же можно, я же говорю, что выберете, то и коммитнется.
                            • 0
                              Это было очень давно, а я не помню, в чём были проблемы (старое ощущение — «ужас, ужас, ужас» и всё). Сейчас опять запустил, вижу проблему с границами выделений (на русском тексте) и замечательный текст «изменено поло�~A: 5, �~A�~B�~@ок: 165». Если что, это не часть изменений. Также вижу отсутствие возможности изменять текст внутри линии. Вижу замечательное поведение PageUp/PageDown (внутри длинного hunk прокручивает на одну строку). Вижу , двойное нажатие на который не ведёт к возвращению отметки к неотмеченным изменениям добавленного файла, а нажатие на единственный внутренний hunk (но не линию) убирает отметку со всех линий и самого hunk’а, но не с имени файла. При «review and edit» (единственный способ всё‐таки изменить текст внутри линии), а также при обычном commit не виден diff (мне он нужен, чтобы всё‐таки составить сообщение), и нельзя вернуться назад, если при просмотре diff’а обнаружилось что‐то не то. Подозреваю, что посмотреть diff можно, настроив mercurial засовывать его в комментарий (вроде где‐то пробегало что‐то такое, работающее для и «hg commit», и для всего остального).

                              Всё это не идёт ни в какое сравнение с AuRecord.
                              • 0
                                Но отмечать изменения в произвольно порядке таки можно. Толку — чуть, из‐за остальных проблем я никогда не поверю, что crecord не собирается мне что‐то испортить (слишком много ошибок в UI, чтобы я считал, что авторы могут написать остальные внутренности без ошибок).
              • 0
                Брать в commit лишь часть локальных изменений файла
                Посмотрите на aurum. AuRecord позволяет брать часть изменений, используя обычный vim’овский diffsplit.

                Вообще для всех остальных задач, по‐моему, достаточно нормально написанного дополнения к vim.
          • 0
            Не плохой. Будь у git ещё, к примеру, нормальный UI, а не просто внутренности наружу — этот аргумент можно было бы даже воспринимать всерьёз.

            Ммм… Отличный плагин для Идеи и ГитХаб — что ещё нужно?)
            • 0
              git gui, gitk, git blame разве не хватает?

              PS. Пардон, не туда написал…
            • 0
              CLI же. Я сам пользуюсь IDEA/RubyMine, но её на всё (по понятным причинам) не хватает. А Git GUI в них вообще лучший в мире.
              • +1
                Ну конечно. Но когда прогаешь и хочешь по ходу коммитить, то прям в Идее кнопку жмакнуть — очень удобно.
          • +1
            Из стандартных есть gitk и git gui.
            А так же есть SmartGit, и многие ide могут делать все операции прямо из себя.
          • 0
            git extensions — кроссплатформенный бесплатный UI для git. Удобный и мощный, можно никогда не пользоваться командной строкой (да простит меня Линус).
          • 0
            Если точнее — у git нет нормального UI по Windows или Linux

            Зато под OSX — вагон.

            Посмотрите на Git Tower (http://www.git-tower.com/) — он прекрасен
            Но если сложно — то есть GitBox (http://gitboxapp.com/) — он простой как почтовый клиент
            Не хочется платить? Есть бесплатный SourceTree (http://www.sourcetreeapp.com/) — который выглядит похуже, но возможностей имеет больше всех

            И это еще не считая всяких опенсорсных GitX, GitY — простенькие и со вкусом.

            Лучшее что удалось найти под Windows — Git Extensions и SmartGit — мягко говоря странны и неудобны.
            • +3
              Если точнее — у git нет нормального UI под Windows или Linux
              Я готов согласиться с тем, что в сыром виде Git for Windows несколько страшен среднему пользователю Windows.

              Однако вообще-то под Windows есть TortoiseGit.

              А это ужé совсем другое дело: настолько приятный UI для Git, что другого и не надо.
              • +1
                Угу, но не все ежедневные проблемы он может решать — stackoverflow.com/q/12528854/251311

                Может сейчас уже и возможно, полгода назад приходилось расчехлять консоль
                • +1
                  В том же git extensions есть UI для rebase / interactive rebase.
                  • 0
                    Ну в tortoisegit тоже есть, но для описанной ситуации его применить не получаатся :-) Там единственный ответ как раз и описывает в чём соль этого граничного случая
              • +1
                TortoiseSVN ужасен, а TortoiseGIT, который пытается быть его клоном, еще хуже.

                Еще раз и медленно — вы думаете что это приятный UI потому что просто не видели нормального UI для Git. Но по какой-то странной причине удобные и продуманные интерфейсы для GIT есть только для OSX

                • 0
                  Дело привычки. Лично мне пары tortoisegit + gitk хватает для 99% ежедневных задач.

                  Удобность и продуманность — субъективные метрики. Мне tortoisegit кажется достаточно удобным и достаточно продуманным, потому как он позволяет мне выполнять то, что мне нужно без каких бы то ни было затруднений :-)
                  • 0
                    Я юзал под виндами tortoisegit + gitk — и это было — ну как первые Жигули. Ну т.е. ездит, выглядит страшно, тарахтит и постоянно что-то не так — то ошибку выдаст какую-нить, то еще что-то.

                    А затем я попробовал Git Tower на маке. Ощущения — как будто сел в новенькую иномарку с автоматом и просто получаю удовольствие. Кликов — меньше, наглядности — больше, автоматизации — тоже.
                    • +1
                      Возможно, одна из причин качества утилиты — её платность $59 это совсем не шуточная цена.

                      А опенсорс это опенсорс.
                      • 0
                        Дык это, SourceTree бесплатен и тоже очень крут. И ни одна линуксовая/виндовая бесплатная утилита и рядом не валялась.
                      • 0
                        Есть чуть менее красивая, но даже более удобная — SourceTree — совершенно бесплатная. И разработчик ее — именитый Atlassian — собственно владелец BitBucket

                        Но почему-то они делают ее только для OSX
                        • –1
                          По скринам — *очень* похоже на TortoiseHG :-)
                          • 0
                            О_о
                            Шок!
                            • 0
                              Похоже, да не то. У всех виндовых утилит проблема одна — они написаны как будто для SVN, без внимания к веткам.

                              Посмотрите как ветки переключаются в Git Extensions, SmartGit
                              У TourtoiseHG — какие-то списки или меню.

                              В SourceTree/Git Tower — все ветки видны в левой панели, переключиться дело одного клика.
                              • +1
                                В тортоисхг — это выпадающий список. В сорстри — это уже развернутый список. Яйца те же
                                • +1
                                  Это неудобная мелочь, которых там миллион. Именно это я имел ввиду когда говорю что нет «нормальных UI». Все что есть — сделанные без внимания к деталям рабочего процесса. И поэтому они неудобны.
                                  Что мешает сделать аналог Git Tower под Windows я не понимаю.
                              • +1
                                Вы не мне рассказывайте, а тому, кто меня шокировал. Я и маком успел немного попользоваться и уж чем-чем, а сурстри был впечатлен.
          • 0
            В нашей компании единицы способны сделать что-либо из командной строки git, ибо хватает UI клиента. И на мой взгляд, это хорошо. Кому нужно, давно освоил командную строку. Используется в основном git extensions и интеграцией в Visual Studio. Отдельные люди, которых я не понимаю, используют TortoiseGit. Термины blob и им подобные тоже большинству не знаком.
          • –2
            Вроде нормальные UI
            — gitorious
            — gitlab
            — gitblit
            Плюс тьма приложений для веток, которые локальные.

            Или что вы имели в виду?
      • –3
        А почему бы и нет.

        Зачем мне как пользователю использовать что то, что пытается угнаться за гитом и его функциональностью?
        Гит вполне себе проверен на огромных проектах (linux, android и тд) и по нему легко можно найти ответы.
        В гите большинство фич были заложены изначально, кому как не Линусу знать что может потребоваться и как будет лучше.

        В итоге другие DVCS, выступают в роли догоняющих.
        • +9
          что то, что пытается угнаться за гитом и его функциональностью
          Да! Вот например взять commit phases или changeset obsolence. Как это «Git такого не умеет»? Git всё умеет, его же Линус написал!
          • +2
            changeset obsolence:
            This feature is experimental! Do not try it unless you are an experienced Mercurial user.

            nice

            p.s. как по мне, любая переделка истории — зло. (реверт тут не рассматриваем)
            • +5
              Так ВЕСЬ гит про переделку истории — реверты, ребэйзы, скваши…
              • +2
                ТОЛЬКО локальные изменения, пока они еще не попали на сервер.
                Все что попало в паблик, уже меняться не должно.
                • 0
                  А, понял о чем вы говорите. А черепикать мы разве можем только локальное?
                  • 0
                    cherry-pick не удаляет исходный коммит, т. е. не меняет прошлую историю.
                • 0
                  Ага. Только меняться оно может. Mercurial просто не имеет возможности указать другому концу, что надо удалить некоторое изменение. С git вам достаточно изменить всё локально, удалить на том конце изменённые ссылки и сделать push. Больше старых измений никто не увидит, а первая же сборка мусора удалит их окончательно.

                  В Mercurial уже появились все необходимые средства для изменения локальной истории. Теперь появляется возможность спрятать изменения с помощью changeset obsolescence. Но удалить их по‐прежнему нельзя.
                  • 0
                    Чтобы не пугать новичков укажу что вы чуток гипертрофируете: все же не так просто удалить публичное в гите. Если кто-то уже получил удаленные другим коммиты, то его следующий push вернет их на место.
          • +1
            Подскажите, что такого в commit phases, чего нельзя сделать в git с ветками, желательно с нормальным примером?
            • 0
              Если фазу поставить secret, то с пушем ченджсет не уйдёт

              ps: лично мне ни разу такого не нужно было и я не совсем уверен, что это именно «киллерфича», просто это единственное, что придумывается
              • 0
                Если я правильно понял, то это тоже самое что выбрать через cherrypick и запушить только нужные комиты? Оставив при это все остальное в локальной ветке, и merge/rebase/cherrypick это все так же когда потребуется?
                • +2
                  Самое главное, что в случае с phase secret исключается человеческий фактор в этом непростом процессе. Т.е. это скорее решение не технической проблемы, а людской
                  • +1
                    Пока не совсем вижу как облегчается.

                    Вот например мне надо залить пару комитов из какой то ветки:
                    git checkout master
                    git cherrypick commit1
                    git cherrypick commit2
                    git push

                    Вроде тоже не сильно сложно, или я что то упускаю в commit phases
                    • +2
                      Облегчается в том, что вы всю вашу магию можете забыть выполнить и по случайному `git push` уедет ченджсет, который не должен был ещё уезжать.

                      Т.е. я не говорю, что сделать в гите это будет сложно, я говорю, что оно защитит вас от ненарочного пуша.
                      • +1
                        Почему он должен уйти куда, если вы все готовите в локальной ветке и мержете в ту которую нужно будет пушить?

                        Уйдет только то что вы сами лично добавили, только подготовленные комиты.
                        • 0
                          Потому что даже у локальной ветки может быть апстрим из origin. И в неё все ченджсеты отправляются при пуше
                          • +1
                            Как у локальной ветки которая создавалась локально специально для данной фичи может быть какой то апстрим? Давайте не путать, если у ветки прописан remote, то она уже никакая не локальная.
                            • +1
                              Я термин «локальная» ветка определяю как ветка, которая показывается в `git branch`, вне зависимости от того, есть у неё апстрим, или нет.

                              Фичабранч легко может жить в удалённом репозитории и быть апстримом для локальной ветки.

                              Для случаев, когда вы из локальной ветки не хотите что-то случайно запушить — есть phase secret.
                              • +1
                                Да с терминологией тяжковато тут.

                                Я понимаю как то так:
                                локальная — это ветка без апстрима, этой ветки больше нет ни у кого кроме вас
                                удаленная — это либо tracking branch либо remote, не важно, важно что все что вы пушите уходит на сервер.

                                В таком виде проще общаться, если вы знаете более удобные названия, я буду не против выслушать.

                                Так вот, для каждой фичи всегда создается отдельная локальная ветка, в которой вы работаете и подготавливаете комит, затем мержите уже в ветку из которой будет происходить пуш. Таким образом, что либо не так запушить становится ну очень проблематично.
                                • 0
                                  > для каждой фичи всегда создается отдельная локальная ветка

                                  Зачем? В чём смысл держать 2 фичабренча (общий и локальный)?
                                  • +1
                                    Если вы работает один над фичей, то публиковать ветку смысла нет, хватит одной локальной, которую в конце сольете с основной.

                                    А если вы работаете не один, то тут уже все тоже самое что с любой другой веткой. Нужна временная ветка для работы. Хотя бы для того что бы держать историю «чистой».

                                    Принцип один и тот же для всех удаленных веток, так что тут ничего нового.
                                    • 0
                                      Занятно :-) Логика в ваших словах есть, но на практике я просто ребейзю свои коммиты до тех пор, пока они не готовы, а потом по результатам сквашу, если нужно и пушу.
                                      • 0
                                        От того у вас и эти проблемы с push, костыли в виде commit phases, когда все работает с ветками просто замечательно и поломать довольно сложно.

                                        Просто надо привыкнуть делать правильно, потом руки будут сами тянуться к git checkout -b… ;)

                                        p.s. Интересно, как вы решаете проблему с автомержем при pull?
                                        • 0
                                          Я не делаю пуллы, я делаю фетчи и ручные ребейзы

                                          ps: у меня нет никаких проблем, я просто попытался придумать хоть какое-нибудь применение mercurial phases (я об этом даже специально сказал, чтобы не подумали, что я и вправду их использую)))
                                    • 0
                                      Мне кажется, что если вы работаете не один над фичей, то это неправильные фичи.

                                      Как мне кажется, фичи должны быть атомарными — так чтобы каждый человек мог сделать кусок.
                                      На крайняк можно сделать так
                                      master — feature_1 — feature_1_subtask_1 — feature_1 — master
                                                         \   feature_1_subtask_2  /
                                      
                                      • 0
                                        Ну это субъективно.

                                        Практика (несколько тысяч бренчей и куча девелоперов) показывает, что подход работает (хотя я о своём опыте в данном тредике вообще не говорил, я лишь попытался придумать практическое применение mercurial phases, о чём и сказал в самом начале)
                                        • 0
                                          Не, это все понятно — я просто говорю о том, что так что в гите, что в меркуриале по моему мнению работать неправильно. Ну точнее что значит неправильно — лишает строгости и лаконичности, которую нам дарует successful branching model и построенный на ней git flow.
                                          • 0
                                            А successful branching model запрещает в одной и той же ветке работать вдвоём разве?
                                            • 0
                                              Мое личное мнение — он этого не подразумевает. Собственно, вероятно у меня это все в голове смешивается с понятием о вообще правильной постановке задачи.
                                              Оттуда уже и видение правильного использования инструментов.
                                        • 0
                                          > несколько тысяч бренчей и куча девелоперов

                                          мне сложно представить зачем столько вообще может понадобится(особенности mercurial?). В том же ядре линукса одна ветка и куча тегов. Но теги то понятно почему куча, это просто указатели.
                                          • 0
                                            фичабренчи, особенность проекта :-)

                                            репозиторий на гите

                                            > Но теги то понятно почему куча, это просто указатели.

                                            Бренчи в гите это точно такие же указатели. Их единственное различие, что они с HEAD двигаются вместе.
                                            • 0
                                              Это понятно, что это всего лишь указатели, но теги -это именно теги, а ветки — это именно ветки с историей.

                                              Зачем вам 1000 веток с историей, вот в чем вопрос?
                                              • 0
                                                А это проблема скорее организационная :-)

                                                Они не мешают, потому особенно никого это не волнует.

                                                > а ветки — это именно ветки с историей.

                                                Ммммм, не хочется спорить, но я не согласен. В гите бренч это лишь указатель на конкретный ченджсет.

                                                А если вспомнить, что ринадлежность ченджсета тому или иному бренчу в гите происходит в рантайме, то удаление бренча это скорее зло, чем добро. Потому что после удаления бренча невозможно сказать, в каком бренче это изменение было добавлено (если только не оставлять это же имя в комментариях специально для этого)
                                                • 0
                                                  > А это проблема скорее организационная :-)
                                                  выглядит это именно так :)

                                                  > В гите бренч это лишь указатель на конкретный ченджсет.
                                                  который держит целую цепь комитов, и чем более ветвистое это дерево тем сложнее с ним работать. Тег тоже может держать цепь комитов, если скажем ветку удалить, но добавить новый вы не сможете пока заново не создадите ветку. То есть да, это все указатели, только свойства у них разные.

                                                  > Потому что после удаления бренча невозможно сказать, в каком бренче это изменение было добавлено
                                                  Ни разу не сталкивался с этим, можете пояснить зачем может понадобится знать откуда пришел комит? Ну например, о, этот комит пришел из ветка_супер_фича, что дальше?
                                                  • 0
                                                    Например, это позволит узнать цель тех или иных модификаций
                                                    • 0
                                                      Для этого обычно используется описание комита. Не убедили.
                                                      • +1
                                                        В комит не вместишь столько, сколько можно вместить в документе, который описывал фичу. Я не понимаю, почему вы принципиально хотите ограничить себя в объёме доступной информации.

                                                        Так или иначе, я здесь не для того, чтобы вас переубедить. Для вас работает один способ, для меня другой. Не убедил — окей.
                                                        • 0
                                                          > В комит не вместишь столько, сколько можно вместить в документе, который описывал фичу.

                                                          1. а сколько информации можно вместить в имя ветки, о, или вы еще документ сохраняете с комитом?
                                                          2. на этот случай обычно указывается номер тикета и краткое описание. По номеру тикета легко находится полное описание.

                                                          > Так или иначе, я здесь не для того, чтобы вас переубедить
                                                          я с вами согласен, я тоже не для того что бы переубеждать вас, но когда вы говорите что для нормальной работы на большом проекте нужно 1000 веток я просто ну ни как не могу согласится, к тому же я не видел ни одного опен сорс проекта с таким количеством веток. Тот же андроид и линукс как то же живут и проблем не знают, и там разработчиков, я думаю, будет по более чем в вашем проекте.
                                                          • 0
                                                            > 2. на этот случай обычно указывается номер тикета и краткое описание. По номеру тикета легко находится полное описание.

                                                            Да, т.е. техническая проблема «получить название ветки» вы предлагаете решать организационно «давайте не будем забывать добавлять номер тикета». А чтобы по-настоящему не забывать — давайте добавим хуки, которые нам помогут это не забыть.

                                                            Итого — у вас 1 организационный инструмент и 1 технический, у меня — 1 технический, при том же результате.

                                                            > говорите что для нормальной работы на большом проекте нужно 1000 веток

                                                            Это исторические ветки, которые после решения задачи просто напросто не были удалены. Понимаете, проект живёт долго, потому фич было больше 1000. А бренчи удалены не были. И они никому не мешают, они где-то там вверху графа, и их никто даже не видит. Есть они не просят, для анализа графа и решения текущих задач не мешают. В чём проблема-то? :-)
                                                            • 0
                                                              У вас случайно написание текста комита не является организационным моментом?
                                                              Давайте еще в теле комита писать
                                                              — комит
                                                              — тест комит
                                                              — ку-ку
                                                              все равно в ветке лежит документ с описанием, так? :)

                                                              Я считаю это обязанность любого разработчика написать нормальное описание комита, включающее туда всю необходимую информацию, как минимум, к какому тикету принадлежит и что именно патч делает.

                                                              В этом случае отпадает необходимость в долго живущих фиче ветках и остальных костылях, в виде сохранения документа с описанием.
                                                              • +1
                                                                Долгоживущие ветки в репозитории в моём случае это не необходимость, это лишь данность. Ветки есть просто потому что они есть и не удалены. Не удалены — потому что они никому не мешают
                                                  • 0
                                                    > и чем более ветвистое это дерево тем сложнее с ним работать
                                                    Удаление имени бренча «проблему» с ветвистым DAG никуда не убирает. Просто из этого дерева пропадают метки (бренчи) напротив некоторых ченджсетов, а дерево остаётся тем же самым, с которым «сложно работать» :-)
                                                    • 0
                                                      > Просто из этого дерева пропадают метки (бренчи) напротив некоторых ченджсетов, а дерево остаётся тем же самым, с которым «сложно работать»

                                                      Как то вы не так работаете с ветками. Ну есть у нас 5-6 веток на все случаи жизни. Все остальное это временные ветки, которые по завершению ребэйзятся по верх одной из 5. Ни каких ветвлений и срача в истории.
                                                      • 0
                                                        >> Как то вы не так работаете с ветками

                                                        У вас свой опыт, у меня свой. У меня он работает. Прекращайте считать свой опыт единственно верным.

                                                        >> Ни каких ветвлений и срача в истории

                                                        Удаление веток вообще никак со «срачем» (спасибо за характеристику репозитория, который вы даже и не видели) и ветвлением не связано.

                                                        Объём ветвлений зависит ТОЛЬКО от числа разрабатываемых фич. Вне зависимости от подхода граф будет ветвиться только по числу фич, и ваше решение даст ту же самую картинку, что и моё. Разве что вы удалите потом названия бренчей из графа, а я нет.

                                                        Вы с этим хоть согласны?
                                                        • 0
                                                          > Удаление веток вообще никак со «срачем» (спасибо за характеристику репозитория, который вы даже и не видели) и ветвлением не связано. Вы с этим хоть согласны?

                                                          Судя по вашему же описанию, у вас создается одновременно огромное количество веток для каждой фичи, мало того эти все ветки потом еще и живут. Вот после такого дерево очень красивое, ветвистое получается — это и называется срач, его нужно прибирать через rebase и удаление старых веток.
                                                          • 0
                                                            Нет, эти ветки исторические, они создаются в момент решения задачи, потом по завершению задачи мерджатся куда нужно и просто остаются в истории, без удаления (потому что зачем их удалять?)).

                                                            Прошло полдня, но так и не понял, почему удаление старых веток что-то должно менять. Дерево то же, визуально выглядит так же, нет только меток.
                                                            • 0
                                                              > завершению задачи мерджатся куда нужно
                                                              > Дерево то же, визуально выглядит так же, нет только меток.

                                                              Либо у вас не так много людей одновременно работает, либо ветвистость у вас не считается какой то проблемой. Тут два программиста работают и ветвистость есть, а когда их скажем 300, и вы говорите что проблемы нету, тем более что вы ветки мержите а не rebase делаете? :)
                                                              • 0
                                                                Проблем нет, делаются мерджи :-) Ветвистость есть, но от неё не уйдёшь
                                                                • 0
                                                                  > Ветвистость есть, но от неё не уйдёшь

                                                                  Вот оно наконец то. Ветвистость легко обходится при желании, когда его нету можно и 1000 веток оставить.
                                                                  • 0
                                                                    Желания нет, потому что проблемы нет.

                                                                    Мердж вместо ребейза — более удобный (субъективно, для меня и проекта) способ управления проектом и организацией репозитория.
                                                                    • 0
                                                                      Работа с одновременно активными даже 5-6 веток, то еще удовольствие, а у вас их >1k
                                                                      Я надеюсь вам никогда не придется накатывать комиты на копию проекта один за одним.
                                                                      • 0
                                                                        Мы не работаем с > 1000 веток одновременно. Я уже дважды сказал, что эти ветки исторические, в них работа велась, скажем, два года назад. С тех пор ветку вмерджили в релиз и оставили на память. Есть она не просит.

                                                                        Каждый разработчик работает со своей веткой исключительно.

                                                                        То, что где-то когда-то были созданы бренчи никому не мешает (и я не могу представить, как оно в принципе может как-то кому-то мешать).
            • +1
              Получить отказ ребейзить (и вообще менять) коммит потому, что он уже выпинан куда-то ещё.
              • 0
                А почему вы вообще должны даже начать думать о ребейзе паблик ветки?
                Складывается ощущение что в виду не правильной работы с ветками, приходится использовать защитные костыли.
                • +1
                  Невнимательность/забывчивость/опечатка. Git на такое даже ухом не пошевелит. Ну и не rebase единым.
                  в виду не правильной работы с ветками
                  какая забавная опечатка в слове «непривычная».
                  • 0
                    Вы вроде бы что то написали, но вообще нечего не понятно, что оно и к чему.
                • +2
                  Когда phases только появились, читал где-то в wiki mercurial или в чьём-то блоге историю и предпосылки появления этой функции. Так вот, это именно защитный механизм от ребейза ченджестов (и других изменений истории), которые уже были запушены в удалённый репозиторий. Для иллюстрации проблемы приводилось письмо Линуса в мейл листе, в котором он сокрушался на одного из контрибьюторов ядра, что тот опять сделал ребейз публичной ветки поверх своих комитов. Так что проблема не надумана, а очень даже насущна.

                  Бегло погуглил, найти эту ссылку не смог, сорри, но история была.
                  • 0
                    Спасибо за внятный ответ. А как именно работает phases, его нужно предварительно настроить или оно само работает, и какова вероятность что пользователь не сделает force уже существующей ветки при пуше?
                    • +1
                      Для того, чтобы оно работало, нужно только обновиться. «Сделать force существующей ветки» так же, как в git, невозможно — из истории на удалённом сервере нельзя удалить ничего, если только у вас нет там доступа к shell. Сделать rebase, «проигнорировав» фазы можно — сначала помечаете изменения как черновики («phase --force --draft»), затем делаете rebase, затем push (опять с ключом --force). Правда всё, чего вы добьётесь, — это появления новой головы в репозитории. При следующем pull изменения, которые вы якобы переместили, опять у вас появятся. Перемещённые версии, впрочем, тоже сохраняться.

                      Phases не запрещают стрелять себе в ногу. Они только усложняют нажатие на курок.
                      • 0
                        Для того, чтобы оно работало, нужно только обновиться.
                        Сервер обновлять не обязательно, подробнее в «hg help phases».
                  • 0
                    www.mail-archive.com/dri-devel@lists.sourceforge.net/msg39091.html — не оно ли?
        • +3
          другие DVCS, выступают в роли догоняющих
          А вот расскажите, пожалуйста, поподробнее, как именно вы пришли к этому выводу.
          • –7
            imho, если бы они были на столько круты и удобны, Линус бы не стал писать велосипед и ядро было бы уже под ним.
            но что то я не вижу кучи проектов, макс для контроля версий используют: git, svn или mercurial (коммерческие рассматривать нет смысла).
            • +4
              Вы даже статью не почитали: разработка Mercurial и Git стартовала одновременно. Олсо Линусу были необходимы octopus merge.
              • 0
                Ну не совсем так.
                Согласно википедии: en.wikipedia.org/wiki/Mercurial

                Mackall decided to write a distributed version control system as a replacement for use with the Linux kernel. This project started a few days after another project called Git, initiated by Linus Torvalds with similar aims.

                В двух словах: Линус не найдя ничего подходящего, начал писать сам. Несколько дней позже аналогичный проект затеял Mackall.
                • +3
                  Пара дней что-то решают? :-)

                  Ну серьёзно, за пару дней ещё не было ничего даже близко рабочего и отражающего суть будущего проекта. Не говоря уже о том, что они могли не знать о намерениях друг друга, или знать не всё.
                  • 0
                    Вы так говорите, как будто Линусу нужно было подождать 2 дня и начать использовать Mercurial?

                    На самом деле ничего не подошло и меркуриала еще не было. Линусу нужно было сидеть и ждать с моря погоды, пока кто то догадается написать нужную для него dvcs?

                    Вот он начал писать сам, откуда он знает что какой то Mackall начал писать чуть позже тоже, к тому же свою dvcs он может контролировать как угодно и ни под кого не подстраиваться.

                    В общем все как написал выше, не было ничего подходящего и он начал писать сам, в чем я не прав?
                    • +1
                      Нет, не говорю.

                      Это было насчёт вашего

                      > Ну не совсем так.

                      В мире ПО, в особенности такого сложного, два дня это таки «одновременно»

                      Вы правы, что не было и что он сам начал писать. Более того, вы правы буквально насчёт «не одновременно», но фактически — одновременно :)
                      • 0
                        > В мире ПО, в особенности такого сложного, два дня это таки «одновременно»
                        Да вы правы. Но если у Линуса ничего нету и у Mackall ничего нету, почему Линус должен выбрать версию Mackall, которой нету? Конечно он будет писать свою :)
                        • +1
                          Не должен :-)

                          Я лишь апеллировал к вашему «Ну не совсем так.», всё остальное окей :-)
    • +7
      Ну к примеру «Ртуть» девелопят более прагматичные люди.
      Все основное стараются запилить на Python и только то что действительно имеет смысл оптимизировать пишут на си. Более того расширения к «ртути» пишутся на Python и если чего из мануала непонятна на Pythonе прочитаешь. Ведь сейчас многие современные девелоперы или Ruby или Python «как орешки щелкают», т.е. легко код читают\пишут на этих языках.

      Да, и как описал Джоэл Спольски(на хабре есть перевод на русский из 6 статей) наименование команд в SVN почти один в один в Mercurial. Примеры: hg rename, hg add, hg remove, etc. А в виду популярности этой SVN переход на Mercurial за счет знакомых имен команд как-то проще осуществляется.
      • –10
        Единственное нормальное объяснение зачем нужен этот mercurial вообще
    • +7
      git не устраивает отсутствием нормального клиента, который освоит дизайнер.
      Любая проблема требует консоли.

      SVN такого недостатка не имеет.
      • +2
        Вполне себе дизайнеры пользуются SmartGit и достаточно успешно.
      • +2
        SVN для дизайнера самое — то. Да и правильно это! А вот разработчику SVN уже «тесно». Все эти Git, Mercurial они поощряют экспериментирование без которого ни обходится ни одна разработка.

        Приведу пример на Mercurial:
        Я хочу попробовать запилить фичу. Для этого делаю новый бранч, девелопю, комичу и вдруг на каком-то этапе я вдруг прихожу к выводу «да это же гуанкод, это нельзя никому показывать». Что я делаю? Я просто удаляю папку!!! Все. Никто никогда и не узнает, что я написал какой-то бред. А в SVN если вы уже создали бранч, то он там будет на вечно!

        А в случае с дизайнером такого нельзя допускать! Потому что одному дизайнеру может показаться «бредом», а другой дизайнер в этом «бреде» может увидеть что-то что приведет к красивому решению. Поэтому все дизайнерские наработки, какими бредовыми они не были должны быть собственностью компании.
      • –1
        Github for Windows?
        • 0
          При первой же ошибке консоль предложит открыть.
    • 0
      Ну допустим у вас есть репозиторий с данными. И куча приложений, работающих с разными папочками в этом репозитории. Представьте оверхед по сравнению с svn.
    • +3
      Впрочем, выбор в пользу Git можно делать и руководствуясь техническими аргументами. Их три:
      1. Octopus merge
      2. Создание тэга не создаёт коммит
      3. git add -i умеет распиливать hunkи
      • +2
        AuRecord тоже умеет распиливать hunk’и, даже и для subversion, если надо. И для mercurial. Третий аргумент исчезает, если правильно выбрать UI, потому что идея, используемая hg record универсальна и работает для любой VCS, умеющей status и cat-file.

        Первый аргумент мне совершенно непонятен — в чём преимущество octopus merge перед двумя merge? Только количеством ревизий?

        А вот второй аргумент меня зачастую весьма достаёт.
  • +3
    Почему вы умолчали о mercurial.selenic.com/wiki/Bookmarks? Те же гитоветки.
    • 0
      Bookmarks в Mercurial это lightweight-tag в Git'е: оба содержат только имя для коммита и ничего больше.

      «Ветки» Git'a, это, скорее, heads — соответствуют heads в Mercurial. Одна ветка в Mercurial может иметь несколько голов, хотя обычно этим не злоупотребляют.

      Там еще много интересных отличий. Например, изменение тэгов в Mercurial входит в коммит и отслеживается в дереве истории, тогда как в Git'е для сохранения информации о дате и авторе ярлыка надо сделать tag c описанием (annotated и/или signed), но в граф истории создание/изменение тэга не включается.
      • +2
        При появлении у коммита потомка bookmark начинает указывать на этого потомка. Совсем как git branch.
        • +1
          Да, точно. Я, похоже, погряз в деталях внутреннего устройства Git'a и Mercurial'а и не сразу понял что Вы хотели сказать.

          Ветки в Hg предназначены и используются для тех же целей, что и в Git'e, причем Hg-коммит привязан к конкретной ветке. Видимо, это часть того, что автор статьи назвал строгой работой с историей.

          Закладки Hg более легковесны чем ветки, при этом активные закладки ведут себя как heads в Git'е. Так что — Вы правы — их удобно использовать с той же целью.
  • –5
    Я бы переименовал эту статью так: «Подробное объяснение, почему Mercurial — говно.»

    Например, для целей ведения коммерческого программного проекта мне больше импонирует Mercurial.
    Строгая работа с историей в Mercurial гарантирует возможность учёта и поиска первоначального источника ошибки.

    Три раза «ха»!
    И чтобы, не быть голословным я просто приложу картинку, на ней изображен маленький кусочек дерева одного проекта в Mercurial, по понятным причинам без лишних подробностей.

    И каждый, кто скажет, что по такой полной истории удобно ходить и что-то там искать, пусть кинет мне в карму.



    • +8
      Изучите матчасть и научитесь пользоваться bookmarks. Благо они в ядре с версии 1.8. Для короткоживущих веток — самое оно.
      • –2
        А как же тогда полная история?
        Про которую я слышу каждый раз когда кто-то хвалит Меркуриал.
        Насколько я знаю букмарки локальны и не идут в дерево.
        Т.е. все преимущества мимо.
        • +3
          Они уже умеют синхронизироваться с сервером.
          • –15
            Капитан Жан Люк Пикард скажет за меня

            image
        • +5
          Насколько я знаю
          Ведь это же только Git развивается.
          • +1
            Ок вы не поняли над чем я смеюсь, я поясню.
            Вам не кажется смешным, что сначала придумываются букмарки, которые как бранчи, только локальные, чтобы не срать в историю, а потом букмаркам делается возможность срать в историю, в результате мы получаем бранчи, которые срут в историю, и букмарки которые срут в историю. Что-то мне теперь не понятно, а где разница то?
            • +3
              Чтобы несратьвисторию есть MQ. А букмарки придумали/позаимствовали для короткоживущих веток.
              а где разница то?
              имя branchа — свойство коммита, имя bookmark — имя указателя на коммит. вы что, мануалы совсем не читали?
              • –2
                А что мне это дает как пользователю?
                • +4
                  Оно даёт как бы branch, который можно взять и удалить.
                • 0
                  оно дает как бы локальный бранч, который не надо давать другим / пушить в ориджн / писать в историю
              • 0
                Возможно я ошибаюсь, но у меня сложилось впечатление, что MQ/branch/bookmark в mercurial представляют из себя разные паттерны использования веток в git. Если так, то не очень понятно, зачем изучать несколько механизмов, чем разобраться с одним (branches & rebase).
                • +7
                  На пальцах: Git не умеет hg branches, Mercurial умеет git branches ⇒ больше способов ветвиться == добро и счастье. Как вы их будете применять и будете ли вообще — дело ваше.
                  MQ ­— очередь патчей. Работа с ней — отдельная наука. Полным её аналогом являются stgit и вроде как ещё GitUM. Staging area же — очередь из одного патча.
                  • +4
                    Я так понял, что собственно ветки нужны для долгоживущих вещей вроде release-2.7, current-development, …, а закладки — для feature branches, чтобы исчезнуть после слияния. Во всяком случае, это кажется логичным.
                    • +1
                      Да, именно.
                    • 0
                      Правильно. В git для и для того, и для другого используются ветки. Достаточно хорошо освоить один механизм. Тем более, что бывает, что некоторые feature branches начинают жить долго :)
                      • 0
                        Закладки — это полный аналог веток в git. Нет никаких проблем иметь долгоживущие закладки вместе с долгоживущими ветками или использовать только их. А вот если вам важно сохранять информацию о том, к какой ветке принадлежит изменение, то в git ничего для этого нет.
                        • 0
                          Не пользовался, но давно мучит такой вот вопрос:

                          закладки же фактически создают ветвление в пределах одного бренча. Будет ли меркуриал ругаться о новых головах в этом случае? По идее должен.

                          Как эту проблему пользующиеся букмарками решают?
                          • 0
                            Он же сам подсказывает — «push -f».
                            • 0
                              Эм, но это неправильно же? Если для выполнения операции требуется -f, значит кто-то что-то делает неверно.

                              Но, понятно, значит никакой магии
                          • 0
                            Ну так вы же мержитесь по имени конкретной закладки. Если попробовать влить в ветку где есть несколько голов с закладками то разумеется оно ругнется.
                            • +1
                              Мой вопрос был скорее о том, что вся реализация букмарков в меркуриале обязывает юзать -f при пуше, что чревато проблемами
                              • +1
                                По-моему, вы субъективно воспринимаете «ключ силы» -f как что-то деструктивное. В данном контексте он означает «да, я прочитал предупреждение».
                                • 0
                                  > как что-то деструктивное

                                  Потому что оно и есть дестркутивное. Вместе с безобидными букмарками вы можете на центральный репозиторий отправить что-то ещё, сами того не подозревая об этом.

                                  Примера назвать не смогу, но вы не можете быть уверены, что ваши изменения не сломают что-нибудь, просто потому что вы уже сняли предохранитель и не узнаете о возможных проблемах.
                                  • +2