Недавно вышел Helm 4, и это отличный повод снова сравнить его с нашей альтернативой — Nelm. В статье смотрим на новые возможности обоих проектов, детально разбираем их отличия и объясняем, что ждёт Nelm дальше.

Основные изменения в Helm 4

В Helm 4 только одно значимое для пользователя изменение, решающее проблемы некорректного обновления ресурсов, — Server-Side Apply вместо 3-Way Merge. Остальные фичи новой версии — это по большей части избавление от техдолга.

Несмотря на то, что внедрение SSA само по себе достойно отдельного релиза, от Helm 4 ждали большего. Из самых популярных запросов: альтернатива Go-шаблонам и доработка выката Custom Resource Definition. Но ни того, ни другого в планах по-прежнему нет.

P. S. Полный список изменений можно найти в нашем обзоре Helm 4.

Будущее Helm

Темп разработки Helm ускорился к новому релизу, но, скорее всего, привычно замедлится после него. Системные проблемы остались: долгие согласования через Helm Improvement Proposals (HIP), высокие требования к обратной совместимости, значительный техдолг в кодовой базе и недостаток контрибьюторов.

Опираясь на текущий опыт, я думаю, что в ближайшие годы в Helm 4 стоит ожидать только небольшие фичи и багфиксы, как это было ранее в Helm 3. Если какие-то крупные изменения и произойдут, то, скорее всего, уже в следующем мажорном релизе Helm.

Что такое Nelm

Nelm — это современная альтернатива Helm 4 с фокусом на обратной совместимости с Helm-чартами и Helm-релизами. Nelm делает всё то же, что и Helm, но лучше.

Nelm появился во «Фланте» как ответ на низкий темп разработки, сложность донесения изменений и игнорирование застарелых проблем в Helm. «Под капотом» используется часть кодовой базы Helm, но самые проблемные части (особенно развёртывание) переписаны с нуля.

Чем Nelm отличается от Helm 4

С новым релизом Helm догнал Nelm только в поддержке Server-Side Apply. Но и Nelm не стоял на месте: например, недавно была добавлена настройка жизненного цикла ресурсов — аннотации werf.io/delete-policy, werf.io/ownership, werf.io/deploy-on.

Давайте рассмотрим ключевые отличия Nelm от Helm 4.

Полноценный выкат CRD

Helm рекомендует класть CRD в директорию crds чарта. Но ресурсы из этой директории не только не умеют обновляться, но и выкатываются только при самой первой установке релиза. При последующих «helm upgrade» директория crds даже не читается.

Некоторые пользователи прибегают к тому, что выкатывают CRD как обычные ресурсы, кладя их в директорию templates, но тут возникают проблемы с порядком выката и превышением размера релизного Secret, поскольку манифесты у CRD объёмные.

Стремясь обойти перечисленные проблемы, некоторые опенсорсные чарты даже организуют отдельный сабчарт для развёртывания CRD.

В Nelm достаточно просто положить ваши CRD в директорию crds. Выкат из неё реализован полноценно: CRD умеют и обновляться, и выкатываться при последующих upgrade’ах релиза.

Задание порядка выката

В Helm для задания порядка выката обычно используют Helm-хуки. Это неплохо работает для простых Job, которые надо запустить до или после выката.

Но что, если для работы Job нужен Deployment? Или, может, Job надо запустить в середине релиза? Даже для таких тривиальных ситуаций нет нормальных решений.

Nelm перед выкатом создаёт граф операций над ресурсами в кластере, и в этом графе определён порядок их выката:

Вместе с этим даётся простой, но очень мощный способ задания порядка выката: аннотация werf.io/deploy-dependency, которая создаёт зависимость между операциями в графе, то есть определяет их порядок. Например, вот такой код:

kind: Deployment
metadata:
  name: backend
  annotations:
    werf.io/deploy-dependency-db: state=ready,kind=StatefulSet,name=postgres

