Справочник по стратегиям поставки со сниженным риском: Blue/Green Deployment, Canary Releases, A/B (split)-тестирование и Feature Toggles, подготовленный на основе собственных заметок, сделанных в разное время под различные нужды.
Blue/Green Deployment
Существование двух прод систем в одно время. Используется, если требуется проверить новую версию приложения на боевой среде перед тем, как перенаправлять на нее трафик.
Blue/Green — дорогая стратегия и ее лучше резервировать под критичные сервисы. Менее критичные вполне могут деплоится с небольшим даунтаймом.
Фичи, которые разворачиваются на определенную когорту пользователей могут использовать Canary Releases (следующий раздел).

Особенности
Стоимость
В общем случае удваивается стоимость прода. Можно снизить за счет поднятия Green только при деплое новой версии.
Zero Downtime
В лучшем случае — полная доступность только на чтение. В OLTP приложение переводится в read-only на время синхронизации данных.
Базы данных
Строго говоря — нужны две. С одной базой можно не переводить в read only.
Rollback
Простым переключением обратно. Однако данные накапливаются. Возможна потребность в корректировках. Лучше стратегия Roll Forward.
Особое внимание
- Долгоживущие транзакции
- Обновление баз данных
- Готовность инфраструктуры к переключению
- Если Blue и Green не изолированы — есть риск уничтожить оба окружения
Canary Releases
Выполняется постепенное развертывание. Используется, когда требуется развертывание без простоев и приложение поддерживает выполнение старого и нового кода одновременно.

Когда использовать
- Система состоит из микросервисов, развивающихся с различной скоростью и проверка функциональности должна проходить в реалистичной среде, идеально — на проде.
- У изменений высокий операционный риск и они должны проверяться с помощью экспериментов на небольшом объеме трафика
- Сервис зависит от внешних систем, с которым невозможно или очень сложно провести эффективное тестирование и единственный способ проверки — непосредственная интеграция с системой
Когда не использовать
- При создании критических систем, сопряженных с безопасностью или жизнью людей, в которых ошибка недопустима. Никто не хочет видеть канареечные релизы в системе жизнеобеспечения.
- Высокая чувствительность пользователей к канареечным экспериментам. Например, операции на огромным числом транзакций в финансовом приложении.
- Эксперимент потребует модификации бэкенда (или базы данных) способом, который не совместим с текущими требованиями к обслуживанию. Например — изменения общей производительности для всего сервиса.
Типичная реализация
С помощью прокси (Envoy, HAProxy), балансировщика или роутера.
Релиз инициируется с помощью CD-оркестратора (Jenkins, Spinnaker), DevOps-платформы (Electric Cloud) или SaaS-платформы (LaunchDarkly, Optimizely)
Технические требования
- Возможность наблюдения за системой, сильная система метрик
- Программируемый прокси или балансировщик, раскрывающий API для динамического управления трафиком
- Декларативное описание конфигурации для использования GitOps
- При изменениях в схеме данных использовать паттерн https://martinfowler.com/bliki/ParallelChange.html
- Передача и парсинг заголовков или токенов, идентифицирующих канареечный запрос
A/B (Split)
Предприниматели вынуждены принимать множество решений, часто с неопределенной или неизвестной отдачей. Такими решениями могут быть: какую фичу реализовать, через какой канал вести продажи или какой тип клиентов обслуживать.
Общий фреймворк выглядит так: генерация идей для выявления вариаций в количестве и природе стратегических опций, тестирование жизнеспособности отобранных опций и принятие решение на основе результатов тестирования.
Здесь и может помочь A/B-тестирование, цели которого — проверка бизнес-решений, снижение стоимости оценки конкурирующих идей и принятие решений на основе данных.
Дадим определение. A/B тестирование — это контролируемый эксперимент, в котором вы держите все переменные постоянными, кроме одной или двух для определения их влияния на целевой показатель.
Канареечные и A/B тесты в чем-то схожи. И те и другие позволяют релизить несколько версий фичи параллельно, сокращают радиус поражения от потенциальных багов с возможностью постепенного продвижения по различным демографическим регионам. Но при этом A/B тесты в большей степени специализируются на проверке удобства использования и влиянии на прибыль.
Цели конкретных экспериментов могут быть более точными:
- Сокращение уровня отказов
- Увеличение среднего времени на странице
- Конверсия читателей статей в клиентов
- Конверсия из социальных сетей в клиентов
- Сокращение времени загрузки страницы
- Улучшение производительности лендинга
Возможная релизная стратегия
Мы можем проводить A/B тесты на внутренних пользователях или, в более сложных сценариях, на клиенах с определенными предпочтениями.
Через A/B тесты можно так же проверять различные версии алгоритмов и изменения в атрибутах качества.
Типичные процесс выглядит следующим образом:
- Внутренняя техническая группа. Немедленное устранение проблем.
- Внутренние клиенты (руководство и продуктовые команды). Небольшие изменения.
- Малая группа потенциальных клиентов
- Небольшая специально отобранная группа существующих клиентов
- Все остальные
Такая стратегия выражается в кругах влияния. На каждом из кругов можно остановиться и исправить.
Управление трафиком
Слепое деление трафика 50/50 — это плохо. Трафик должен быть разложен по источникам.
Примеры: органика, рекламный трафик, прямые заходы.
Правила
- Тестирование одного компонента за раз. В мультивариантной среде сложно определить, что именно повлияло на изменение целевых метрик.
- Алгоритм доставки контента
- Расположение элементов UI
- Бандлы, цены, стратегии отображения продукта
- Соцальные фичи
- Рекомендательные алгоритмы
- Контент для увеличения уровня вовлеченности
- Расположение статей или видео на сайте
- Варианты заголовков
- Стоимость подписки
- Тестирование реселлеров
- Тестирование минорных изменений. На сайтах обычно мелочи оказывают максимальное влияние: расположение форм, кнопок, их цвет и так далее.
- Проведение высокоуровневых тестов. Совершенно разные страницы. Это лучше, чем та же страница с множеством изменений.
- Анализ множества метрик в совокупности относительно целевой метрики
- Создать идентичные условия: аудитория, время суток. Повышение статистической значимости результатов.
- Разные гаджеты — разные переменные, разные результаты.
Feature Toggles
Позволяет отделить поставку от релиза и отключить функциональность на боевых серверах в случае необходимости. Это узкое определение. Более широкое — дает полный контроль над жизненным циклом отдельно взятой фичи.

