MAATRIX / Блог / Скачки задержки ровно в 03:15: бэкап соседа забивал общий аплинк

Скачки задержки ровно в 03:15: бэкап соседа забивал общий аплинк

MAATRIX

Мониторинг третью ночь подряд рисовал одну и ту же картину: ровно в 03:15 задержка до сервера подскакивала в несколько раз, часть пакетов терялась, а через пару минут всё возвращалось к норме — как будто кто-то щёлкал выключателем. Собственная нагрузка на VPS в этот момент не менялась ни на йоту. Разбираем инцидент от первого симптома до найденной причины: почему идеально регулярное расписание сбоя почти всегда означает чужую cron-задачу на разделяемой инфраструктуре, и что с этим делать.

Симптом: скачок ровно в 03:15 каждую ночь

Первый сигнал пришёл не от пользователей, а от собственного мониторинга. Blackbox-проверка ICMP до арендованного VPS, которая обычно держала задержку в спокойном узком диапазоне, каждую ночь давала всплеск на графике — острый пик, а не плавный рост. Grafana с алертом по probe_icmp_duration_seconds из Prometheus начала присылать уведомления в одно и то же время несколько ночей подряд.

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

  • Точное время начала и конца — не «около трёх ночи», а 03:15:0X до 03:1Y:0Z по логам мониторинга, с указанием часового пояса сервера мониторинга и часового пояса самого VPS (это разные вещи, если они в разных дата-центрах).
  • Характер деградации — рост RTT (round-trip time) в разы от базового уровня, появление потерь пакетов (packet loss), а не просто «медленно открывается сайт». Это разные симптомы с разными причинами.
  • Длительность — окно деградации ограничено по времени и заканчивается само, без вмешательства. Это резко отличает картину от постепенной деградации при исчерпании ресурсов.
  • Повторяемость — совпадение окна из ночи в ночь с точностью до минуты, а не «плюс-минус полчаса».

Собранные вместе, эти четыре пункта — материал для тикета в поддержку и для собственного расследования, а не жалоба «у нас тормозит». Без них разговор с провайдером обычно упирается в «у нас всё зелёное».

Как устроен разделяемый канал на виртуализированном узле

Ключевая вещь, которую нужно понимать про обычный VPS: одна физическая машина (узел, node, гипервизор) хостит десятки или сотни виртуальных серверов разных клиентов. Эти VPS делят между собой физические ресурсы узла — процессорные ядра, оперативную память, дисковую подсистему и сетевой аплинк, то есть физический порт или агрегированный канал, через который узел вообще подключён к внешней сети провайдера.

Для CPU и памяти современные гипервизоры (KVM, Xen, VMware) умеют относительно честно делить ресурсы через квоты, cgroups, лимиты по vCPU — перерасход виден как steal time на соседних машинах и управляем на уровне гипервизора.

С сетью исторически всё менее прозрачно. Физический аплинк узла — конечная труба фиксированной пропускной способности, через которую общаются с внешним миром все виртуальные машины на этом узле. Если провайдер не настроил жёсткий network QoS с гарантированной полосой на каждую VPS (а на бюджетных и средних тарифах это чаще исключение, чем правило), трафик всех арендаторов узла конкурирует за одну трубу на равных, без изоляции.

Дальше механика простая:

  1. Один из соседей по физическому узлу запускает регулярную тяжёлую сетевую задачу — например, полный бэкап крупного объёма данных, который каждую ночь отправляется по сети во внешнее хранилище (S3-совместимый бакет, другой дата-центр, специализированный backup-сервис).
  2. На время передачи эта VPS начинает генерировать трафик, сопоставимый по объёму с пропускной способностью всего аплинка узла или значимой его долей.
  3. Общий канал узла насыщается (saturation) — пакеты от всех остальных VPS, включая вашу, начинают вставать в очередь на исходящем порту или теряться при переполнении буферов.
  4. Как только бэкап соседа завершается, насыщение канала исчезает, и задержка у всех возвращается к норме — так же резко, как и выросла.

