Установите зависимость модуля в systemd ВНЕ файла модуля.

Вопрос или проблема

Я хочу запускать некоторые контейнеры через systemd, и у каждого из них есть связанный файл compose, так что должно быть возможно написать только один файл unit для systemd и указать файл compose как имя экземпляра. Таким образом, файл unit будет содержать что-то вроде:

ExecStart=/usr/local/bin/docker-compose -f %i.yaml up

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

Пример: n-tier-app.yaml зависит от basic-services.yaml

Определите зависимости в файлах drop-in <unit>.d/ для каждой инстанции. Например, если у вас есть шаблон [email protected], вы можете дополнительно настроить отдельные экземпляры через [email protected]/foo.conf и [email protected]/deps.conf.

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

Зависимости без упорядочивания можно определить аналогично описанному выше, путем создания символьных ссылок на какой-либо unit в <unit>.requires/ или <unit>.wants/. Это работает с шаблонами, потому что имеет значение только имя символьной ссылки; она может указывать на несуществующий файл (например, на ../[email protected]), так как systemd вручную разрешает его базу до unit. Однако это ограничено Wants/Requires и поэтому обычно полезно только для добавления зависимости из unit типа .target, который имеет специальную возможность автоматически добавлять After ко любой зависимости – следовательно, <unit>.d/*.conf предпочтительнее для всех других случаев.

Ответ или решение

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

Теория: Управление зависимостями в systemd

systemd предлагает различные способы управления зависимостями между сервисами. Зависимости можно задавать с помощью деклараций Requires, Wants, After и Before.

  • Requires: обозначает жесткую зависимость. Если указанный сервис не запущен или не может быть запущен, то и сам сервис не будет запущен.
  • Wants: более гибкая зависимость. systemd попытается запустить указанный сервис, но если он будет недоступен, основной сервис всё равно может быть запущен.
  • After/Before: используются для задания порядка запуска сервисов, без указания на необходимость их сосуществования.

Пример: Применение .d/ drop-in файлов

Чтобы управлять зависимостями без прямого редактирования основного unit-файла, можно использовать drop-in файлы, которые размещаются в директориях unit.d/. Например, в вашем случае, у вас есть шаблонный unit-файл <подразделение>@.service, через который управляются различные инстанции контейнеров.

Чтобы правильным образом выставить зависимость между инстанциями:

  1. Создайте директорию для drop-in файлов для конкретной инстанции сервиса. Пусть это будет /etc/systemd/system/[email protected]/instance_name.d/.

  2. Создайте конфигурационные файлы для каждой инстанции, где можно конкретизировать зависимости. Например, dependency.conf может содержать:

    [Unit]
    Requires=basic-services@instance_name.service
    After=basic-services@instance_name.service
  3. Добавление дополнительных зависимостей в instance_name.d/:
    Дополнительно, для реализации зависимости обязательно наличие symlink в директорию wants/ или requires/. Например:

    ln -s /etc/systemd/system/basic-services@basic_services.service /etc/systemd/system/[email protected]/instance_name.wants/basic-services@basic_services.service

Применение: Практическая реализация и учет ограничений

Использование drop-in файлов для управления зависимостями позволяет гибко изменять настройки для каждой инстанции без необходимости модификации оригинального шаблонного unit-файла. Это особенно полезно в случаях, когда количество управляемых контейнеров растет, и.к. он позволяет централизовать изменения конфигураций и облегчает их тестирование.

Преимущества такого подхода:

  • Гибкость: Возможность изменять настройки для каждой инстанции отдельно.
  • Контроль: Управление порядком запуска и точек отказа на уровне systemd.
  • Снижение рисков: Позволяет тестировать изменения на одной инстанции, прежде чем применять их массово.

Ограничения и рекомендации:

  • Не следует пренебрегать тестированием конфигурации на живой системе. Проведите тесты на полном цикле запуска/остановки контейнеров в тестовом окружении.
  • Убедитесь, что все symlink создаются корректно и указывают на существующие файлы, чтобы избежать ошибок поиска units.

Внедрение описанных методов позволит оптимально управлять зависимостями containers и их orchestration, поддерживая чистоту и организованность конфигурационных файлов systemd. Это особенно актуально в сложных деплоях, где наличие и правильная последовательность запуска сервисов критичны для работы всего приложения.

Оцените материал
Добавить комментарий

Капча загружается...