Перетяжка, Премия ТПрогер, 13.11
Перетяжка, Премия ТПрогер, 13.11
Перетяжка, Премия ТПрогер, 13.11

Как мы сократили время доставки кода в 40 раз, или Непрерывная поставка в действии

Как сократить доставку кода в 40 раз: опыт CI/CD

972 открытий4К показов
Как мы сократили время доставки кода в 40 раз, или Непрерывная поставка в действии

Что делать, когда разработчики больше ждут, чем разрабатывают

Почему разработчики большую часть времени… ждут?

Как вы думаете, чем обычно занимаются разработчики? Программируют с утра до вечера? Или участвуют в планированиях? Проектируют решения? Проводят ретро? На самом деле, если понаблюдать за отдельными участниками команды в течение рабочего дня, окажется, что рабочий день в основном состоит из… ожиданий.

Ждут всего подряд. Ждут, когда подготовят требования. Ждут, когда пройдет сборка на этапе проверки пулл-реквеста. Ждут, пока его примут. Ждут очередного сборочного агента, прохождения проверок, свободного окна на полигоне, исправления очередного бага на стенде…

Если повезет — не придется слишком долго ждать согласования установки от тимлида в продакшен. Но уж наверняка команду заставит подождать очередной релизный цикл. И вот свершилось — вы в проде… Хотя постойте, ведь надо еще подождать завершения регресса, в котором вот только что выявили блокер, и все ждут его исправления. Если при всем при этом инструменты автоматизации не дали осечки, то мы наконец на проде. И уж тогда вишенкой на торте окажется ожидание включения фича-тогла.

В общем, одно сплошное ожидание. Надо было что-то менять — жизнь слишком коротка, чтобы столько ждать. После анализа процессов решили действовать по трем направлениям: во-первых, поделить команду на фича-команды для быстрого старта разработки; во-вторых, внедрить Trunk Based Development для упрощения работы с кодом; в-третьих, создать систему непрерывной поставки (CDP) для автоматизации доставки до продакшена.

О TBD и CD простыми словами

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

Git-flow — это как обычная касса. Разработчики набирают полную «тележку» изменений в своих ветках, работают неделями, а потом все это нужно провести через сложную процедуру слияния и тестирования.

Trunk Based Development — это экспресс-касса. Берешь одно-два небольших изменения, быстро «пробиваешь» через простую процедуру и сразу попадаешь в основную ветку.

Основные принципы TBD:

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

CD (Continuous Deployment) — это процесс непрерывной поставки кода, который использует полностью автоматизированный конвейер. В нем ваш артефакт, собранный из транка, проходит все этапы контроля качества и доставляется в продакшен без участия инженера. Все виды тестов и проверок безопасности запускаются автоматически, результаты учитываются, и в случае успешного прохождения кволити гейтов происходит автоматизированный деплой в продакшен.

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

При использовании git-flow обычно нужен координатор. Это может быть тимлид, старший разработчик или менеджер релиза, который следит за содержанием фич, попадающих в состав релизной ветки, решает конфликты слияний и контролирует регрессионное тестирование и саму раскатку релиза. С TBD и CD эта сложность просто исчезает — код автоматически проходит весь путь от разработчика до клиента.

Как это было у нас

Фича-команды для быстрого старта

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

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

Переход на TBD

Следующим шагом проанализировали, как работаем с кодом. Выяснилось, что git-flow создает много накладных расходов: нужен координатор, который следит за составом фич в релизе, разрешает конфликты слияний, контролирует релизные ветки и процесс раскатки релиза. Плюс сами ветки живут долго, накапливают изменения, потом их сложно мержить, а главное — достаточно сложно анализировать проблему и устранять ее, если что-то идет не по плану при тестировании релиза или сразу после установки в прод. Ведь в большом релизе достаточно сложно сразу понять, какая именно из фич принесла поломку. Соответственно, анализ проблем в случае их возникновения регулярно затягивался, плюс приходилось проводить поиск ответственных за исправление. Все это накладные расходы, которые несет продукт и от которых хотелось бы избавиться, подыскав новый инструмент.

