ќсновы CI/CD

Continuous Integration / Continuous Delivery

ћерион Ќетворкс

ќсновна€ цель любого проекта по разработке ѕќ – получить прибыль за счет автоматизации бизнес-процессов. „ем быстрее вы начнете выпускать новые версии, тем лучше дл€ компании. Ќо как же научитьс€ выпускать новые версии максимально быстро?  онечно же, все можно делать вручную. Ќапример, подключить удаленный сервер через SSH, клонировать клонировать репозиторий с новым кодом, собрать его и запустить через командную строку. ƒа, такой способ работает, но он малоэффективен. —егодн€ мы поговорим об автоматизации процесса разработки и выхода новых версий.

CI и CD – это два сокращени€, которые означают Continuous Integration (Ќепрерывна€ интеграци€) и Continuous Delivery (Ќепрерывное развертывание).


CI

CI описывает процесс добавлени€ изменений в репозиторий. Ќиже схематически представлен простой пример коллективной разработки.

ѕростой пример коллективной разработки

ќдновременно может работать цела€ группа людей, но все изменени€ передаютс€ в главную ветку master поэтапно. ’от€ даже в такой простой схеме возникает несколько вопросов.

  1.  ак мы узнаем, что код, который идет в ветку master, компилируетс€?
  2. ћы хотим, чтобы разработчики писали тесты дл€ кода.  ак быть уверенными в том, что тестовое покрытие не уменьшитс€?
  3. ¬се сотрудники команды должны форматировать код в соответствие с определенным стилем.  ак отследить возможные нарушени€?

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

CI используетс€ дл€ автоматизации выше обозначенных пунктов.

Ќачнем с первого пункта.  ак можно проверить, что новые изменени€ не сломают сборку? ƒл€ этого нам потребуетс€ еще один блок в схеме.

Ѕазова€ CI

Ѕольшинство CI-процессов можно описать по следующему алгоритму.

  1. ѕри открытии каждого Pull Request (запроса на включение изменений) и отправке новых изменений, Git-сервер отправл€ет уведомление CI-серверу.
  2. CI-сервер клонирует репозиторий, провер€ет исходную ветку (например bugfix/wrong-sorting) и сливает ее с основной веткой master.
  3. «атем запускаетс€ скрипт сборки. Ќапример ./gradlew build.
  4. ≈сли команда возвращает код «0», то сборка прошла успешно. ¬се остальные значени€ считаютс€ ошибкой.
  5. CI-сервер отправл€ет запрос на Git-сервер с результатом сборки.
  6. ≈сли сборка прошла без ошибок, то Pull Request разрешаетс€ слить. ¬ противном случае он блокируетс€.

ƒанный процесс гарантирует, что код, попадающий в ветку master, не сломает дальнейшие сборки.


ѕроверка тестового покрыти€

ƒавайте немного усложним задачу. ѕредположим, нам захотелось установить минимальный охват тестового покрыти€. Ёто означает, что в любой момент времени покрытие ветки master должно быть не менее 50%. ѕлагин Jacoco идеально справл€етс€ с этой задачей. ¬ы просто настраиваете его так, чтобы при охвате тестового покрыти€ ниже допустимого, сборка уходила в ошибку.

–еализовать такой подход проще некуда. Ќо есть небольша€ оговорка. Ётот метод работает только при условии, что плагин настраивалс€ на старте проекта.

ѕредставим ситуацию: вы работаете над проектом, которому уже 5 лет. — момента первого коммита никто не провер€л тестовое покрытие. –азработчики добавл€ли тесты в случайном пор€дке и без какой-либо организации. Ќо вот однажды вы решаете увеличить количество тестов. ¬ы настраиваете плагин Jacoco на минимальную планку в 60%. —пуст€ какое-то врем€ разработчик открывает новый Pull Request. «атем разработчики вдруг понимают, что покрытие – всего лишь 30%. “ак что дл€ успешного закрыти€ задачи нужно покрыть не менее 30% кода продукта.  ак вы можете догадатьс€, дл€ проекта 5-летней давности – это практически неразрешима€ проблема.

Ќо что, если будут провер€тьс€ только будущие изменени€ в коде, а не весь продукт? ≈сли в Pull Request разработчик изменит 200 строк, то нужно будет охватить не менее 120 из них (при тестовом покрытии в 60%). “огда не придетс€ проходить по множеству модулей, которые не относ€тс€ к задаче. ¬ принципе, проблема решаема. Ќо как применить все это к проекту?   счастью, есть решение.

CI с проверкой тестового покрыти€

ќтчет Jacoco отправл€етс€ на сервер тестового покрыти€.

ќдно из самых попул€рных решений – SonarCloud.

—ервер хранит статистику по предыдущим вычислени€м. Ёто очень удобно: вычисл€ть тестовое покрытие не только всего кода, но и будущих изменений. «атем результат анализа отправл€етс€ на CI-сервер, который перенаправл€ет его на Git-сервер.

