Errors
Kubernetes

Kubernetes: How can we create service dependencies using kubernetes

Ты развернул в кластере веб-приложение и базу данных. Прописал манифесты, накатил их и — бац — ваше приложение сразу полетело в цикл перезапусков, потому что не

Ты развернул в кластере веб-приложение и базу данных. Прописал манифесты, накатил их и — бац — ваше приложение сразу полетело в цикл перезапусков, потому что не нашло базу. Суровые будни: кубер не знает о ваших логических зависимостях между подами. Он создаёт всё примерно одновременно, и кто успел, тот и стартанул.

Вам нужно, чтобы MySQL точно была готова к коннекту до старта веб-сервиса. Наивная надежда на простой порядок в kubectl apply не сработает — поды могут создаваться в разной последовательности, да и readiness самого пода базы нужно дождаться.

Ждём готовности, а не просто создания

Прямой команды «запусти это после того» в Kubernetes нет. Но есть паттерны. Базовый — использовать readinessProbe для сервиса базы данных и initContainers для веб-приложения.

В под веб-приложения добавляем initContainer, который будет терзать проверкой доступность MySQL. Пока база не откликнется, основной контейнер не стартанёт.

apiVersion: v1
kind: Pod
metadata:
  name: web-app-pod
spec:
  initContainers:
  - name: wait-for-db
    image: appropriate/curl
    command: ['sh', '-c', 'until curl http://mysql-service:3306; do echo waiting; sleep 2; done']
  containers:
  - name: web-app
    image: your-web-app:latest
    env:
    - name: DB_HOST
      value: "mysql-service"

Это грубый пример. В реальности для проверки MySQL лучше использовать специализированный клиент (mysqladmin ping) или скрипт на Python.

Уровень сервиса: зависеть от Service, а не от Pod

Ваш веб-сервис зависит от другого сервиса (MySQL), а не от конкретных под. Убедитесь, что Service для базы создан и селектит правильные поды. InitContainer будет обращаться по DNS-имени этого сервиса (mysql-service). Кубер начнёт резолвить имя только когда сервис реально существует.

Порядок применения манифестов всё же имеет значение: сначала сервис и deployment базы, потом — всё для приложения. Можно склеить манифесты в один файл — kubectl apply -f all-in-one.yaml — ресурсы создаются в том порядке, в котором описаны.

Если всё совсем сложно — Helm и зависимости

Когда сервисов много, управлять зависимостями вручную становится тем ещё танцем с бубном. Здесь в игру входят пакетные менеджеры, например Helm.

В Helm вы можете явно указать в Chart.yaml зависимости (dependencies) между чартами. Установщик (Tiller в Helm 2 или Helm 3) будет учитывать порядок. Это чисто оркестрационный уровень развёртывания, а не runtime-ожидание внутри кластера, но часто этого достаточно.

Итог

Kubernetes не запускает ресурсы по вашим логическим зависимостям. Ваша задача — описать условия готовности.

Порядок действий: накатываете манифесты БД и её Service, добавляете в под приложения initContainer с проверкой доступности этого сервиса, настраиваете readinessProbe для самих под БД. Или упаковываете всё в Helm с явными dependency. В 90% случаев initContainer — ваш выход.