Фиче тоглы позволяют разработчикам держать под контролем жизненный цикл фичи без зависимости от поставки кода. Фича сразу оборачивается в тогл и отправляется в прод со всеми. Когда релизить фичу — отдельное решение (не техническое).
Преимущества
- Совместные усилия при работе над релизом
- Логические поставки избавляют от блокировок при неполной готовности фичи
- Ускорение разработки за счет сокращения затрат на мердж конфликты и рефакторинг
- Снижение рисков поставки
- Управляемые код ревью за счет частых и небольших коммитов
Вариации управления переключателями
- Параметры командной строки
- Через базу данных
- Админка
- Rest API
- Параметр в коде
Использование для миграции данных
- Пишем второй DaoNew
- Заводим 4 флага: «чтение» и «запись» для каждого Dao
- Начинаем открывать «запись» DaoNew, оцениваем результаты и ищем ошибки
- Начинаем открывать «чтение» DaoNew для небольшой группы пользователей со сравнением результатов
- Миграция данных
- Отключаем read/write к старой базе
- Вычищаем Feature Flags
Процесс перехода к Feature Toggle
- Выявить текущие болевые точки
- Что сейчас сложно делать?
- Какие проблемы возникают в процессе разработки?
- Какие из них продолжают возникать в проде?
- Определить сценарии использования
- Для чего будет использоваться FT?
- Кто стейкхолдеры (кроме разработки)?
- Требуется ли улучшение взаимодействия между участниками процесса?
- Писать свое или купить готовое?
- Total Cost of Ownership
- Развитие системы при росте аппетита бизнеса
- Технический долг
- Неизвестный, эволюционирующий скоуп. Подобные платформы все еще в новинку и определить скоуп может оказаться затруднительным.
- Минимальная жизнеспособная функциональность. Обычно внутренние разработки не сильно акцентируются на юзабилити, масштабируемости или кросс-командной поддержке. Они создаются, чтобы устранить острую боль с помощью минимальной функциональности.
- Поддержка множества языков. Требуется знать нюансы языков, чтобы не попасть в просак с производительностью и стабильностью работы.
- Комплаенс. Контроль доступа, логи, аудит, кастомные права.
- Total Cost of Ownership
- Принять решение
- Атрибуты: стабильность, поддержка множества языков, масштабируемость, интуитивность, поддержка
- Интеграция и коллаборация. Изменение в том числе культуры. Вместо отправки сразу на прод готовой фичи, управление разработчиком ее релизным циклом самостоятельно. Самостоятельное планирование релиза фичи.
На что обратить внимание
- Соглашение об именованиях. Чтобы у двух команд не было флага с одним именем.
- temp-временные, без temp- — эксплуатационные
- Удаление неиспользуемых флагов. Если все время в состоянии on или off — удалить.
- Логирование изменения состояний флага
- Контроль доступа к флагам
- Просмотр статусов флагов