0 --- # Секция мета-информации
...
1 project: string ! # Уникальное имя проекта приложения. Подробнее здесь
2 configVersion: string ! # Версия конфигурации. На данный момент поддерживается единственная версия 1
3 deploy: # Настройка выката. Подробнее здесь
...
8 cleanup: # Настройка удаления неактульных образов. Подробнее здесь
...
21 --- # Cекция Dockerfile image: может использоваться произвольное количество секций
...
22 image: string || [ string, ... ] || ~ ! # Одно или несколько уникальных имён для образа. Подробнее здесь
23 dockerfile: string # Путь к Dockerfile относительно папки проекта
24 context: string # Путь к контексту внутри папки проекта (значение по умолчанию .)
25 target: string # Конкретная стадия Dockerfile (по умолчанию — последняя, подобно docker build --target)
26 args: { name string: value string, ... } # Переменные окружения на время сборки (подобно docker build --build-arg)
27 addHost: [ string, ... ] # Установить связь host-to-IP (host:ip) (подобно docker build --add-host)
28 network: string # Сетевой режим для инструкций RUN во время сборки (подобно docker build --network)
29 ssh: string # Сокет агента SSH или ключи для сборки определённых слоёв (только если используется BuildKit) (подобно docker build --ssh)
30 --- # Cекция Stapel image/artifact: может использоваться произвольное количество секций
...
31 image: string || [ string, ... ] || ~ ! # Одно или несколько уникальных имён для образа. Подробнее здесь
32 artifact: string # Уникальное имя артефакта. Подробнее здесь
33 from: string # Имя и тег базового образа. Подробнее здесь
34 fromLatest: bool # Использование актуального базового образа (без кеширования). Подробнее здесь
35 herebyIAdmitThatFromLatestMightBreakReproducibility: bool # Подтверждение понимания проблемы использования директивы fromLatest. Подробнее здесь
36 fromImage: string # Использование образа из werf.yaml в качестве базового. Подробнее здесь
37 fromArtifact: string # Использование артефакта из werf.yaml в качестве базового. Подробнее здесь
38 fromCacheVersion: string # Версия кеша. Подробнее здесь
39 git: # Набор директив для добавления исходных файлов из git-репозиториев (как репозитория проекта, так и любого другого). Подробнее здесь
...
40 url: string # Адрес git-репозитория. Подробнее здесь
41   branch: string # Имя ветки. Подробнее здесь
42   herebyIAdmitThatBranchMightBreakReproducibility: bool # Подтверждение понимания проблемы использования директивы branch. Подробнее здесь
43   commit: string # Коммит
44   tag: string # Имя тега
45   add: string # Исходный путь в репозитории. Подробнее здесь
46   to: string # Путь назначения в образе. Подробнее здесь
47   owner: string # Имя или UID владельца. Подробнее здесь
48   group: string # Имя или GID группы. Подробнее здесь
49   includePaths: [ string, ... ] # Маски для добавления. Подробнее здесь
50   excludePaths: [ string, ... ] # Маски для исключения. Подробнее здесь
51   stageDependencies: # Настройка перевыполнения сборочных инструкций при изменениях определённых файлов в репозитории. Подробнее здесь
52     install: [ string, ... ] # Маски для стадии install
53     beforeSetup: [ string, ... ] # Маски для стадии beforeSetup
54     setup: [ string, ... ] # Маски для стадии setup
55 shell: # Shell сборочные инструкции. Подробнее здесь
...
56   beforeInstall: [ string, ... ] # Команды для стадии beforeInstall. Подробнее здесь
57   install: [ string, ... ] # Команды для стадии install. Подробнее здесь
58   beforeSetup: [ string, ... ] # Команды для стадии beforeSetup. Подробнее здесь
59   setup: [ string, ... ] # Команды для стадии setup. Подробнее здесь
60   cacheVersion: string # Общая версия кеша. Подробнее здесь
61   beforeInstallCacheVersion: string # Версия кеша для стадии beforeInstall. Подробнее здесь
62   installCacheVersion: string # Версия кеша для стадии install. Подробнее здесь
63   beforeSetupCacheVersion: string # Версия кеша для стадии beforeSetup. Подробнее здесь
64   setupCacheVersion: string # Версия кеша для стадии setup. Подробнее здесь
65 ansible: # Ansible сборочные инструкции. Подробнее здесь
...
66   beforeInstall: [ task, ... ] # Задания для стадии beforeInstall. Подробнее здесь
67   install: [ task, ... ] # Задания для стадии install. Подробнее здесь
68   beforeSetup: [ task, ... ] # Задания для стадии beforeSetup. Подробнее здесь
69   setup: [ task, ... ] # Задания для стадии setup. Подробнее здесь
70   cacheVersion: string # Общая версия кеша. Подробнее здесь
71   beforeInstallCacheVersion: string # Версия кеша для стадии beforeInstall. Подробнее здесь
72   installCacheVersion: string # Версия кеша для стадии install. Подробнее здесь
73   beforeSetupCacheVersion: string # Версия кеша для стадии beforeSetup. Подробнее здесь
74   setupCacheVersion: string # Версия кеша для стадии setup. Подробнее здесь
75 docker: # Набор директив для изменения манифеста образа. Подробнее здесь
...
76   USER: string # Имя пользователя (или UID) и опционально пользовательская группа (или GID). Подробнее здесь
77   WORKDIR: string # Рабочая директория. Подробнее здесь
78   VOLUME: [ string, ... ] # Точки монтирования. Подробнее здесь
79   ENV: { name string: value string, ... } # Переменные окружения. Подробнее здесь
80   LABEL: { name string: value string, ... } # Метаданные. Подробнее здесь
81   EXPOSE: [ string, ... ] # Описание сетевых портов, которые будут прослушиваться в запущенном контейнере. Подробнее здесь
82   ENTRYPOINT: string # Команда по умолчанию, которая будет выполнена при запуске контейнера. Как сборщик Stapel работает с CMD и ENTRYPOINT. Подробнее здесь
83   CMD: string # Аргументы по умолчанию для ENTRYPOINT. Как сборщик Stapel работает с CMD и ENTRYPOINT. Подробнее здесь
84   HEALTHCHECK: string # Инструкции, которые Docker может использовать для проверки работоспособности запущенного контейнера. Подробнее здесь
85 mount: # Точки монтирования. Подробнее здесь
...
86 from: tmp_dir || build_dir # Имя служебной директории
87   fromPath: string # Абсолютный или относительный путь до произвольного файла на хосте
88   to: string # Абсолютный путь в образе
89 import: # Импортирование из образов и артефактов. Подробнее здесь
...
90 artifact: string # Имя артефакта, из которого выполнять копирование файлов
91   image: string # Имя образа, из которого выполнять копирование файлов
92   stage: string # Имя стадии, из которой выполнять копирование файлов (по умолчанию последняя)
93   before: string # Выбор стадии импортирования файлов при сборке, до стадии install или setup
94   after: string # Выбор стадии импортирования файлов при сборке, после стадии install или setup
95   add: string # Абсолютный путь до файла или директории в выбранном образе/артефакте
96   to: string # Абсолютный путь в конечном образе. По умолчанию соответствует пути add
97   owner: string # Имя или UID владельца
98   group: string # Имя или GID группы
99   includePaths: [ string, ... ] # Маски для добавления
100   excludePaths: [ string, ... ] # Маски для исключения

