Как реализовать Blue-Green Deployment в Kubernetes?

Что такое Blue-Green Deployment

Blue-Green — это стратегия развёртывания, при которой работают две независимые среды (или версии приложения): текущая «blue» (production) и новая «green». Трафик переключается с blue на green мгновенно или за одну операцию, что позволяет быстро откатиться, просто переключив трафик обратно.

Основные подходы в Kubernetes

  1. Switch Service selector — один Service указывает на набор подов по меткам (например, app=myapp-blue). Для релиза вы разворачиваете myapp-green, проверяете, затем патчите Service, чтобы он указывал на app=myapp-green.

  2. Ingress / LoadBalancer switch — держите два Service (myapp-blue, myapp-green) и переключаете бэкенд в Ingress/области LB. Удобно при использовании облачных TargetGroups/ALB.

  3. Parallel services + external router — у вас два endpoint’а, внешний роутер/NGINX/LoadBalancer меняет целевые группы.

  4. Service mesh / Argo Rollouts — позволяет плавно/автоматически переключать трафик и ставить проверки (можно считать уже за продвинутый подход).

Пошаговая процедура (пример со Service selector)

  1. Подготовка: у приложения должны быть корректные readinessProbe и livenessProbe.

  2. Развернуть green: создать Deployment myapp-green с другим label (app: myapp-green) и нужной версией.
    kubectl apply -f deployment-green.yaml

  3. Подождать готовности: kubectl rollout status deploy/myapp-green и убедиться, что все поды в Ready.

  4. Smoke-тесты: вызвать endpoints на green (через kubectl port-forward, kubectl exec в debug-pod или внутренний LB) и прогнать health checks, интеграционные тесты.

Переключение трафика: поменять selector у Service myapp:

kubectl patch svc myapp -p '{"spec":{"selector":{"app":"myapp-green"}}}'

  1. или отредактировать spec.selector в YAML и kubectl apply -f service.yaml.

  2. Проверить трафик и метрики (latency, errors).

  3. При проблеме — откат: патчнуть selector обратно на myapp-blue. Откат моментален.

  4. Очистка: удалить старый Deployment myapp-blue после подтверждения стабильности или оставить на время как «горячий» откат.

YAML-пример (упрощённо)

# Service (до переключения указывает на myapp-blue)

apiVersion: v1
kind: Service
metadata: { name: myapp }
spec:
selector: { app: myapp-blue }
ports: \[{ port: 80, targetPort: 8080 }\]

Две Deployments с разными метками: app: myapp-blue и app: myapp-green.

Важные операционные моменты

  • Readiness — критичен: Service не направит трафик на неполностью готовый pod.

  • Stateful components / БД-миграции — миграции делайте backward-compatible: сначала добавить поля, потом мигрировать чтение/запись, использовать feature flags; нельзя переключать трафик до гарантированной совместимости.

  • Сессии и sticky sessions — если приложение использует in-memory сессии, переключение сломает пользователей. Решения: external session store (Redis), sticky sessions на LB (учесть TTL), или прокатный подход с синхронизацией сессий.

  • Конфигурации и секреты — убедитесь, что green использует правильные ConfigMap/Secret; избегайте вручную встроенных секретов в image.

  • Мониторинг и алерты — перед переключением соберите baseline метрик и настройте быстрые алерты.

  • DNS/TTL — если вы полагаетесь на DNS-перенаправление, учтите TTL задержку; лучше переключать на уровне ClusterIP/Ingress/LB, а не изменять DNS, чтобы избежать propagation delay.

  • Automatization — CI/CD (Helm, kubectl, ArgoCD) позволяет автоматизировать создание green, тестирование и переключение. Argo Rollouts / Istio дают расширенные возможности (canary + blue-green, health checks, автоматический rollback).

Rollback и cleanup

Откат реализуется сменой селектора или бэкенда обратно. После стабилизации стоит удалить старую среду или оставить её ограниченное время как hot backup; не забывайте про ресурсы и стоимость.

Полезные практики

— Прогонять smoke-тесты и нагрузочное тестирование на green до переключения.
— Логировать версии в ответах (сбрасываемый заголовок X-App-Version) для верификации трафика.
— Хранить миграции и схемы отдельно и выполнять миграцию в безопасном режиме.