Именно поэтому ваша собственная VPS может ничего не делать в этот момент, а сеть всё равно «проседает»: проблема не в вашей машине, а в общей трубе. Похожий кейс с другой стороны — когда чужая нагрузка выключает канал полностью, а не только повышает задержку — разобран в статье про соседа по гипервизору, который положил канал.

Нужен сервер под эту задачу?

Разверните VPS MAATRIX за пару минут: NVMe, AMD EPYC, root-доступ, локации UK, США, Франция и РФ. Оплата картой РФ и по СБП.

Арендовать сервер

Первым делом проверяем себя: собственный cron и автоматизацию

Прежде чем подозревать соседей, нужно исключить куда более вероятный вариант — что регулярная нагрузка исходит от вас самих. Совпадение по времени с собственным заданием — самая частая причина «загадочных» ночных провалов, и её проверка занимает пять минут.

Смотрим системный cron и cron конкретных пользователей:

# cron текущего пользователя и root
crontab -l
sudo crontab -l -u root

# cron всех пользователей системы разом
for u in $(cut -d: -f1 /etc/passwd); do
  echo "=== $u ==="
  crontab -l -u "$u" 2>/dev/null
done

# системные каталоги cron
cat /etc/crontab
ls -la /etc/cron.d/ /etc/cron.daily/ /etc/cron.hourly/

Отдельно проверяем systemd-таймеры — на современных дистрибутивах регулярные задачи всё чаще живут там, а не в cron:

systemctl list-timers --all
# для конкретного таймера — точное расписание
systemctl cat backup.timer

И заглядываем в планировщики самого приложения — они часто остаются вне поля зрения, потому что живут внутри контейнера или фреймворка, а не в системном cron:

# Celery beat, если используется
celery -A myapp inspect scheduled

# запланированные задачи внутри Docker-контейнеров
docker ps --format '{{.Names}}' | xargs -I{} docker exec {} sh -c 'crontab -l 2>/dev/null; echo ---'

Если ни один из этих источников не даёт задачу около 03:15 — это важный отрицательный результат: он не объясняет проблему, но резко сужает круг подозреваемых. Как методично проверять расписание собственных задач и не путать «тихий сбой» с чужой нагрузкой, подробно разобрано в статье про cron, который не отработал ночью.

Идеальная регулярность — подпись расписания, а не случайность

Случайные сбои — деградация линка у провайдера, флап BGP-маршрута, кратковременная перегрузка магистрального оператора — почти никогда не повторяются с точностью до минуты много ночей подряд. У них рваная картина: то в час ночи, то в четыре. А вот запланированная задача — cron, systemd-таймер, встроенный планировщик backup-агента — по определению стартует в одно и то же время с точностью, которую даёт системные часы.

Поэтому резкий фронт роста задержки, плато потерь пакетов и такой же резкий спад обратно — а не постепенное нарастание и медленное затухание — сильный аргумент в пользу гипотезы «где-то на этой инфраструктуре стартует и заканчивается ресурсоёмкая задача по расписанию». Плавная деградация больше похожа на органический рост нагрузки (дневной трафик реальных пользователей); резкий скачок и такой же резкий спад — на включение и выключение конкретного процесса.

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

#!/bin/bash
# ping_watch.sh — непрерывный лог RTT и потерь с таймстампом
LOGFILE=/var/log/ping_watch.log
TARGET=8.8.8.8   # или адрес вашего апстрим-шлюза

while true; do
  ts=$(date '+%Y-%m-%d %H:%M:%S')
  result=$(ping -c 1 -W 1 "$TARGET" 2>&1)
  rtt=$(echo "$result" | grep -oP 'time=\K[0-9.]+' )
  loss=$(echo "$result" | grep -c '1 packets transmitted, 0 received')
  echo "$ts rtt=${rtt:-timeout} loss=${loss}" >> "$LOGFILE"
  sleep 1
