Практика Руководство

Автоперезапуск игрового сервера: служба systemd и лимиты

Автоматический перезапуск игрового сервера через systemd: настройка Restart=on-failure, защита от бесконечных циклов и таймауты сохранения.

Автоперезапуск игрового сервера: служба systemd и лимиты

Игровые серверы часто сталкиваются с непредвиденными сбоями: утечки памяти, неперехваченные исключения в модах или аварийные завершения из-за нехватки ресурсов вызывают падение процесса. Если сервер запущен вручную через консоль или самодельный цикл while true, он либо остаётся выключенным до утра, пока администратор не проверит сервер, либо входит в бесконечный цикл перезапусков, забивая накопитель логами сбоев.

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

Разница между Restart=always и Restart=on-failure#

Многие администраторы совершают грубую ошибку, устанавливая в юните директиву Restart=always. В этом случае systemd будет перезапускать сервер даже тогда, когда администратор намеренно остановил процесс штатной командой для технического обслуживания.

Директива Restart=on-failure действует избирательно:

  • Чистый выход с кодом 0 (штатная остановка или команда сохранения и выхода) не вызывает перезапуск.
  • Падение процесса по сигналу ядра (SIGSEGV, SIGKILL), завершение с ненулевым кодом ошибки или срабатывание таймаута активируют автоматический перезапуск.

Добавьте обязательную задержку RestartSec:

ini
[Service]
Restart=on-failure
RestartSec=10

Задержка в 10–15 секунд необходима операционной системе, чтобы полностью освободить сетевые сокеты TCP/UDP и разгрузить оперативную память перед новым запуском бинарного файла.

Защита от бесконечного цикла падений через StartLimitBurst#

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

Для защиты от «шторма перезапусков» используйте секцию [Unit] с лимитами срабатываний:

ini
[Unit]
Description=Resilient Dedicated Game Server
After=network.target
StartLimitIntervalSec=300s
StartLimitBurst=5

Эта связка параметров означает: если сервер упал более 5 раз в течение 5 минут (300 секунд), systemd принудительно переведёт службу в состояние failed и прекратит попытки запуска, защищая сервер от перегрузки.

Корректный останов и таймауты сохранения мира#

Игровым серверам (например, Minecraft, CS2, Palworld, Rust) требуется значительное время на выгрузку чанков и фиксацию изменений мира на диск при получении сигнала остановки.

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

Сконфигурируйте увеличенный таймаут и мягкий сигнал завершения:

ini
[Service]
KillSignal=SIGTERM
TimeoutStopSec=60
FinalKillSignal=SIGKILL

Итоговый шаблон отказоустойчивой службы:

bash
cat << 'EOF' | sudo tee /etc/systemd/system/gameserver-resilient.service
[Unit]
Description=Resilient Dedicated Game Server
After=network.target
StartLimitIntervalSec=300s
StartLimitBurst=5

[Service]
Type=simple
User=gameserver
Group=gameserver
WorkingDirectory=/opt/gameserver
ExecStart=/opt/gameserver/server_binary -dedicated +port 27015
Restart=on-failure
RestartSec=10
KillSignal=SIGTERM
TimeoutStopSec=60

[Install]
WantedBy=multi-user.target
EOF

Примените созданный юнит:

bash
sudo systemctl daemon-reload
sudo systemctl enable gameserver-resilient

Анализ причин сбоев и аудит перезапусков#

Чтобы понять, почему сервер перезапускался ночью, запросите системный журнал службы с фильтром по времени и кодам возврата:

bash
journalctl -u gameserver-resilient --since "12 hours ago" --no-pager | grep -E "(Failed|exit|Killed|signal)"

Команда systemctl show позволяет просмотреть точный код завершения последнего упавшего процесса:

bash
systemctl show gameserver-resilient -p Result -p ExecMainStatus -p ExecMainCode

Для непрерывного контроля за состоянием игровых служб и получения мгновенных уведомлений об авариях в Telegram или Discord администраторы подключают панели управления серверами, где встроенные системы мониторинга отслеживают метрики процесса и восстанавливают службы автоматически.

Источники#