…означает, что операция создания/обновления Deployment’а backend будет выполняться только после создания/обновления и готовности StatefulSet’а postgres. Граф станет выглядеть так:

werf.io/deploy-dependency работает и для обычных ресурсов, и для хуков. Позже мы добавим возможность указания зависимости от целого чарта.

Как альтернатива, в Nelm есть ещё и аннотация werf.io/weight. Работает аналогично helm.sh/hook-weight, но не только для хуков, а и для обычных ресурсов.

Также аннотация external-dependency.werf.io/resource позволяет указать зависимость от ресурсов Kubernetes вне Helm-релиза, например от Secret, создаваемых оператором.

Конечно, Helm-хуки и их веса тоже поддерживаются.

Жизненный цикл ресурсов

В Helm можно запретить удаление ресурса с helm.sh/resource-policy: keep и настроить политики удаления хуков с helm.sh/hook-delete-policy. Но что делать, если надо деплоить иммутабельную Job в середине релиза? А если хочется подчищать обычный ресурс после его выката? Или катить один и тот же ресурс разными релизами?

Недавно мы добавили в Nelm целый ряд новых возможностей для управления жизненным циклом ресурсов.

Аннотация werf.io/delete-policy, напоминающая helm.sh/hook-delete-policy, позволяет пересоздавать ресурс вместо обновления (before-creation), пересоздавать его, только если получили ошибку «field is immutable» (before-creation-if-immutable), или удалять ресурс при удачном (succeeded) или неудачном (failed) выкате. Эта аннотация, как и все другие, работает и для хуков, и для обычных ресурсов.

Аннотация werf.io/ownership позволяет добиться хук-подобного поведения для обычных ресурсов, а именно: не применять и не проверять релизные аннотации на ресурсе, не удалять ресурс, если он пропал из чарта или если удаляется релиз.

Ещё одна аннотация — werf.io/deploy-on — даёт возможность отрендерить ресурс только при install, upgrade, rollback или uninstall релиза, как уже можно делать с хуками. Но использование этой аннотации не делает из ресурса хук.

С этими аннотациями даже можно получить поведение Helm-хука без объявления хука. К примеру, этот хук:

metadata:
  annotations:
    helm.sh/hook: pre-install
    helm.sh/hook-delete-policy: before-hook-creation

…аналогичен этому не-хуку:

metadata:
  annotations:
    werf.io/deploy-on: install
    werf.io/delete-policy: before-creation
    werf.io/ownership: anyone

В целом мы рекомендуем больше не использовать Helm-хуки при написании чартов. При этом чарты становятся проще, поведение ресурсов настраивается гибче, а выкат ускоряется, поскольку хуки больше не катятся в отдельной фазе. Однако использование хуков может иметь смысл, если хочется сохранить совместимость чарта с обычным Helm.

Продвинутое отслеживание ресурсов

В Helm 3 было базовое ожидание готовности ресурсов для некоторых стандартных Kubernetes-ресурсов. Helm 4 заменил эту подсистему на kstatus, что сделало ожидание готовности немного точнее, хотя кардинально ничего не поменялось.

В Nelm есть своя продвинутая система отслеживания ресурсов. В сравнении с Helm 4 она:

  • точнее, чем kstatus, детектирует готовность ресурса;

  • способна отслеживать не только готовность, но и просто присутствие или отсутствие ресурса, а также обнаруживать ошибки, вроде падающих проб, и реагировать на них;

  • позволяет отслеживать готовность популярных кастомных ресурсов по написанным вручную наборам правил;

  • определяет готовность остальных кастомных ресурсов эвристически, что работает для большинства ресурсов, причём без ложных срабатываний;

  • отображает во время выката в терминале информацию о текущем статусе и ошибках ресурсов, а также их логи и ивенты.

Отслеживание не требует никакой конфигурации, но может быть настроено или выключено флагами командной строки и аннотациями.

