Если monitoring-snmp-sync.service застрял в activating, не перезапускайте его по кругу. Сначала проверьте, не ждут ли друг друга скрипт синхронизации и экспортёр.

В опубликованном на Хабре разборе «Как systemd превратил обычный скрипт перезапуска в бесконечный дедлок» цепочка выглядела так:

таймер
 → monitoring-snmp-sync.service
 → snmp-sync.sh
 → systemctl try-restart monitoring-snmp-exporter
 → monitoring-snmp-exporter.service
 → After=monitoring-snmp-sync.service

Скрипт ждал перезапуска экспортёра. Экспортёр ждал завершения скрипта. Таймаут не прерывал ожидание, поэтому мониторинг мог молчать неделями.

Задача администратора — проверить не отдельную службу, а всю цепочку. После исправления нужно доказать, что список целей снова обновляется и конечная метрика относится к существующему устройству.

Сначала найдите, на каком звене остановилась цепочка

Начните с двух юнитов:

systemctl status monitoring-snmp-sync.service
systemctl status monitoring-snmp-exporter.service

Затем откройте их журналы:

journalctl -u monitoring-snmp-sync.service
journalctl -u monitoring-snmp-exporter.service

systemctl status показывает состояние юнита и результат последней попытки запуска. journalctl -u выводит сообщения выбранной службы. Такой порядок диагностики описан в руководстве Fastfox по циклам перезапуска systemd.

Наблюдаемый признакЧто происходит в systemdКоманда проверкиЧто искать
sync.service долго остаётся в activatingoneshot-скрипт не завершилсяsystemctl status monitoring-snmp-sync.serviceактивный процесс systemctl, который ждёт другую службу
Экспортёр не переходит в activeзапуск поставлен после незавершённого sync-юнитаsystemctl status monitoring-snmp-exporter.serviceожидание задания либо зависимость от monitoring-snmp-sync.service
Экспортёр несколько раз запускается и падаетсработала политика Restart=on-failurejournalctl -u monitoring-snmp-exporter.serviceпервая ошибка приложения перед повторными запусками
Экспортёр остаётся в failedsystemd остановил новые попытки запускаsystemctl show monitoring-snmp-exporter.service -p StartLimitIntervalUSec -p StartLimitBurstэффективный интервал и число разрешённых запусков

Состояние activating без конечного таймаута требует проверки зависимостей. Ещё один перезапуск лишь запускает ту же цепочку заново.

Если службы активны, но пользователи или внешняя система не получают ожидаемый результат, пройдите проверку сервиса за зелёными серверными метриками. Состояние active подтверждает работу процесса, но не всей операции.

Как четыре обычные настройки образовали дедлок

Таймер раз в минуту запускал monitoring-snmp-sync.service. Это был юнит Type=oneshot: он выполнял snmp-sync.sh, обновлял /etc/snmp/snmp.yml, а при изменении файла вызывал:

systemctl try-restart monitoring-snmp-exporter.service

Вызов работал синхронно. Скрипт не мог завершиться, пока systemd не закончит перезапуск экспортёра.

У экспортёра при этом стояла зависимость:

After=monitoring-snmp-sync.service

По systemd.unit(5), на который ссылается автор разбора на Хабре, After= задаёт порядок запуска, когда оба юнита запускаются одновременно. В этой схеме экспортёр получил задание на запуск до завершения sync-юнита и встал в очередь за ним.

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

monitoring-snmp-sync.service
 ждёт завершения systemctl try-restart
 ↓
monitoring-snmp-exporter.service
 ждёт завершения monitoring-snmp-sync.service
 ↓
monitoring-snmp-sync.service

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

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

Почему systemd не остановил операцию через 90 секунд

Общий DefaultTimeoutStartSec= в systemd равен 90 секундам. Но у Type=oneshot значение TimeoutStartSec= по умолчанию отключено: systemd использует infinity.

Оба параметра приведены в разборе инцидента на Хабре со ссылкой на документацию systemd. Из-за исключения для oneshot ожидание могло продолжаться неограниченно.

Проверьте эффективное значение, а не только текст unit-файла:

systemctl show monitoring-snmp-sync.service -p Type -p TimeoutStartUSec

Если команда показывает TimeoutStartUSec=infinity, systemd не завершит зависший запуск по стандартному 90-секундному пределу.

Явный таймаут ограничит последствия, но не исправит граф. После его срабатывания перезапуск экспортёра всё равно не выполнится. Основная правка должна разорвать синхронное ожидание.

try-restart создаёт другой сбой, когда экспортёр уже остановлен

systemctl try-restart перезапускает только работающий юнит. Если экспортёр остановлен, команда ничего не запускает. Такое поведение описано в том же разборе инцидента на Хабре.

На одном из четырёх хостов именно это и произошло. Скрипт обновил конфигурацию, вызвал try-restart, но экспортёр уже не работал. Команда не вернула ошибку запуска, потому что запуска не было.

Здесь нужен выбор по требуемому результату:

Для обязательного запуска команда будет выглядеть так:

systemctl --no-block restart monitoring-snmp-exporter.service