Имя проекта

Имя проекта должно быть уникальным в пределах группы проектов, собираемых на одном сборочном узле и развертываемых на один и тот же кластер Kubernetes (например, уникальным в пределах всех групп одного GitLab).

Имя проекта должно быть не более 50 символов, содержать только строчные буквы латинского алфавита, цифры и знак дефиса.

Последствия смены имени проекта

ВНИМАНИЕ. Никогда не меняйте имя проекта в процессе работы, если вы не осознаете всех последствий.

Смена имени проекта приводит к следующим проблемам:

  1. Инвалидация сборочного кэша. Все образы должны быть собраны повторно, а старые удалены из локального хранилища или Docker registry вручную.
  2. Создание совершенно нового Helm-релиза. Смена имени проекта и повторное развертывание приложения приведет к созданию еще одного экземпляра, если вы уже развернули ваше приложение в кластере Kubernetes.

werf не поддерживает изменение имени проекта и все возникающие проблемы должны быть разрешены вручную.

Выкат

Имя релиза

werf позволяет определять пользовательский шаблон имени Helm-релиза, который используется во время процесса деплоя для генерации имени релиза:

project: PROJECT_NAME
configVersion: 1
deploy:
  helmRelease: TEMPLATE
  helmReleaseSlug: false

В качестве значения для deploy.helmRelease указывается Go-шаблон с разделителями [[ и ]]. Поддерживаются функции project и env. Значение шаблона имени релиза по умолчанию: [[ project ]]-[[ env ]].

Можно комбинировать переменные доступные в Go-шаблоне с переменными окружения следующим образом:

deploy:
  helmRelease: >-
    [[ project ]]-{{ env "HELM_RELEASE_EXTRA" }}-[[ env ]]

deploy.helmReleaseSlug включает или отключает слагификацию имени Helm-релиза (включен по умолчанию).

Namespace в Kubernetes

werf позволяет определять пользовательский шаблон namespace в Kubernetes, который будет использоваться во время процесса деплоя для генерации имени namespace.

Пользовательский шаблон namespace Kubernetes определяется в секции мета-информации в файле werf.yaml:

project: PROJECT_NAME
configVersion: 1
deploy:
  namespace: TEMPLATE
  namespaceSlug: true|false

В качестве значения для deploy.namespace указывается Go-шаблон с разделителями [[ и ]]. Поддерживаются функции project и env. Значение шаблона имени namespace по умолчанию: [[ project ]]-[[ env ]].

deploy.namespaceSlug включает или отключает слагификацию имени namespace Kubernetes. Включен по умолчанию.

Очистка

Конфигурация политик очистки

