Зависимости systemd определяют порядок запуска, условия работы и взаимосвязи между юнитами. Они позволяют задавать, какие сервисы должны стартовать раньше/позже, что является обязательным условием для запуска, а также что должно быть остановлено вместе с юнитом.

Основные концепции

  • ordering dependencies — определяют порядок запуска (After/Before), но не гарантируют наличие работающего сервиса.
  • requirement dependencies — определяют обязательность (Requires, Wants, Requisite), формируют граф зависимостей.
  • conflict bindings — определяют несовместимость юнитов (Conflicts, Before/After вместе).
  • lifecycle coupling — параметры, влияющие на совместное остановку/старт (PartOf, BindsTo).
  • unit activation — зависимости влияют на то, какие юниты активируются при enable/start.

Структура / состав

  • ключевые директивы секции [Unit]:
    • Requires=, Wants=, Requisite=
    • BindsTo=, PartOf=
    • After=, Before=
    • Conflicts=
    • OnFailure=
  • targets — логические точки синхронизации (multi-user.target, network-online.target).
  • зависимости могут быть транзитивными через targets.
  • drop-in конфигурации могут добавлять зависимости к существующим юнитам.

Минимальные рабочие примеры

# Сервис, требующий запущенной сети
[Unit]
Description=MyApp service
Requires=network-online.target
After=network-online.target
 
[Service]
ExecStart=/opt/myapp/bin/myapp
# Мягкая зависимость от Redis (не критично)
[Unit]
Description=Worker service
Wants=redis.service
After=redis.service
 
[Service]
ExecStart=/opt/worker/run
# Жёсткое связывание: остановка одного ведёт к остановке другого
[Unit]
Description=Helper service
BindsTo=mainapp.service
After=mainapp.service
 
[Service]
ExecStart=/usr/bin/helper
# Сервис запускается, если другой упал (OnFailure)
[Unit]
Description=Monitoring handler
OnFailure=alert-handler.service
 
[Service]
ExecStart=/usr/bin/alert-script

Типичные операции / кейсы

  • проверка зависимостей:
    • systemctl list-dependencies myapp.service
    • systemctl list-dependencies --reverse myapp.service
  • анализ порядка запуска:
    • systemd-analyze critical-chain
  • добавление зависимостей через drop-in:
    • systemctl edit myapp.service → добавление [Unit] After=postgresql.service
  • организация каскада рестартов:
    • OnFailure=handler.service — обработчик аварий
  • создание жёстко связанных сервисов:
    • BindsTo= + PartOf= → parent-child связка
  • корректное ожидание сети:
    • After=network-online.target + Wants=network-online.target + включённый systemd-networkd-wait-online.service

Диагностика / ошибки

  • Юнит стартует раньше, чем доступен зависимый сервис — проверить разницу между After= и Requires=; After= только порядок, Requires= гарантирует запуск.
  • Сервис не стартует (Dependency failed) — проверить, что зависимый юнит активируется и не падает сам; systemctl status <dependency>.
  • Зависимость игнорируется — проверить, в каком каталоге находится конфигурация; могут быть override-и; systemd-analyze verify.
  • Сервис неожиданно останавливается — возможно работает связка BindsTo=; проверять journalctl -u <service> на события stop из-за зависимости.
  • Циклическая зависимость — systemd ругнётся в status; проверить After/Before комбинации; перенести зависимости в target.
  • Запускается лишний сервис — Wants= активирует зависимость автоматически; если это нежелательно → использовать After= без Wants=.

Дополнительные материалы