Монорепозиторий
В системе контроля версий монорепозиторий («mono» от греческого μόνος, мо́нос, 'единственный, одинокий' и репозиторий) является стратегией разработки программного обеспечения, когда код множества подпроектов хранится в одном и том же репозитории. К 2017 году некоторым формам этой практики разработки уже более десяти лет, но основное название этой концепции появилось недавно[1]. Многие попытки были сделаны для разделения понятий монолитных приложений и прочих более новых форм монорепозиториев[2][3][4].
Google[5], Facebook[6], Microsoft[7] и Twitter используют огромные монорепозитории с различными стратегиями для масштабирования систем сборки и контроля версий с огромными объёмами кода и ежедневными изменениями.
Преимущества
Существует ряд возможных преимуществ монорепозиториев над отдельными репозиториями[5][8]:
Простота повторного использования кода — схожая функциональность или коммуникационные протоколы могут быть выделены в общие библиотеки и напрямую подключаться к проектам без необходимости в менеджере пакетов для подключения зависимостей.
- Упрощённое управление зависимостями — в многокомпонентной среде репозитория, где разные проекты зависят от сторонних компонентов, эти компоненты могут загружаться или встраиваться множество раз. В монорепозитории сборка может быть легко оптимизирована, поскольку все зависимые компоненты находятся в одной и той же базе кода.
- Атомарные коммиты — когда проекты, работающие вместе, содержатся в раздельных репозиториях, необходимы релизы синхронизирующие версий одного проекта с другим для их совместной работы. В достаточно огромных проектах борьба за совместимость версий с различными зависимостями может превратиться в ад зависимостей.
- Крупномасштабный рефакторинг кода — поскольку разработчики имеют доступ ко всему монолитному проекту, манипуляции по упрощению кода гарантированно сохранят функционирование каждой части проекта после окончания манипуляций.
- Сотрудничество между командами — в монорепозитории, использующем зависимости с исходным кодом, одни команды легче могут улучшать проекты, над которыми работали другие команды. Это ведёт к более гибкому владению кодом.
Ограничения и недостатки
- Потеря информации версий — и хотя это необязательно, некоторые монорепозитории собираются, используя один номер версии сборки по всем подпроектам в монорепозитории. Это приводит к потере индивидуальной нумерации версий каждого подпроекта.
- Отсутствие надёжности подпроектов — с разделением репозиториев доступ к репозиторию может быть предоставлен по мере необходимости. Монорепозиторий даёт доступ для чтения ко всему программному обеспечению в проекте, что, вероятно, представляет угрозу безопасности.
- Больший объём хранилища — с разделёнными репозиториями вы вносите правки только в подпроект, в котором вы заинтересованы. С монорепозиториями вам, возможно, потребуется вносить правки во все подпроекты. Это не является проблемой в случае использования SVN, которая позволяет загружать любую часть репозитория по мере необходимости (даже единственную директорию).
Проблема масштабируемости
Компании с большим числом проектов сталкиваются с проблемами масштабируемости монорепозитория, в частности касающихся инструментов сборки и систем контроля версий[6]. Предполагается, что монорепозиторий компании Google является самым большим в мире и подпадает под классификацию ультра крупномасштабных систем[5] и должен обслуживать тысячи разработчиков каждый день в репозитории размером более 80 терабайт[9].
Компании, использующие или переходящие к существующим системам контроля версий обнаружили, что программное обеспечение не могло эффективно обработать количество данных, необходимое для огромных монорепозиториев. Facebook и Microsoft решили поддерживать или форкать существующие репозитории Mercurial и Git соответственно, в то время, как Google, в конечном итоге, создала свою собственную систему контроля версий.
Более десяти лет Google полагался на Perforce, развёрнутой на единственной машине. В 2005 сервер для сборки Google мог быть единовременно заблокирован до 10 минут, а в 2010 от 30 секунд до 1 минуты[10].
Facebook столкнулся с проблемами производительности системы контроля версий Mercurial и внёс вклад в разработку клиента[11]; в январе 2014 года сделал его быстрее конкурирующей реализации в Git.
В марте 2014 Microsoft анонсировала переход к использованию Git для собственного монорепозитория[12][7]. В процессе перехода Microsoft внесла существенный вклад в разработку Git клиента для удаления доступа к ненужным файлам и улучшила обработку больших файлов посредством виртуальной файловой системы для Git[13].
Лишь несколько инструментов сборки работают хорошо в монорепозитории. Системы, основанные на ориентированном ациклическом графе, такие как Buck (software), Bazel, Pants и Please, используют обособленные сборки и тесты для активной области разработки[1].
Twitter начал разработку Pants в 2011, поскольку Buck от Facebook и Bazel от Google на тот момент имели закрытый код[14]. Twitter открыла код Pants в 2012 году под лицензией Apache 2.0[15].
Система сборки Please, основанная на Go, была разработана в 2016 Thought Machine, вдохновлённой Bazel от Google и недовольной Buck от Facebook[16].
Bazel, Buck, Pants и Please используют Starlark (ранее Skylark) — предметно-ориентированный язык сборки, основанный на Python.
Некоторые специальные инструменты сборки для монорепозиториев, такие как Lerna, разрешают проблему дублирования зависимостей, но не обладают возможностями ориентированного ациклического графа.