Search
Write a publication
Pull to refresh
3612.25
RUVDS.com
VDS/VPS-хостинг. Скидка 15% по коду HABR15

GitLab CI/CD components: повторно используемый CI как путь к чистому и здоровому GitLab

Level of difficultyMedium
Reading time6 min
Views940
Лиса снова копирует код
Лиса снова копирует код

Ходит легенда, что однажды разработчики GitLab закупились шапками, сделанными из переработанных крышечек от бутылок. И их настолько вдохновила идея повторного использования, что они решили добавить такую возможность и в свой продукт. Подкрепив это всё стандартизацией CI, они представили комьюнити новый механизм — GitLab CI/CD components.

В этой статье я хочу рассказать Хабру, для чего вообще нужны компоненты, как ими пользоваться и где использовать.

Советую перед прочтением ознакомиться со статьёй по важным механизмам GitLab.

Что же это за механизм?

CI/CD components — переиспользуемые блоки конфигурации пайплайна, оформленные как версионируемые модули. Появились с 16-й версии GitLab. По сути это просто шаблоны, которые с помощью директивы inlude подключаются в CI. Однако, в отличие от обычных шаблонов, они публикуются в отдельный каталог, благодаря чему доступны за пределами проекта, в котором реализованы, и мы можем использовать общий шаблон для нескольких проектов.

При использовании self-managed версии мы сразу забираем общие шаблоны, а также имеем возможность добавлять свои, что особенно актуально для решения проблемы дублирования кода.

Каждый шаблон — yaml-файл, содержащий определённую конфигурацию. Существует несколько паттернов их использования:

  • Просто добавляем директиву include и наслаждаемся результатом работы готового пайплайна.

  • После включения через include используем extends для использования каких-то шаблонных задач (обычно это скрытые задачи, начинающиеся с точки. Пример: .deploy-ansible). Подробнее об этом далее.

Как этим пользоваться?

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

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

Основной и самый популярный способ — это директива include.

Шаблон использования:

---
include:
  - component: <FQDN>/<namespace>/<project>/<component-name>@<version>
    inputs:
      <param1>: <value1>
      <param2>: <value2>

Пример использования:

# Пример использования встроенного компонента GiLab - Autodevops
---
include:
  - component: gitlab.com/components/autodevops/build@2.11.0
  inputs:
    stage: build

# Пример использования своего компонента
---
include:
  - component: $CI_SERVER_FQDN/my-org/deploy-components/java@1.0.0
    inputs:
      stage: build
      version: 21

Разберём на примере нашего компонента: здесь переменная $CI_SERVER_FQDN — домен, используемый для GitLab. Далее путь до самого проекта my-org/deploy-components/ , потом идёт имя шаблона и версия компонента javа@1.0.0.

.gitlab-ci.yml         # CI, например, для тестирования компонента
README.md              # документация по эксплуатации
templates/             # основная директория с шаблонами
├── template1.yml
└── template2.yml

Гибкая настройка при использовании компонента

Важное преимущество шаблонов — возможность переопределять отдельные части при помощи директивы extends. Давайте быстро вспомним, в чём суть обратного глубокого слияния, используемого в реализации extends: задача дополняет базовую, при конфликте новых ключей с ключами шаблона берутся новые значения. Рассмотрим пример компонента, содержащего скрытую задачу .test, которая требует определённых переменных, тогда для её использования мы напишем свою задачу, унаследованную от .test:

test-job:
  extends: .tests
  variables:
    SOME_FLAG: "true"

Это частая практика для компонентов: использовать скрытые задачи, чтобы далее дополнять их определёнными переменными или настройками, при этом сохранив основную логику.

Структура компонента

Структура CI/CD компонента в GitLab основана на yaml-файлах — шаблонах. Чтобы мы могли версионировать и делиться компонентом между проектами, мы используем отдельный проект, который также можно опубликовать в CI/CD Catalog для общего использования.

Структура проекта

Основная структура проекта выглядит примерно так:

.gitlab-ci.yml         # CI например для тестирования компонента
README.md              # документация по эксплуатации
templates/             # основная директория с шаблонами
├── template1.yml
└── template2.yml
  • templates/: Основная директория для компонента. Она содержит все необходимые шаблоны.

  • README.MD: Обязательный файл с описанием компонента, примерами использования, доступными inputs (входными параметрами) и инструкциями.

  • .gitlab-ci.yml: Рекомендую добавить CI для самого компонента. Полезно для автоматизации тестирования и версионирования.

Структура шаблонов компонента

Структура yaml-конфига для компонента делится на две части, разделённые ---:

  • spec:: Метаданные компонента, включая входные параметры (inputs). Здесь мы определяем, что именно должен на вход получать наш компонент для корректной работы.

  • Основная конфигурация: Стандартный CI-конфиг, который использует inputs для гибкой настройки.

