Jinja в SLS

Тема дорожной карты · SaltStack

SLS-файл — это не YAML, а шаблон, который становится YAML после рендеринга. Понимание этого двухступенчатого конвейера — Jinja сначала, YAML потом — главное, что отличает уверенную работу с состояниями от борьбы с загадочными ошибками парсера. Jinja в SLS позволяет одним файлом описывать поведение для разных ОС, генерировать десятки однотипных состояний циклом и подтягивать параметры из pillar, не размножая почти одинаковые файлы. При этом важно помнить: Jinja оперирует текстом. Она не знает про YAML-структуру, не проверяет отступы и честно склеивает то, что вы ей дали, — а валидность результата проверит уже YAML-парсер на следующем шаге.

Как это работает

Первая строка SLS может задавать рендерер явно шебангом — #!jinja|yaml — но обычно это не нужно: такая связка и есть значение по умолчанию. Миньон получает файл, выполняет все Jinja-конструкции и передаёт получившийся текст YAML-парсеру. Типовой пример — выбор имени пакета по grains:

{% if grains['os_family'] == 'Debian' %}
{% set pkg = 'apache2' %}
{% else %}
{% set pkg = 'httpd' %}
{% endif %}

веб-сервер:
  pkg.installed:
    - name: {{ pkg }}

Цикл генерирует несколько состояний из одного блока — каждая итерация должна давать уникальный ID:

{% for user in salt['pillar.get']('app_users', []) %}
{{ user }}_account:
  user.present:
    - name: {{ user }}
{% endfor %}

Диагностика двухступенчатая: salt-call --local slsutil.renderer /srv/salt/app/init.sls показывает текст после Jinja, salt 'web*' state.show_sls app — структуру после YAML, state.apply app test=True — что реально изменится.

Когда применять

Jinja в SLS оправдана, когда без неё пришлось бы копировать файлы: одна формула на несколько дистрибутивов, состояния из списков в pillar (пользователи, виртуальные хосты, cron-задачи), включение и выключение блоков по окружению. Хорошая практика — держать логику наверху файла: собрать все {% set %} и вычисления в первых строках, а ниже оставить почти чистый YAML с подстановками {{ }}. Так файл остаётся читаемым, а диффы — осмысленными. Когда условной логики становится больше, чем самих состояний, пора выносить данные в map.jinja или разбивать формулу на отдельные SLS-файлы с включением через top.sls.

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

Классика — отступы внутри циклов и условий: Jinja-теги стоят с отступом «для красоты», лишние пробелы попадают в результат, и YAML падает. Держите {% %}-теги в начале строки или управляйте пробелами через {%- и -%}. Вторая ошибка — неуникальные ID состояний в цикле: две итерации дают одинаковый ключ, и YAML молча перезапишет первый блок вторым либо Salt откажется применять дубль. Третья — правка SLS без прогона state.show_sls: ошибка рендеринга одного файла валит весь highstate на миньоне. И не прячьте в Jinja обращения к внешним системам — рендеринг должен быть быстрым и детерминированным.

Связанные понятия

Полезные ресурсы

Проверить знания (2)

Загрузка вопросов…