done

Запускаем как systemd-сервис или через nohup, оставляем на несколько ночей, потом смотрим срез именно на интересующий интервал:

grep "03:1" /var/log/ping_watch.log | less

Для более информативной картины полезнее mtr в режиме отчёта — он показывает задержку и потери отдельно по каждому хопу маршрута, что помогает отличить проблему именно на стороне узла провайдера от проблемы где-то дальше в сети:

mtr --report --report-cycles 100 --interval 1 8.8.8.8 > /var/log/mtr_0315.log

Если этот отчёт запущен вручную именно в проблемное окно, по нему обычно видно: деградация начинается уже на первом-втором хопе (шлюз узла провайдера), а не в середине маршрута у транзитных операторов — довод в пользу локальной проблемы на стороне узла, а не в интернете вообще. Общая методика таких замеров разобрана в статье как измерить реальный пинг до сервера; а если разовый ping ничего не показывает, а нагрузка всё равно скачет — стоит прочитать про потерю пакетов, которой не видно в обычном ping.

Обращение в поддержку хостинга: что писать и что ответили

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

  • ID виртуальной машины и/или узла (node), если он виден в панели управления;
  • точное окно деградации на нескольких датах подряд, с часовым поясом;
  • характер деградации — рост RTT в разы, появление packet loss, а не общие слова;
  • прикреплённые графики из мониторинга и/или лог ping_watch.sh / mtr за эти окна;
  • прямой вопрос: наблюдается ли на этом физическом узле в указанное время аномальная нагрузка от других клиентов, и возможна ли миграция VPS на менее загруженный узел.

Пример текста обращения:

Тема: Регулярная деградация сети каждую ночь в 03:15-03:17 (UTC+3), VM #XXXXX

Добрый день. N ночей подряд (список дат) в окне 03:15-03:17 по времени
сервера наблюдаем резкий рост RTT до внешних узлов от базового уровня
и появление packet loss (точные цифры и графики — во вложении из
собственного mtr/ping-лога). Собственные cron/systemd-таймеры и
планировщики приложений на это время не назначены — проверено и
исключено. Деградация начинается уже на первом хопе от нашей VM, что
указывает на сторону узла/аплинка, а не на маршрут дальше в сети.

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

В подтверждённых подобных случаях реакция поддержки обычно выглядит так: инженеры поднимают статистику загрузки аплинка узла за указанные даты и видят, что именно в этом окне резко растёт исходящий трафик от одной конкретной VM другого клиента — характер нагрузки (равномерный, продолжительный, большой объём) соответствует профилю полного сетевого бэкапа во внешнее хранилище, а не пиковому веб-трафику. Дальше провайдер либо связывается с этим клиентом и просит перенести расписание задачи, либо ограничивает его полосу через traffic shaping, либо предлагает мигрировать вашу VM на менее загруженный узел — в зависимости от внутренней политики.

Корневая причина: «шумный сосед» и что делать дальше

Итоговый диагноз в такой истории — классический noisy neighbor («шумный сосед»): эффект на разделяемой инфраструктуре, при котором интенсивная нагрузка одного арендатора общего физического ресурса ощутимо ухудшает работу всех остальных, даже если они сами ничего аномального не делают. Один узел — одна физическая труба на всех, и без явного QoS от провайдера никто не гарантирует, что чужой бэкап не заберёт себе большую часть полосы именно тогда, когда он запущен.

Что можно сделать в зависимости от того, насколько сервис критичен к стабильности сетевой задержки:

ВариантКогда имеет смыслЧто решает
Migration на другой узел того же провайдераБюджет ограничен, деградация не критична для бизнеса, разовый случайУбирает конкретного соседа, но не гарантирует, что новый узел свободен от той же проблемы
Запрос к провайдеру ограничить/перенести соседаПровайдер отзывчив, проблема подтверждена логамиУстраняет причину напрямую, но зависит от готовности провайдера работать с чужим клиентом
Переход на выделенный сервер (dedicated)Задержка критична для бизнеса (трейдинг, real-time API, VoIP, игровые серверы), бюджет позволяетФизический аплинк не делится вообще ни с кем — класс проблемы исчезает полностью
Постоянный мониторинг сетевой задержки как отдельной метрикиВсегда, независимо от выбранного вариантаЛовит повторение проблемы или её появление на новом узле на раннем этапе

Если сервис чувствителен к сетевой задержке — торговые алгоритмы, VoIP, real-time многопользовательские игры, API с жёсткими SLA по времени ответа — единственное решение, убирающее саму возможность подобного эффекта, а не смягчающее его, это переход на выделенный сервер, где физический сетевой канал не делится ни с кем. Разница между этими моделями и признаки, что пора мигрировать с VPS на dedicated, разобраны в статье выделенный сервер против VPS: когда пора переезжать.

Если переход на выделенный сервер пока не по бюджету, работает и более лёгкий путь: попросить провайдера ограничить/перенести шумного соседа либо смигрировать вашу VM на менее загруженный узел — многие делают это бесплатно по обоснованному запросу с конкретными логами.

Отдельная рекомендация вне зависимости от выбранного пути: заведите сетевую задержку как метрику мониторинга первого класса, наравне с CPU и памятью, а не как то, что проверяется руками при жалобах пользователей. Свои CPU и память были в норме — поэтому проблему заметили не сразу, а по жалобам с задержкой. Постоянный ICMP/TCP-пробинг с алертом на превышение порога задержки или появление потерь — через blackbox_exporter с Prometheus и Grafana, или через smokeping — ловит такие внешние эффекты автоматически, а не постфактум.

Нужен сервер под эту задачу?

Разверните VPS MAATRIX за пару минут: NVMe, AMD EPYC, root-доступ, локации UK, США, Франция и РФ. Оплата картой РФ и по СБП.

Арендовать сервер

Нужны сами нейросети для контента?

Генерируйте изображения, видео и озвучку нейросетями на falapi.io — десятки моделей в одном окне. Оплата картой РФ и по СБП.

Частые вопросы

Почему CPU и память у меня в норме, а сеть всё равно проседает?

Потому что причина не в вашей VM, а в разделяемом физическом канале узла. Нагрузку на CPU/память гипервизор изолирует между арендаторами куда строже, чем сетевой трафик, если провайдер не настроил отдельный QoS на сеть.

Как отличить шумного соседа от проблемы у моего апстрим-провайдера интернета?

Смотрите, где именно на маршруте начинается деградация: если она видна уже на первом-втором хопе (шлюз узла провайдера) через mtr, а дальше по маршруту всё чисто, — вероятнее локальная проблема на узле. Если деградация появляется в середине маршрута у транзитных операторов — это, скорее, внешняя сетевая проблема, не связанная с соседями по узлу.

Провайдер отказывается признавать проблему — что делать?

Присылайте не жалобу, а конкретные данные: точное время, длительность, характер деградации (RTT/loss), логи mtr/ping за несколько ночей подряд. Без цифр большинство обращений закрывают формальной отпиской «у нас всё в порядке».

Поможет ли просто более дорогой тариф VPS у того же провайдера?

Не обязательно — более дорогой тариф часто означает больше vCPU и RAM, но не гарантирует отдельный физический аплинк. Уточняйте у провайдера явно, включает ли тариф гарантированную полосу (guaranteed bandwidth) или только «до» (up to), и рассматривайте выделенный сервер, если гарантия важна.

Стоит ли переезжать на выделенный сервер сразу после одного такого случая?

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

Обсудить статью, задать вопрос или начать новую тему

Есть вопрос по этой статье, идея для обсуждения или просто хотите поделиться опытом? Сообщество MAATRIX ждёт. Для общения, пожалуйста, зарегистрируйтесь в нашем личном кабинете.

Перейти в сообщество →