Давайте поговорим немного о самих inputs — параметрах, которые мы задаём, когда подключаем компонент. Именно они обеспечивают гибкость. Параметры определяются в spec.input и содержат следующие поля:

  • type:

    • string (по умолчанию);

    • boolean;

    • number;

    • array.

  • default: Значение по умолчанию.

  • description: Описание (отображается в CI/CD Catalog).

  • options: Опционально, список допустимых значений. Полезно, когда мы хотим ограничить возможные варианты значений.

Чтобы подставить inputs в конфиг, используется следующий синтаксис: $[[ inputs.name ]] .

Пример inputs:

spec:
  inputs:
    stage:
      type: string
      default: test
      description: "Этап пайплайна, на котором запускаем job"
    enable_cache:
      type: boolean
      default: false
      description: "Включить кэширование зависимостей"
    versions:
      type: array
      default: ["1.0", "2.0"]
      description: "Массив версий для тестирования"

Пример компонента:

spec:
  inputs:
    message:
      type: string
      default: "Hello, World!"
      description: "Сообщение для вывода"
    stage:
      type: string
      default: test
      description: "Этап пайплайна"
---
echo-job:
  stage: $[[ inputs.stage ]]  # Подставляем inputs.stage
  script: 
    - echo "$[[ inputs.message ]]"  # Подставляем inputs.message

Однако есть ещё одна практика для передачи значений в компонент — variables внутри самих задач. Давайте посмотрим на пример компонента:

spec:
  inputs:
    message:
      type: string
      default: "Hello, World!"
      description: "Сообщение для вывода"
    stage:
      type: string
      default: test
      description: "Этап пайплайна"
---
.echo-job:  # Скрытая job 
  stage: $[[ inputs.stage ]]  # Подставляем inputs.stage
  variables:  # Определение variables
    GREETING_PREFIX: "Output:"  # Определяем variable
    MESSAGE_TEXT: "$[[ ` ]]"  # Variable зависит от input
  script: 
    - echo "$GREETING_PREFIX $MESSAGE_TEXT"  # Использование variables в скрипте

И его использование:

include:
  - component: gitlab.example.com/my-org/echo-component@1.0.0
    inputs:
      message: "I'm absolute!"
      stage: build

my-echo:
  extends: .echo-job  # Наследует скрытую job из компонента, включая variables и script
  variables:  # Переопределение variables
    GREETING_PREFIX: "New Prefix:"
  rules:  # Добавляем rules
    - if: '$CI_COMMIT_BRANCH == "main"'

Здесь мы использовали переменную, определённую в variables. Также хочется обратить внимание на то, что inputs.message мы вынесли в переменные job. Это хорошая практика, которая делает визуально код более читаемым.

У такого варианта определения переменных есть свои плюсы и минусы:

  • Гибкость: таким образом мы получаем более гибкую настройку конкретных job, так как задаём переменные более локально относительно inputs.

  • Валидация: inputs позволяет задавать варианты значений и типы переменных, что повышает надёжность. variables такой функциональностью не обладают.

  • Сложность и читаемость: inputs более понятны для конечного пользователя компонента, чем variables и скрытые job. Подобные решения нужно подробно пояснять в документации.

Рекомендации по использованию компонентов

  • Не бойтесь использовать компоненты, ограничения на include достаточно большие, чтобы вы могли включить столько компонентов, сколько потребуется.
    Пример: проект на Java будет включать компоненты по сборке, тестированию, деплою и анализаторы (например, SAST).

  • extends лучше, чем копирование кода. Вынесите общую логику в компонент и дополняйте уже с помощью директивы.

  • Используйте rules для директивы include, когда есть шаблоны, которые не должны выполняться всегда.

  • Перед использованием обращайтесь к документации компонента. Там вы найдёте доступные переменные, область их определения (inputs или через variables и extends), а также возможные способы применения и примеры.

Рекомендации по созданию компонентов:

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

  • Не злоупотребляйте с вложенностью зависимостей. Компоненты могут сами включать другие компоненты, но это может усложнить поведение. Советую использовать их в меру и указывать статические версии (не @main).

  • Документируйте в README.MD. Опишите логику, переменные и примеры использования. Это поможет вашим коллегам и вам самим в будущем.

  • Версионирование и релизы обеспечат более стабильную работу компонента. Статические версии ведут себя более предсказуемо, чем latest.

  • Тестирование самого компонента в его CI — отличная практика, особенно если вы используете автоматизацию для релизов.

Чуть-чуть выводов

GitLab CI/CD components — мощный инструмент для быстрого создания пайплайнов из готовых шаблонов. Придерживайтесь минимально необходимого переопределения, гибкой настройки через переменные и контроля версий, и вы получите воспроизводимый и легко поддерживаемый CI.

Также советую ознакомиться с основными общедоступными компонентами GitLab. Они доступны по ссылке.

© 2025 ООО «МТ ФИНАНС»

Tags:
Hubs:
+14
Comments4

Articles

Information

Website
ruvds.com
Registered
Founded
Employees
11–30 employees
Location
Россия
Representative
ruvds