Конфигурация очистки состоит из набора политик, keepPolicies, по которым выполняется выборка значимых образов на основе истории git. Таким образом, в результате очистки неудовлетворяющие политикам образы удаляются.

Каждая политика состоит из двух частей:

  • references определяет множество references, git-тегов или git-веток, которые будут использоваться при сканировании.
  • imagesPerReference определяет лимит искомых образов для каждого reference из множества.

Любая политика должна быть связана с множеством git-тегов (tag: string || /REGEXP/) либо git-веток (branch: string || /REGEXP/). Можно указать определённое имя reference или задать специфичную группу, используя синтаксис регулярных выражений golang.

tag: v1.1.1
tag: /^v.*$/
branch: master
branch: /^(master|production)$/

При сканировании описанный набор git-веток будет искаться среди origin remote references, но при написании конфигурации префикс origin/ в названии веток опускается

Заданное множество references можно лимитировать, основываясь на времени создания git-тега или активности в git-ветке. Группа параметров limit позволяет писать гибкие и эффективные политики под различные workflow.

- references:
    branch: /^features\/.*/
    limit:
      last: 10
      in: 168h
      operator: And

В примере описывается выборка из не более чем 10 последних веток с префиксом features/ в имени, в которых была какая-либо активность за последнюю неделю.

  • Параметр last: int позволяет выбирать последние n references из определённого в branch/tag множества.
  • Параметр in: duration string (синтаксис доступен в документации) позволяет выбирать git-теги, которые были созданы в указанный период, или git-ветки с активностью в рамках периода. Также для определённого множества branch/tag.
  • Параметр operator: And || Or определяет какие references будут результатом политики, те которые удовлетворяют оба условия или любое из них (And по умолчанию).

По умолчанию при сканировании reference количество искомых образов не ограничено, но поведение может настраиваться группой параметров imagesPerReference:

imagesPerReference:
  last: int
  in: duration string
  operator: And || Or
  • Параметр last: int определяет количество искомых образов для каждого reference. По умолчанию количество не ограничено (-1).
  • Параметр in: duration string (синтаксис доступен в документации) определяет период, в рамках которого необходимо выполнять поиск образов.
  • Параметр operator: And || Or определяет какие образы сохранятся после применения политики, те которые удовлетворяют оба условия или любое из них (And по умолчанию)

Для git-тегов проверяется только HEAD-коммит и значение last >1 не имеет никакого смысла, является невалидным

При описании группы политик необходимо идти от общего к частному. Другими словами, imagesPerReference для конкретного reference будет соответствовать последней политике, под которую он подпадает:

- references:
    branch: /.*/
  imagesPerReference:
    last: 1
- references:
    branch: master
  imagesPerReference:
    last: 5

В данном случае, для reference master справедливы обе политики и при сканировании ветки last будет равен 5.

Политики по умолчанию

В случае, если в werf.yaml отсутствуют пользовательские политики очистки, используются политики по умолчанию, соответствующие следующей конфигурации:

cleanup:
  keepPolicies:
  - references:
      tag: /.*/
      limit:
        last: 10
  - references:
      branch: /.*/
      limit:
        last: 10
        in: 168h
        operator: And
    imagesPerReference:
      last: 2
      in: 168h
      operator: And
  - references:  
      branch: /^(master|staging|production)$/
    imagesPerReference:
      last: 10

Разберём каждую политику по отдельности:

  1. Сохранять образ для 10 последних тегов (по дате создания).
  2. Сохранять по не более чем два образа, опубликованных за последнюю неделю, для не более 10 веток с активностью за последнюю неделю.
  3. Сохранять по 10 образов для веток master, staging и production.

Секция image

Образы описываются с помощью директивы image: image: string, с которой начинается описание образа в конфигурации.

image: frontend

Если в файле конфигурации описывается только один образ, то он может быть безымянным:

image: ~

Если в файле конфигурации описывается более одного образа, то каждый образ должен иметь собственное имя:

image: frontend
...
---
image: backend
...

Образ может иметь несколько имен, указываемых в виде YAML-списка (это эквивалентно описанию нескольких одинаковых образов с разными именами):

image: [main-front,main-back]

Имя образа требуется при использовании в helm-шаблонах, а также при запуске команд для определённого образа, описанного в werf.yaml.

Сборщик Dockerfile

Сборка образа с использованием имеющегося Dockerfile — самый простой путь начать использовать werf в существующем проекте. Ниже приведен пример минимального файла werf.yaml, описывающего образ example проекта:

project: my-project
configVersion: 1
---
image: example
dockerfile: Dockerfile

Также, вы можете описывать несколько образов из одного и того же Dockerfile:

image: backend
dockerfile: Dockerfile
target: backend
---
image: frontend
dockerfile: Dockerfile
target: frontend

И конечно, вы можете описывать образы, основанные на разных Dockerfile:

image: backend
dockerfile: dockerfiles/DockerfileBackend
---
image: frontend
dockerfile: dockerfiles/DockerfileFrontend

Stapel сборщик

Альтернативный способ сборки образов с использованием т.н. сборщика Stapel. Его особенности:

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