Шифрование values.yaml и других файлов

В Helm нет поддержки работы с зашифрованными файлами в чарте, но есть плагин helm-secrets.

В Nelm «из коробки» есть поддержка работы с зашифрованными values-файлами, а также с произвольными зашифрованными файлами в директории secrets чарта. Секреты в Nelm гораздо проще в работе, чем использование плагина helm-secrets.

Сгенерируйте секретный ключ и создайте файл с зашифрованными values:

NELM_SECRET_KEY=$(nelm chart secret key create)
nelm chart secret values-file edit secret-values.yaml

…после чего используйте зашифрованные values так же, как и обычные:

# templates/secret.yaml
kind: Secret
stringData:
  mySecret: {{ .Values.mySecretValue }}
nelm release install -n foo -r bar

Также есть возможность шифровать произвольные файлы в директории secret чарта.

Планирование релизов

В Nelm нативно реализован аналог плагина helm diff для Helm. Команда nelm release plan install точно отобразит, что произойдёт с ресурсами в кластере при следующем выкате:

Результат крайне точен и основывается на анализе плана операций над ресурсами, который строится перед каждым выкатом. Кроме того, в отличие от helm diff, план строится на основании обновления ресурсов через SSA, а не через 3WM.

Позже мы доделаем построение и сохранение плана одной командой (nelm release plan install --save-plan) и передачу его в другую команду (nelm release install --use-plan). Таким образом можно будет утвердить план и быть уверенным, что Nelm не сделает ничего, что вы не запланировали. С Helm и helm diff подобное реализовать нельзя.

Чего не хватает в Nelm

В Nelm не поддерживаются Helm 3 CLI-плагины. Они завязаны на CLI Helm: на формат команд, опций и даже на то, как выводятся логи. Обеспечить такую совместимость, переписав половину кодовой базы Helm, — слишком дорогая задача. Взамен мы реализуем функциональность самых востребованных плагинов в самом Nelm (например, плагины helm diff, helm secrets).

В Nelm нет поддержки post-renderer’ов. Вместо этого мы добавим альтернативу Go-шаблонам и патчинг ресурсов «из коробки», без необходимости ставить плагины и что-либо конфигурировать. Почему такой подход нам кажется удачнее, можно прочесть в соответствующих issues: #54, #115.

Nelm пока нельзя использовать с Argo CD и Flux, но мы решим это Nelm-оператором, кастомные ресурсы которого можно будет деплоить с Argo CD, Flux или чем угодно другим.

Helmwave, Helmfile и подобные не работают с Nelm. Вероятно, решим реализацией Nelmfile, сразу доступной из Nelm CLI.

Что будет с Nelm после релиза Helm 4.0

Nelm является движком развёртывания werf, которую на сегодняшний день используют в 20 тысячах проектов. Кроме того, Nelm прямо сейчас внедряется и в другие продукты, например в Deckhouse Kubernetes Platform. Так что Nelm — один из наших ключевых продуктов, прямо или опосредованно используемый большинством клиентов, а значит, забрасывать его мы точно не собираемся.

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

За последний год мы стабилизировали Nelm v1, провели крупный рефакторинг всей кодовой базы, занесли немало новых фич, а в ближайший месяц ожидаем присоединения к команде Nelm ещё двух фултайм-разработчиков.

Ближайшие планы

В течение полугода планируются релиз Nelm v2, миграция на кодовую базу Helm 4 и релиз Nelm-оператора для интеграции с Argo CD и Flux.

В планах на следующий год — альтернатива Go-шаблонам, патчинг чартов и скачивание чартов напрямую из Git.

Мы продолжим активно развивать Nelm — так же, как уже 9 лет активно развиваем и поддерживаем werf. Узнать больше о Nelm и попробовать его можно, зайдя в наш GitHub-репозиторий.

Читайте также в нашем блоге

Комментарии (0)