Привет, Хабр!
Сегодня поговорим о том, как избежать нервов во время деплоя с помощью стратегии Rolling Updates. Это один из самых лучших и безопасных способов обновления приложений. Если вы хотите минимизировать простои, исключить массовые ошибки и при этом уверенно управлять процессом обновления, Rolling Updates — это ваш выбор.
Rolling Updates — это стратегия деплоя, при которой обновление приложения происходит поэтапно, с минимальными перебоями в работе сервиса. Вместо остановки всех компонентов приложения и замены их новыми версиями, Rolling Updates обновляет небольшие группы (называемые батчами) экземпляров приложения, постепенно замещая старые версии новыми.
Подготовка
При планировании Rolling Updates, важно понимать, что речь идет о постепенном обновлении системы или приложения без полного отключения сервиса.
Для успешного Rolling Update необходима надежная инфраструктура и система мониторинга. В первую очередь, потребуется оркестратор, который может управлять параллельными процессами, как, например, Kubernetes.
Система мониторинга — это не просто опция, а основа. Необходимо отслеживать ключевые метрики.
Пример конфигурации для Kubernetes:
apiVersion: apps/v1 kind: Deployment metadata: name: my-app spec: replicas: 4 strategy: type: RollingUpdate rollingUpdate: maxUnavailable: 1 maxSurge: 2 template: spec: containers: - name: my-app-container image: my-app:latest
Задали стратегию RollingUpdate
с параметрами maxUnavailable: 1
(максимум одна недоступная реплика) и maxSurge: 2
(максимум две новые реплики за раз).
Опытные команды SRE тщательно планируют батчи, основываясь на требованиях системы и текущих нагрузках. Здесь очень важен Service Level Objective (SLO), который определяет допустимые уровни доступности и производительности.
Стандартная рекомендация — обновлять не более 25% системы за один раз. Однако все зависит от специфики инфраструктуры. Например, в микросервисных архитектурах это число может быть выше, если каждый сервис изолирован и не оказывает сильного влияния на другие части системы.
Перед началом обновления протестируйте батчи на изолированных серверах или тестовых окружениях. Таким образом, можно будет предсказать поведение реальной системы и скорректировать параметры обновления.
Правильно настроенный мониторинг — залог успешного Rolling Update. Несколько метрик:
-
Время простоя: метрика, измеряющая перерывы в работе сервиса. Она должна стремиться к нулю в идеальных условиях. Небольшие увеличения могут быть допустимы, если обновление требует замены целых нод.
-
Процент обновленных нод: метрика, отображающая текущий прогресс деплоя.
-
Производительность системы: мониторьте CPU, RAM, и дисковую нагрузку. Особенно важно отслеживать аномальные скачки во время обновлений.
Реализация и управление Rolling Updates в Kubernetes
Пример простой конфигурации Rolling Updates в Kubernetes:
apiVersion: apps/v1 kind: Deployment metadata: name: my-app spec: replicas: 4 template: metadata: labels: app: my-app spec: containers: - name: my-app-container image: my-app:v1 selector: matchLabels: app: my-app strategy: type: RollingUpdate rollingUpdate: maxUnavailable: 1 maxSurge: 1
Rolling Updates происходит за счет параметров maxUnavailable
и maxSurge
. Первый отвечает за количество подов, которые могут быть недоступны во время обновления, а второй – за количество новых подов, которые могут быть созданы до того, как старые будут удалены.
Для того чтобы запустить обновление, достаточно изменить версию контейнера с помощью следующей команды:
kubectl set image deployment/my-app my-app-container=my-app:v2
Kubernetes начнет обновление в реальном времени, поэтапно заменяя поды старой версии новыми.
Следить за процессом можно командой:
kubectl rollout status deployment/my-app
Если что-то пошло не так, можно быстро откатить обновление:
kubectl rollout undo deployment/my-app
Kubernetes поддерживает механизмы для проверки готовности контейнеров через readiness probes и их живучести через liveness probes. Эти проверки позволяют убедиться, что обновленные контейнеры готовы к приему трафика, а приложение стабильно работает. Пример конфигурации проверок:
apiVersion: apps/v1 kind: Deployment metadata: name: my-health-app spec: replicas: 4 template: metadata: labels: app: my-health-app spec: containers: - name: my-health-container image: my-health-app:v1 readinessProbe: httpGet: path: /healthz port: 8080 initialDelaySeconds: 5 periodSeconds: 10 livenessProbe: httpGet: path: /healthz port: 8080 initialDelaySeconds: 15 periodSeconds: 20
Используем readinessProbe
для проверки готовности контейнера, и livenessProbe
для контроля его состояния. Таким образом, только поды, которые успешно прошли проверку, остаются активными, что повышает надежность и снижает риск сбоев.
Также важно не забывать о том, что более сложные системы требуют гибкости. Kubernetes позволяет использовать процентные значения в параметрах maxUnavailable
и maxSurge
. Например:
apiVersion: apps/v1 kind: Deployment metadata: name: my-advanced-app spec: replicas: 10 strategy: type: RollingUpdate rollingUpdate: maxUnavailable: "20%" # Динамическое значение для большого числа подов maxSurge: "50%" # Ускорение деплоя за счет увеличения количества новых подов template: metadata: labels: app: my-advanced-app spec: containers: - name: my-advanced-app-container image: my-advanced-app:v2
В данном случае используются процентные значения, что позволяет динамически управлять процессом Rolling Updates для крупных приложений с большим количеством реплик.
Во время Rolling Updates могут возникать непредвиденные ситуации, например, контейнеры могут не пройти проверку готовности или возникнут проблемы с производительностью на отдельных подах. В таких случаях нужно откатить обновления:
kubectl rollout undo deployment/my-app
Этот откат возвращает систему к предыдущему стабильному состоянию.
Rolling Updates можно интегрировать с CI/CD инструментами, чтобы автоматизировать и ускорить процесс деплоя.
Пример конфигурации пайплайна с Jenkins:
pipeline { agent any stages { stage('Build') { steps { sh 'docker build -t my-app:v2 .' } } stage('Deploy') { steps { sh 'kubectl set image deployment/my-app my-app-container=my-app:v2' } } stage('Monitor') { steps { script { timeout(time: 10, unit: 'MINUTES') { def status = sh(script: 'kubectl rollout status deployment/my-app', returnStatus: true) if (status != 0) { error "Rolling Update failed!" } } } } } } }
Простой Jenkins пайплайн, который выполняет сборку Docker-образа, деплой на Kubernetes и мониторинг статуса обновления.
Лучшие практики по управлению надежностью, доступностью и эффективностью сервисов можно изучить на онлайн-курсе «SRE практики и инструменты».
ссылка на оригинал статьи https://habr.com/ru/articles/842190/
Добавить комментарий