Решили перейти на TBD. Этот подход на тот момент уже начал внедряться в организации и сулил командам определенные преимущества. Схема простая: ответвляемся от транка, делаем небольшое изменение, сразу вливаем обратно. Никаких долгоживущих веток, никаких сложных схем слияния. Джентльменское соглашение между инженерами тут следующее: вливать в транк можно только логически завершенное изменение, минимальное требование — сервис компилируется и все юнит-тесты проходят. Исходим из того, что эта сборка должна быть готова к установке в пром.

Quality gates и фича-тоглы

Нам нужна была гарантия, что изменения не сломают код в главной ветке. Поэтому добавили Quality gates — автоматические проверки кода перед слиянием. Это набор критериев, которые код должен пройти: юнит и контрактные тесты, проверки безопасности и статический анализ кода на уязвимости, наличие фича-тоглов. Если хоть один критерий не выполнен — код не попадает в основную ветку.

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

Переворачивание пирамиды тестирования

Параллельно занялись пирамидой тестирования. Раньше основная нагрузка была на медленные интеграционные тесты, которые требовали развертывания полных окружений и зависели от доступности полигонов. Если какой-то из сервисов, необходимый для тестирования, на полигоне недоступен — весь процесс встает.

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

Создали систему быстрых и стабильных тестов, которые могли работать независимо от внешних систем. Большую часть проверок перенесли на уровень компонентных тестов — они значительно быстрее интеграционных и при этом проверяют реальную логику работы сервиса. Такое решение позволило отказаться от большей части интеграционных тестов, соответственно, мы уменьшили верхний уровень пирамиды и значительно расширили средний ее слой. Нижний слой увеличился за счет Quality gates и требований к минимальному уровню покрытия нового кода тестами. И пирамида приобрела целевой вид.

В результате уже через 30 минут после написания кода инженеры команды получали заключение и понимали, можно ли ставить эту сборку в продакшен. Вместо дней ожидания — минуты.

Автоматизация доставки

Осталась одна проблема: даже готовые артефакты долго (и не в полном объеме) добирались до клиентов. Подбили статистику: 40% сборок отсеивалось на самом раннем этапе, на первом контроле качества. 10% отсеивалось на Quality gates — не проходили тесты или проверки безопасности. 25–30% терялось на ожиданиях (опять!).

Каких? Поскольку процесс состоял из отдельных джобов, которые надо было запускать последовательно, один за другим, то разработчики ждали завершения работы агентов TeamCity, ждали завершения проверок тестов и сканеров безопасности, ждали установки на полигон. Инженеру приходилось ждать завершения всех технологических процессов, чтобы нажать очередную кнопку для перехода на следующий этап… И так для каждой подготовленной им версии. Конечно, это никому не нравилось: порядка 30% сборок никуда не двигались, хотя были готовы к установке на прод.

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

Continuous Deployment (CD) — это процесс доставки каждого коммита с использованием полностью автоматизированного пайплайна, который берет готовый код и доставляет его в продакшен без участия инженера. Вместо часов ожидания, пока разработчик вручную запустит сборку, увидит результаты и нажмет кнопки для перехода между стендами, мы получили систему, которая делает все это сама, и притом быстро. Код проходит все этапы: сборка → тестирование → проверки безопасности → деплой на тестовый стенд → установка в продакшен.

Ключевое отличие от обычной автоматизации — CD работает end-to-end, от коммита до продакшена. Раньше у нас были отдельные автоматизированные элементы, но переходы между ними требовали ручного вмешательства. CD связал их все в единый процесс с контролем качества на каждом этапе.

Итог: спустя неделю докатили первую полностью автоматическую поставку. Процесс от коммита до установки в прод занял около часа.

Как все это сказалось на разработке

Автоматизация процессов освободила до 15% времени инженеров. Эти часы команда потратила на более глубокую проработку новых задач, закрытие техдолга, личное развитие. Появилось больше времени делать то, что действительно интересно.

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

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