“ака€ рабоча€ модель позвол€ет примен€ть культуру об€зательного тестировани€ на любой стадии развити€ продукта, поскольку провер€етс€ лишь часть изменений.

≈сли говорить о стиле оформлени€ кода, то отличий практически нет. ћожете попробовать плагин Checkstyle. ќн автоматически отклон€ет сборку, котора€ нарушает любое из за€вленных требований. Ќапример, в коде есть неиспользованный импорт.  роме того, вы можете присмотретьс€ к облачным сервисам, которые выполн€ют анализ кода и визуально отображают результаты в виде графиков (SonarCloud это тоже умеет).


CD

CD описывает процесс автоматического развертывани€ новой версии продукта.

ƒавайте еще немного подкорректируем схему CI. ¬от так конвейерный процесс CI/CD мог бы выгл€деть в реальном проекте.

ѕроцесс непрерывной интеграции и развертывани€

ѕервое отличие – теперь CI-сервер называетс€ CI/CD-сервером. ƒело в том, что зачастую оба процесса (CI и CD) выполн€ютс€ одним и тем же диспетчером задач. “ак что мы будем рассматривать именно этот случай.

Ќо так бывает не всегда. Ќапример, задачи по интеграции могут делегироватьс€ на GitLab CI, а задачи по доставке – отдаватьс€ в Jenkins.

ѕрава€ часть схемы изображает CI. ћы обсудили ее выше. —лева показана CD. «адача по CD создает проект (или повторно использует артефакты, полученные на стадии CI) и развертывает его на конечном сервере.

—тоит отметить, что сервер в нашем случае – это пон€тие абстрактное. Ќапример, развертывание может выполн€тьс€ в кластер Kubernetes. “ак что самих серверов может быть несколько.

ќбычно после стадии развертывани€ на почту приход€т сообщени€ о выполнении. Ќапример, CD-сервер может уведомл€ть подписчиков об успешном развертывании/ошибках.

¬ любом случае, возникает важный вопрос. ¬ какой момент мы должны запускать задачи по CD? “риггеры могут быть разными.

  1. –азвертывание после каждого сли€ни€ Pull Request.
  2. –азвертывание по расписанию.
  3. –азвертывание после каждого сли€ни€ Pull Request с определенной веткой.
  4. —очетание нескольких вариантов.

¬ первом пункте процесс выстроен так, что задачи по CI и CD всегда выполн€ютс€ последовательно. ƒанный подход весьма попул€рен при разработке программ с исходным кодом. Ѕиблиотека Semantic Release помогает настроить проект дл€ прозрачной интеграции данной модели.

¬ажно помнить о трактовке пон€ти€ deploy (развертывание). Ёто не всегда «что-то где-то запустить». Ќапример, при разработке библиотеки, нет никакого запуска. ¬ данном случае процесс развертывани€ означает выпуск новой версии библиотеки.

¬торой пункт не зависит от процесса CI, ведь проект развертываетс€ по определенному расписанию. Ќапример, ежедневно в 01:00.

“ретий пункт аналогичен первому, но с небольшими отличи€ми. ѕредположим, в репозитории у нас есть 2 основные ветки: develop и master. ¬ develop содержатс€ самые последние изменени€, а в master – только релизы версий. ≈сли мы хотим развертывать только ветку master, то не нужно вызывать CD-задачу по сли€нию в develop.

ѕоследний пункт – это сочетание подходов. Ќапример, ветку develop можно развертывать по расписанию в среду разработки. ј ветку master – в реальную среду по каждому сли€нию Pull Request.


»нструменты

Ќа рынке доступно множество решений по автоматизации процессов CI/CD. Ќиже представлено несколько продуктов.

  1. Jenkins. ќдин из самых востребованных инструментов CI/CD в мире. —вою попул€рность он заслужил, благодар€ политике открытого кода (open-source). “о есть вам не нужно ни за что платить. ¬ Jenkins вы можете императивно описывать конвейеры сборки с помощью Groovy. — одной стороны это достаточно гибкое решение, но с другой – требует более высокого уровн€ квалификации.
  2. GitHub Actions. Ётот инструмент дл€ CI/CD доступен дл€ GitHub и GitHub Enterprise. ¬ отличие от Jenkins, GitHub Actions предлагает декларативные сценарии сборки с YAML-конфигурацией.  роме того, в данном решении доступна интеграци€ с различными системами обеспечени€ качества (например SonarCube). “аким образом, сборку можно описать в нескольких текстовых строках.
  3. GitLab CI. ¬о многом похож на GitHub Actions, но со своими особенност€ми. Ќапример, GitLab CI может указывать на определенные тесты, вызывающие ошибку в сборке.
  4. Travis CI. ќблачный CI/CD-сервис. ѕредлагает множество возможностей, не требующих сложных настроек. Ќапример, шифрование данных, которые следует скрыть в публичном репозитории. ≈сть и при€тный бонус в том, что Travis CI можно совершенно бесплатно использовать в публичных open-source проектах на GitHub, GitLab и BitBucket.

—кидки 50% в Merion Academy

¬ыбрать курс