Stateful-приложения в Swarm

TL;DR: Stateful в Swarm: constraint на конкретную ноду + named volume + 1 реплика. Для серьёзных баз — managed DB (RDS) лучше, чем Swarm.

Stateful приложения (БД) сложнее stateless, так как данные лежат на диске конкретной ноды.

Стратегия 1: Привязка к ноде (Pinning)

Жестко привяжите сервис к конкретной ноде, где лежат данные.

services:
  db:
    image: postgres
    volumes:
      - /opt/data/pg:/var/lib/postgresql/data
    deploy:
      replicas: 1
      placement:
        constraints: [node.hostname == node-1]
  • Плюс: Простота, максимальная скорость диска (I/O).
  • Минус: Если node-1 сгорит, сервис не переедет, пока вы не восстановите данные на другой ноде.

Стратегия 2: Сетевые хранилища (NFS / Cloud Volumes)

Используйте драйверы томов, которые монтируют сетевые диски.

volumes:
  db-data:
    driver: local
    driver_opts:
      type: nfs
      o: addr=192.168.1.100,rw
      device: ":/path/to/nfs/share"
  • Плюс: Сервис может переехать на любую ноду, данные “едут” за ним.
  • Минус: Задержки сети, сложность настройки NFS/GlusterFS/Ceph.

Типичные ошибки

ОшибкаСимптомРешение
БД с replicas: 2Два инстанса пишут в разные volumes — split brainreplicas: 1 + constraint на одну ноду
Volume на другой нодеБД рестартовала на воркере без данныхConstraint привязывает к ноде с volume
Нет бэкапа volumeНода упала — данные потеряныРегулярный pg_dump + внешнее хранилище
global mode для БДБД на каждой нодеreplicated с 1 репликой для stateful