- Вопрос или проблема
- Как Requires=, так и Wants= приведут к запуску зависимых единиц
- After=, с другой стороны, только указывает порядок запуска.
- Ответ или решение
- Понимание basic.target после загрузки в CentOS 7
- Введение
- Основные понятия Systemd
- Структура basic.target
- Интерпретация
- Ответ на ваш вопрос
- Почему не объединять два After= в одно?
- Почему не использовать Requires= вместо Wants= (кроме timers.target)?
- Заключение
Вопрос или проблема
Вопрос, который у меня здесь есть, заключается в понимании basic.target
при загрузке моего сервера CentOS 7.
Некоторые вещи, которые я, кажется, правильно знаю о Systemd:
-
Requires=unit2
означает, чтоunit1
будет активирован только в том случае, еслиunit2
полностью выполнится -
Wants=unit2
означает, чтоunit1
будет активирован независимо от того, завершится ли успешно указанныйunit2
или нет -
After=unit2
означает, чтоunit1
будет активирован только после активацииunit2
-
В Systemd обычно все начинается параллельно
-
.target
в основном используется для “группировки” и “упорядочивания” (см. systemd.target) -
На самом деле
basic.target
должен быть активирован (вместе со всеми его зависимостями), прежде чем достичьmulti-user.target
(который является уровнем выполнения по умолчанию для сервера)
Хорошо, надеюсь, что на данный момент я прав.
Теперь, рассматривая basic.target
:
$ sudo cat /usr/lib/systemd/system/basic.target
[Unit]
Description=Basic System
Documentation=man:systemd.special(7)
Requires=sysinit.target
After=sysinit.target
Wants=sockets.target timers.target paths.target slices.target
After=sockets.target paths.target slices.target
Итак, теперь моя интерпретация такова:
-
basic.target
будет активирован только после успешного завершенияsysinit.target
-
Кроме того,
basic.target
желает, чтобыsockets.target
и т.д. работали -
Дополнительный
After=
означает, что, пожалуйста, активируйтеbasic.target
только после активацииsockets.target
,paths.target
иslices.target
. Ничего страшного, еслиtimers.target
не выполняется. -
Так почему бы не объединить два
After=
в одно? Почему бы не использоватьRequire=
вместоWants
(за исключениемtimers.target
)?
Ваш вопрос в пункте 4 выделяется, остальные служат контекстом.
Почему бы не объединить два
After=
в одно?
Нет никаких технических причин, препятствующих объединению двух директив After=
. Порядок единиц в After=
, Wants=
и Requires=
не имеет значения; они могут даже быть из разных файлов (например, переопределений) и все равно будут объединены в единый набор для проверки. Таким образом, решение о том, объединять или нет, может основываться на факторах, таких как читаемость и удобство шаблонизации.
Почему бы не использовать
Require=
вместоWants=
(за исключениемtimers.target
)?
чтобы запустить цели, но не дать сбой basic.target
, если некоторые из зависимых целей не выполняются.
Это противоположно Requires=sysinit.target
, что приведет к запуску sysinit.target
и даст сбой basic.target
, если sysinit.target
не выполнится.
Как Requires=
, так и Wants=
приведут к запуску зависимых единиц
(и это запустит их желания и требования к запуску, каскадно опускаясь вниз по дереву). Разница заключается в том, что происходит, если требуемая служба не запускается. Если служба отсутствует или не может быть запущена, все службы, которые Requires=
эту службу, также не смогут запуститься. Однако службы, которые Wants=
неудавшуюся службу, все равно будут запускаться. Например, если paths.target
или slices.target
из-за какой-либо причины не будут выполнены в текущей конфигурации, basic.target
все равно может быть достигнут с помощью Wants=
, но не с помощью Requires=
.
After=
, с другой стороны, только указывает порядок запуска.
Предположим, some.service
имеет After=postres.service
без Wants=
и Requires=
, но в системе нет postgres.service
. some.service
запустится как обычно, игнорируя отсутствующий postres.service
. Если postres.service
есть в системе, но неудачно попытался запуститься, some.service
будет ждать, пока postres.service
попытается запуститься, а затем все равно запустится.
Не имеет значения, включен some.service
или нет. Если не включен, когда вы запускаете его вручную, он запустится без попытки запустить postres.service
.
Добавление Requires=postres.service
или Wants=postres.service
к some.service
приведет к тому, что postres.service
также будет запущен при запуске some.service
любым способом. Если postres.service
находится в Requires=
, его сбой в запуске также приведет к неудаче запуска some.service
.
Если вы просто укажете Requires=
без After=
, я не совсем уверен. Мое предположение, что systemd
запустит их одновременно, и сбой postres.service
ничего не сделает.
** есть один случай, в котором я уверен: если в some.service
вы укажете только Requires=postres.service
без After=postres.service
, но postres.service
отсутствует в системе, любые попытки запустить some.service
потерпят неудачу.
Поэтому всем обычно рекомендуется использовать как Requires=
, так и After=
вместе, когда вы хотите убедиться, что одна служба успешно запустится до запуска другой службы.
Ответ или решение
Понимание basic.target после загрузки в CentOS 7
Введение
Система инициализации Systemd является неотъемлемой частью современных дистрибутивов на базе Linux, таких как CentOS 7. Понять, как работает basic.target
, имеет решающее значение для администраторов, стремящихся оптимизировать время загрузки, а также для настройки и диагностики служб. В этом ответе мы подробно разберем, что такое basic.target
, его зависимости и роль в процессе загрузки системы.
Основные понятия Systemd
Перед тем как углубиться в basic.target
, давайте обобщим несколько ключевых понятий:
- Requires= — означает, что одна единица (unit1) будет активирована только в том случае, если успехом завершится активация другой единицы (unit2).
- Wants= — указывает на то, что unit1 будет активирована независимо от успеха unit2. Это более «мягкий» вариант, который не приводит к сбою, если unit2 не может начать работу.
- After= — указывает, что unit1 будет активирована только после активации unit2.
- .target — используется для группировки и упорядочивания других юнитов.
Важно отметить, что в Systemd единицы, как правило, запускаются параллельно, что значительно ускоряет процесс загрузки.
Структура basic.target
Теперь рассмотрим сам basic.target
. Исходный файл определяет его зависимости:
[Unit]
Description=Basic System
Documentation=man:systemd.special(7)
Requires=sysinit.target
After=sysinit.target
Wants=sockets.target timers.target paths.target slices.target
After=sockets.target paths.target slices.target
Интерпретация
-
Зависимости от sysinit.target:
basic.target
активируется после успешного завершенияsysinit.target
. Это означает, что все основные системные инициализации должны быть выполнены, прежде чем мы можем начать другие базовые службы.
-
Желательные юниты:
Wants=sockets.target
,timers.target
,paths.target
,slices.target
подразумевают, чтоbasic.target
предпочитает наличие этих юнитов, но они не являются обязательными для его активации.
-
Указание порядка:
After=sockets.target
,After=paths.target
,After=slices.target
указывает на то, чтоbasic.target
активируется после этих юнитов. Однако это не значит, что они являются обязательными для его успешного прогресса, особенно в случае сtimers.target
.
Ответ на ваш вопрос
Почему не объединять два After=
в одно?
Нет технических ограничений на объединение нескольких After=
в одну строку. Однако из соображений читаемости и удобства разработки лучше оставить их раздельными. Это упрощает управление зависимостями и позволяет легче отслеживать, какие юниты должны активироваться в каком порядке.
Почему не использовать Requires=
вместо Wants=
(кроме timers.target
)?
Использование Wants=
вместо Requires=
здесь обусловлено желанием обеспечить некоторую устойчивость системы к сбоям. Если один из желаемых юнитов, таких как sockets.target
или slices.target
, не может быть запущен, это не повлияет на успешное достижение basic.target
. Альтернативно, использование Requires=
означало бы, что если зависимый юнит не может запуститься, это приведет к сбою всей группы.
Заключение
Понимание basic.target
в контексте Systemd является критически важным для оптимизации вращения сервера на CentOS 7. Правильная расстановка зависимостей и понимание их функциональности поможет не только в конфигурировании системы, но и в управлении службами. Соблюдение оптимальной структуры загрузки может способствовать увеличению производительности и надежности ваших приложений и служб.