Docker Swarm
1Docker Swarm: кластер контейнеров2Services: масштабирование и rolling updates← вы здесь3Stack deploy: продакшн на Swarm
Урок 2~12 минут

Services: масштабирование и rolling updates

В Swarm приложения запускаются как services — декларативное описание желаемого состояния. Swarm сам следит чтобы нужное количество реплик всегда работало.

Service vs Container

bash
# Обычный контейнер (docker run)
docker run -d nginx    # запустил и забыл — упал, никто не перезапустит
 
# Swarm service
docker service create --name web --replicas 3 nginx
# Swarm следит: упала реплика → запустить новую на свободной ноде

Service — это желаемое состояние (desired state). Reconciliation loop постоянно сравнивает желаемое с фактическим и исправляет расхождения.

Создание сервиса

bash
docker service create \
  --name web \
  --replicas 3 \
  --publish published=80,target=80 \
  --env NODE_ENV=production \
  --limit-cpu 0.5 \
  --limit-memory 512M \
  nginx:alpine
bash
docker service ls              # список сервисов
docker service ps web          # задачи сервиса (где работают реплики)
docker service inspect web     # полные настройки
docker service logs web        # логи всех реплик

Масштабирование

bash
docker service scale web=5     # увеличить до 5 реплик
docker service scale web=1     # уменьшить до 1
 
# Несколько сервисов сразу
docker service scale web=5 api=3 worker=10

Swarm распределяет реплики по нодам равномерно. Если нода недоступна — реплики переезжают на другие.

Попробуй в симуляции

Rolling Update

Обновление без остановки трафика:

bash
docker service update \
  --image nginx:1.26 \
  --update-parallelism 1 \      # обновлять по 1 реплике
  --update-delay 10s \           # ждать 10 сек между репликами
  --update-failure-action rollback \  # откатить при ошибке
  web
Было:    [v1.25] [v1.25] [v1.25]
Шаг 1:   [v1.26] [v1.25] [v1.25]  ← обновили 1-ю, ждём 10 сек
Шаг 2:   [v1.26] [v1.26] [v1.25]  ← обновили 2-ю, ждём 10 сек
Шаг 3:   [v1.26] [v1.26] [v1.26]  ← готово
bash
docker service rollback web    # откатить к предыдущей версии

Placement constraints

Куда Swarm может планировать задачи:

bash
# Только на нодах с меткой env=prod
docker service create \
  --constraint 'node.labels.env==prod' \
  --name api myapp:latest
 
# Только менеджеры (осторожно — нагружает управляющие ноды)
--constraint 'node.role==manager'
 
# Только воркеры
--constraint 'node.role==worker'
 
# Только конкретная нода
--constraint 'node.hostname==worker-2'
bash
# Навесить метку на ноду
docker node update --label-add env=prod worker-1
docker node update --label-add role=db worker-2

Глобальный режим

Вместо N реплик — по одной на каждую ноду (мониторинг, логи):

bash
docker service create \
  --mode global \
  --name node-exporter \
  prom/node-exporter

Ingress и балансировка

Swarm встроенно балансирует нагрузку. Routing mesh: любой запрос на любую ноду кластера попадает к одной из реплик сервиса — даже если реплика не на этой ноде.

Запрос → worker-1:80 → Swarm routing mesh → реплика на worker-2:80
bash
# Публикация порта
--publish published=8080,target=3000        # routing mesh (все ноды)
--publish published=8080,target=3000,mode=host  # только ноды с репликой

В следующем уроке — Stack deploy: запуск всего приложения одной командой.

Service = желаемое состояние. Swarm сам следит чтобы нужное количество реплик всегда работало. Rolling update — обновляет по одной реплике без даунтайма.
⚖️
Scaling & Rolling Update2 реплик
worker-1
v1.0
worker-2
v1.0
worker-3
🎯
Миссия 1 из 4
Как масштабировать сервис до 5 реплик?