← Kubernetes: Kustomize и Helm
5 мин · просто · Урок 1 из 9

Kustomize: манифесты одной группой

Как kustomization.yaml собирает разрозненные YAML в одну единицу и почему Kustomize не шаблонизатор.

Одно приложение в Kubernetes редко описывается одним файлом. Deployment, Service, ConfigMap, иногда Ingress и ServiceAccount. Применять их по одному через kubectl apply -f быстро надоедает: легко забыть файл, легко применить не то, что лежит в git.

Kustomize решает эту задачу без шаблонов. Это инструмент, который читает описание группы манифестов из файла kustomization.yaml, собирает из перечисленных в нём YAML один итоговый поток объектов и по дороге может наложить на них правки. Отдельно ставить его не нужно: Kustomize встроен в kubectl начиная с версии 1.14.

kustomization.yaml

Минимальный файл содержит только список ресурсов:

# kustomization.yaml
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
  - deployment.yaml
  - service.yaml

resources перечисляет пути относительно самого kustomization.yaml. Туда кладут файлы, папки с собственным kustomization.yaml внутри и даже URL на удалённый репозиторий.

Применяют такую папку флагом -k вместо -f:

kubectl apply -k .

kubectl найдёт kustomization.yaml, соберёт группу и отправит объекты в кластер. Удаляется группа тем же способом:

kubectl delete -k .

Имя файла проверяется буквально: kustomization.yaml, kustomization.yml или Kustomization. Файл kustomize.yaml kubectl не увидит и скажет, что конфигурации в папке нет.

Посмотреть результат до применения

kubectl kustomize делает ровно то же самое, но печатает итоговый YAML в stdout, ничего не отправляя в API-сервер:

kubectl kustomize .

На выходе получится многодокументный YAML: объекты разделены строкой ---. Это самый быстрый способ понять, что реально уедет в кластер. Тот же вывод удобно скармливать дальше по конвейеру:

kubectl kustomize . | kubectl apply --dry-run=server -f -

Так kubectl проверит объекты на стороне API-сервера, включая валидацию схемы и admission-контроллеры, но не запишет их.

Структура папки

Обычная раскладка выглядит так:

app/
  kustomization.yaml
  deployment.yaml
  service.yaml
  configmap.yaml

Сами манифесты остаются валидными YAML. Их можно применить и напрямую через kubectl apply -f deployment.yaml, Kustomize ничего в них не портит и не добавляет своего синтаксиса. Это отличает подход от шаблонизаторов: там файл с {{ }} внутри перестаёт быть валидным манифестом и без рендера бесполезен.

Это не шаблонизатор

Helm подставляет значения в шаблоны и на выходе получает манифест. Kustomize идёт с другой стороны: у него на входе уже готовый валидный манифест, а изменения описываются отдельно и накладываются поверх. Никаких переменных, циклов и условий в манифестах нет и не будет, это осознанное ограничение проекта.

Отсюда следует практический вывод. Kustomize хорош, когда у вас один набор манифестов и несколько его вариаций (dev, stage, prod). Он плохо подходит, когда нужно раздавать конфигурируемый пакет наружу, чужим людям с непредсказуемыми требованиями. Там уместнее Helm.

Что обычно ломается

Флаг -k принимает папку, а не файл. kubectl apply -k kustomization.yaml завершится ошибкой, правильно kubectl apply -k . или kubectl apply -k ./app.

Пути в resources считаются от расположения kustomization.yaml, а не от текущего каталога терминала. Если запускаете команду из корня репозитория, а конфигурация лежит в app/, пути внутри всё равно остаются относительно app/.

Версия Kustomize внутри kubectl отстаёт от отдельной утилиты kustomize. Свежие поля из документации проекта могут не работать в вашем kubectl. Проверить версию можно через kubectl version, а при расхождении поставить отдельный бинарник kustomize и рендерить им.

Домашка

Теорию закрепляет задание на своём кластере: 1 шаг с проверкой. Кластер поднимается по треку Kubernetes локально, задания лежат в репозитории k8s-practice.

./run.sh start k8s-kustomize-base     # развернуть стартовое состояние
./run.sh verify k8s-kustomize-base    # проверить текущий шаг

Коротко

Прошли материал до конца? Отметьте урок пройденным.