Главное преимущество для клиентов — они получают новые фичи спустя всего час после создания, при этом фичи эти более высокого качества, чем прежде. Это означает быстрое получение обратной связи от пользователей, возможность экспериментировать с новыми идеями, оперативно проводить А/Б-тесты и конкурентное преимущество для продукта за счет высокой скорости реакции на потребности рынка.

Практические советы

Тут может возникнуть закономерный вопрос: «Все это здорово, но это у вас большая организация, команды выделенных инженеров и ресурсы на титанические перевороты тестирования. А что делать нам?»

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

Если у вас низкий ТТМ

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

Если хотите попробовать элементы TBD

Начните постепенно: сократите время жизни веток до двух-трех дней максимум, договоритесь делать ревью приоритетом — отвлекаться от задач ради ревью коллег. Попробуйте фича-тоглы на одной небольшой фиче. Увеличивайте частоту релизов, это приведет их одновременному уменьшению, а значит, увеличению скорости тестирования.

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

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

«База» для разработчика

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

Ну, а если это читает тимлид…

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

Простой план для любой команды

5 шагов к более быстрой разработке

  1. Измерьте текущее состояние — сколько времени тратится от постановки задачи до прода?
  2. Найдите самое медленное звено — ревью, тестирование, деплой?
  3. Начните с одного небольшого улучшения — автоматизируйте самую болезненную операцию.
  4. Улучшите качество изменений — делайте мердж-реквесты меньше и понятнее.
  5. Измерьте результат и повторите.

Прежде чем начнете действовать

Примененные нами подходы — не волшебные решения всех проблем разработки. Это инструменты, которые работают в определенных условиях, и слепо копировать их не стоит. В первую очередь надо оценить готовность команды к изменениям, возможно, вам потребуется дополнительная подготовка «почвы» перед внедрением.

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

Также важно понимать, что в сплоченной команде инженеров обычно не требуется досконально писать документацию, вместо этого мы используем груминги в формате event storming, спецификации API сервисов, BPM-схемы, сиквенс-диаграммы и комментарии, которые являются частью кода самого сервиса. При такой конфигурации команды писать отдельные статьи для декларации намерений разработать ту или иную логику — только тратить время инженеров. Если документация для вас важнее работающего сервиса, стоит задуматься над автоматизацией генерации такой документации… впрочем, это уже тема отдельной статьи.

TBD требует от разработчиков высокого уровня осознанности, ведь важно сохранять код в основной ветке целостным. Страховкой тут являются юнит-тесты и автоматизированный контроль качества перед влитием нового кода в транк. Вам нужна уверенность в том, что ветка целостна и готова к установке в прод в любой момент времени, поэтому компонентные тесты играют очень важную роль, т. к. позволяют проверять функциональность сервиса быстро и комплексно. Их необходимо внедрить в состав Quality gates, чтобы получить преимущества ТБД, а не хлопоты от его использования.

Что касается CD. Это хорошая практика для зрелых команд, позволяющая повысить эффективность работы команды (эффективность измеряем по методике DORA), снизить риски для продуктива при одновременном уменьшении времени доставки кода, а также освободить команду от рутины в пользу более творческих задач. Однако если у вас низкий уровень вовлеченности команды или столь же низкий уровень доверия к инженерам, то, возможно, про этот путь стоит забыть и, опять же, поработать с вовлеченностью инженеров.

Отталкивайтесь от вашей цели, начните с анализа: тратит ли команда значительное время на ожидания? Если процессы уже работают быстро и предсказуемо — возможно, менять ничего и не нужно. Любые изменения требуют времени на адаптацию, команда должна усвоить принципы работы новых подходов, а также осознать преимущества, которые получат клиенты и сами инженеры от внедрения новой практики. В противном случае самые современные практики превратятся в борьбу с сопротивлением или, того хуже, в дополнительную бюрократию, которая замедлит, а не ускорит разработку.

Следите за новыми постами
Следите за новыми постами по любимым темам
972 открытий4К показов