Флаг --no-block ставит задание в очередь и сразу возвращает управление скрипту. Этот механизм описан в разборе на Хабре. Sync-юнит завершится, после чего systemd сможет выполнить отложенный запуск экспортёра.

Команду без блокировки нельзя считать подтверждением успешного запуска. Она подтверждает только приём задания. Результат проверяют отдельным шагом — так же, как при контроле результата автоматического перезапуска 1С.

Цикл перезапуска — не дедлок

Дедлок и цикл перезапусков выглядят похоже только снаружи: служба не работает, а systemd занят. Механика у них разная.

При дедлоке два задания ждут друг друга. Процесс может долго оставаться в activating, не переходя к новой попытке.

При цикле экспортёр запускается, завершается с ошибкой, а Restart=on-failure просит systemd повторить запуск. Руководство Fastfox описывает этот маршрут как старт → ошибка → рестарт.

В исследованном случае один экспортёр завершался из-за ошибки YAML:

line 12: mapping values are not allowed in this context

После нескольких быстрых попыток systemd прекратил запускать службу. В разборе на Хабре приведены стандартные значения: StartLimitBurst=5 попыток за StartLimitIntervalSec=10s.

СценарийЧто видно в status или журналеЧего не делатьИсправление
Дедлок sync-юнита и экспортёраsync.service остаётся в activating, экспортёр ждёт запускаперезапускать оба юнита по кругуразорвать зависимость либо вызвать systemctl --no-block restart
try-restart встретил остановленный экспортёркоманда завершилась, но экспортёр остался inactiveсчитать нулевой код подтверждением работающей службызаменить try-restart на restart, если служба обязана работать
Экспортёр падает сразу после запускав журнале повторяется ошибка приложенияувеличивать число попыток до проверки первой ошибкиисправить конфигурацию, права или окружение
Сработал предел запусковfailed, start-limit-hit, Start request repeated too quicklyвыполнять только reset-failedустранить причину падения, затем сбросить состояние

reset-failed снова разрешает запуск. Конфигурацию, права и ошибку приложения команда не исправляет.

Как восстановить экспортёр после start-limit-hit

Сначала найдите первую содержательную ошибку. Последние сообщения о лимите показывают следствие, а не причину:

journalctl -u monitoring-snmp-exporter.service

Для ошибки YAML исправьте сам файл /etc/snmp/snmp.yml. Затем запустите экспортёр вручную через systemd и снова проверьте журнал.

После устранения причины сбросьте состояние:

systemctl reset-failed monitoring-snmp-exporter.service
systemctl restart monitoring-snmp-exporter.service
systemctl status monitoring-snmp-exporter.service

По руководству Fastfox, systemctl reset-failed очищает состояние failed и счётчик лимита запусков. Та же последовательность нужна при сообщении Start request repeated too quickly: сначала причина, затем сброс.

Если меняли unit-файл, перечитайте конфигурацию systemd:

systemctl daemon-reload

daemon-reload нужен после изменения unit-файлов, что также указано в руководстве Fastfox. Изменение только /etc/snmp/snmp.yml такой команды не требует: этот файл читает экспортёр, а не менеджер systemd.

После исправления проверьте данные, а не зелёный статус

Работающий процесс ещё не доказывает, что мониторинг видит актуальные цели. В разобранном инциденте метрика

up{snmp_device="..."} = 0

оставалась для устройства, удалённого неделей ранее. Скрипт синхронизации завис, список целей замёрз, а старая временная серия продолжала попадать в мониторинг.

Проверка должна пройти по тому же маршруту, что и данные:

  1. Таймер запускает monitoring-snmp-sync.service.
  2. Скрипт завершает работу.
  3. Файл целей получает ожидаемое содержимое.
  4. systemd принимает и выполняет перезапуск экспортёра.
  5. Экспортёр отвечает на запрос.
  6. Мониторинг получает метрики по текущему списку устройств.

Последний пункт отделяет восстановленную службу от восстановленного наблюдения. Если график продолжает показывать удалённую цель, цепочка ещё сломана.

В инфраструктуре 1С применяйте тот же принцип: связывайте пользовательскую операцию с журналами приложения и показателями сервера. Отдельный маршрут описан в материале о поиске задержки по APDEX, техжурналу и метрикам.

Мониторинг должен следить за возрастом собственных данных

Сбой оставался незамеченным две–три недели. Мониторинг проверял удалённые устройства, но не контролировал работу механизма, который обновлял их список.

Добавьте отдельный признак свежести. Это может быть время последнего успешного выполнения sync-юнита либо метка времени последнего принятого файла целей. Порог выберите из расписания: если таймер работает раз в минуту, несколько пропущенных запусков уже требуют проверки.

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

Правило для скриптов перезапуска под systemd

Юнит не должен синхронно перезапускать службу, которая через After= ждёт завершения этого же юнита. Разорвите зависимость либо поставьте перезапуск в очередь через --no-block.

Перед возвратом мониторинга в работу проверьте пять пунктов:

snmp systemd администрирование мониторинг 1с перезапуск служб