Один и тот же сайт в одну и ту же минуту открывается у знакомого в Казани, у коллеги в Берлине и не открывается у клиента в третьем городе. В чате появляется короткое «у вас упало». Формально это сообщение — наблюдение, но в нём нет трёх вещей, без которых его нельзя проверить: времени, адреса, по которому шёл запрос, и этапа, на котором что-то пошло не так. Вопрос «он упал?» требует уточнения: откуда, когда и на каком шаге?

Две точки проверки на отдельных серверах нужны именно для того, чтобы на это уточнение отвечали записи, а не память и догадки. Но две точки — не волшебный прибор. Они дают два ряда наблюдений, и польза от них зависит от того, насколько эти ряды сопоставимы. Ниже разберём, что должна записывать каждая точка, как разделить запрос на этапы, как читать расхождения между Россией и Европой и где «независимость» оказывается кажущейся.

Начинаем с наблюдения, а не с диагноза

Точка проверки — это маленькая программа на сервере в определённом регионе, которая по расписанию делает запрос к вашему сайту и сохраняет результат. Главная ошибка начинающего — сохранять только вердикт: «ок» или «не ок». Вердикт — это вывод, а вывод зависит от порогов и настроек. Через неделю никто не вспомнит, был ли таймаут пять секунд или десять и какой именно адрес вернул DNS.

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

  • Время начала в UTC с точностью до секунды и идентификатор прогона. Местное время сервера в записях ни к чему: у двух точек оно будет разным.
  • Идентификатор точки и её регион в том виде, как вы его себе задали, например «ru-1» и «fr-1».
  • Имя, которое запрашивалось, и IP-адрес, в который оно превратилось. Это единственный способ позже увидеть, что две точки ходили не в одно и то же место.
  • Тип запроса: только установление соединения, запрос главной страницы, запрос служебного адреса здоровья, сценарий в браузере. Это разные проверки, и смешивать их в одном графике нельзя.
  • Результат по каждому этапу: прошёл или нет, сколько заняло и какая ошибка.
  • Версию самой проверки: если вы поменяли таймаут или заголовки, график до и после перестаёт быть одним рядом.

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

Запрос — это не одно событие, а четыре

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

Этапы запроса и то, что о них говорит сбой
ЭтапКак выглядит сбойЧто это может означатьЧего это не доказывает
DNSимя не разрешилось, разрешилось с задержкой или в другой адреспроблема у резолвера точки, у DNS-сервера домена, разные ответы для разных регионовчто сайт недоступен: приложение при этом может работать
Соединениетаймаут при установлении TCP-соединения или отказмаршрут до адреса, фильтрация на пути, перегруженный или закрытый порт на стороне серверапричину: молчание на этом шаге выглядит одинаково при разных поломках
TLSошибка рукопожатия, неверный сертификат, обрыв посреди обменапросроченный или неверный сертификат, несовместимые настройки, вмешательство на путичто приложение сломано: до него запрос ещё не дошёл
Ответ приложениякод 5xx, долгое ожидание первого байта, обрыв при чтении тела, неверное содержимоесбой самого приложения, прокси, базы данных или upstreamчто проблема региональная: если ошибка у обеих точек, она скорее общая

Смысл разделения в том, что на разных этапах «виноваты» разные участки. Если у французской точки всё прошло, а у российской соединение не установилось, то вопрос о приложении даже не возникает: запрос до него не добрался. Если же обе точки получили ответ 502 после успешного TLS, региональный путь тут ни при чём, и разбираться нужно с самим сайтом.

Ответ приложения тоже делится на две части

Последний этап стоит разрезать ещё раз: время до первого байта ответа и время получения всего тела. Страница может начать отвечать быстро и застрять на середине, а может долго «думать» и затем отдать всё сразу. Для диагностики это разные симптомы.

Здесь полезно помнить, как ведёт себя обратный прокси перед приложением. В документации nginx сказано, что при включённой буферизации ответа upstream сервер сначала накапливает данные, а при выключенной передаёт их клиенту по мере получения; поведение можно менять и заголовком ответа X-Accel-Buffering, если конфигурация это не запрещает (nginx: HTTP proxy module). Для проверки это значит следующее: «время до первого байта» у потокового ответа и у буферизованного означает разное. В первом случае вы видите, когда приложение начало отвечать, во втором — примерно когда оно закончило. Если вы сравниваете две точки, убедитесь, что они обращаются к адресу с одинаковой схемой буферизации, иначе различие во времени окажется свойством конфигурации, а не сети.

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

Одинаковые запросы и одни часы

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

  • тот же адрес и тот же путь, те же заголовки, включая User-Agent и Host;
  • та же политика редиректов: следовать или нет, и до какого предела;
  • те же таймауты по этапам и тот же общий дедлайн;
  • то же условие успеха: код ответа и, например, наличие конкретной строки в теле;
  • тот же интервал и расписание запуска.

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

Время: зачем синхронизировать часы

Две точки записывают результаты с метками времени своих серверов. Если часы расходятся на десятки секунд, а интервал проверки — минута, вы начнёте сопоставлять не те наблюдения. Условный пример: обе точки проверяют раз в 60 секунд, у российской часы отстают на 25 секунд. Сбой, который у европейской точки зафиксирован в 12:00:10, у российской по её метке «12:00:00» — и вы решаете, что она увидела его раньше или одновременно, хотя на деле позже. Для разбора инцидента порядок событий важнее абсолютных значений, и он ломается первым.

Практически нужны две вещи. Во-первых, на обоих серверах работает синхронизация времени, и вы раз в какое-то время смотрите на её состояние. Во-вторых, в записи сохраняется не только метка с точки, но и метка приёма на стороне, куда результаты собираются: по разнице видно, не уплыли ли часы. Сравнивать наблюдения стоит по окнам, а не по точным секундам: «в окне с 12:00 до 12:02 по UTC европейская точка получила ответ, российская — таймаут соединения». Окно шире, чем интервал проверки, и потому устойчивее к небольшой разнице в часах.

Что значат разные результаты двух регионов

Теперь у нас две точки, одинаковые запросы и общая шкала времени. Возможны четыре комбинации, и у каждой есть соблазн слишком быстрого вывода.

Обе точки получили успех

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

Обе точки получили сбой на одном и том же этапе

Если и российская, и европейская точки получили 5xx после успешного TLS, дело почти наверняка в самом сервисе: приложение, база, upstream. Если обе не смогли разрешить имя, смотрите на DNS домена. Совпадение этапа у двух разных регионов — сильный признак общей причины, но не абсолютный: возможны два независимых сбоя одновременно, хоть и редко.

Сбой только у одной точки

Это тот самый интересный случай, ради которого всё затевалось. Предположим, европейская точка получила ответ, а российская — таймаут установления соединения. Вывод «в России заблокировали» был бы преждевременным. Таймаут на этапе соединения одинаково выглядит при потере пакетов на маршруте, при перегруженном или недоступном промежуточном узле, при фильтрации по адресу, при проблеме у хостинга самой точки. По одному таймауту нельзя отличить эти причины, и уж тем более по одному ping, который вообще мог не доходить по совсем другим причинам, чем ваш HTTPS-запрос. Обвинять регулятора, провайдера или собственное приложение на основе такого наблюдения нельзя.

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

  1. Сравнить разрешённые адреса. Если точки получили разные IP для одного имени, расхождение началось ещё на DNS, и дальнейшие этапы сравнивать бессмысленно: они ходили в разные места.
  2. Определить этап остановки. Таймаут соединения, обрыв при TLS и сброс после отправки запроса — три разных картины, хотя пользователь видит одну и ту же «не открывается».
  3. Проверить обратное направление. Достаёт ли сервер российской точки до других, заведомо рабочих сайтов? Если нет, неисправна сама точка.
  4. Повторить с другого адреса или другим способом, если это допустимо у вас по правилам, и записать результат отдельным наблюдением, не смешивая с основным рядом.
  5. Подождать повторения. Единичный провал в одном регионе — одно событие, а ряд провалов на протяжении двадцати минут — другое.

Результат такой работы — не «причина найдена», а перечень фактов: на каком этапе, с какого адреса, с каких точек и в какое окно возникло различие. Этого достаточно, чтобы поддержка передала жалобу дальше, а не гадала.

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

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

АРЕНДОВАТЬ СЕРВЕР

Когда независимость оказывается кажущейся

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

  • Общий резолвер. Если обе точки используют один публичный DNS-сервис, а он дал сбой, вы увидите «сайт недоступен из двух регионов», хотя сайт жив. Лучше явно задать резолвер каждой точки и записывать, какой использовался.
  • Общий код проверки с общей ошибкой. Если новая версия скрипта неверно разбирает ответ, обе точки одновременно начнут сообщать о сбое. Поэтому версия проверки фиксируется в записи, а обновление выкатывается сначала на одну точку.
  • Общее хранилище результатов и общий канал уведомлений. Если обе точки пишут в одну базу, лежащую на вашем же рабочем сервере, то при его падении вы потеряете и сайт, и наблюдателя. Если уведомления идут через один и тот же канал, молчание канала легко принять за тишину в мониторинге.
  • Общий адрес назначения. Обе точки идут на один и тот же балансировщик или CDN-узел. Это нормально, если вы проверяете именно публичный путь, но тогда зелёный результат говорит о нём, а не о каждом сервере за ним.
  • Общий провайдер или общая точка отказа в управлении. Два сервера у одного поставщика независимы ровно настолько, насколько независимы у него сеть и обслуживание. Нельзя заранее считать, что разные VPS стоят на разном оборудовании или дают отказоустойчивость; проверяйте условия размещения у конкретного провайдера, а для принципиально разных путей выбирайте разные локации.
  • Общее время. Если синхронизация обеих точек опирается на один и тот же источник и он врёт, ошибка будет одинаковой, и её не заметить, сравнивая точки между собой.

Отдельный вопрос — кто следит за самими точками. Если точка тихо умерла, на графике это выглядит как отсутствие записей, а не как сбой сайта. Хороший признак здоровья схемы — регулярный сигнал «я жива» от каждой точки и тревога, когда он пропал. Подробнее о том, как проверять сам мониторинг на живучесть, мы писали в материале «Проверка мониторинга на живучесть: кто сторожит сторожа».

Две точки на VPS: что и где разворачивать

Для такой схемы подходят два небольших сервера в разных локациях. В публичном предложении MAATRIX перечислены UK, US, RU и FR, а сам VPS — это NVMe, процессоры AMD EPYC и root-доступ, так что поставить собственную проверку и службу сбора можно без ограничений обычной общей площадки. Для задачи «Россия и Европа» естественная пара — сервер в RU и сервер в FR. Состав локаций и доступность конкретных образов проверяйте в форме заказа: одинаковое наличие всего во всех локациях ничем не подтверждено.

Сколько ресурсов нужно, зависит от того, что именно проверяет точка. Запрос по HTTPS раз в минуту — нагрузка ничтожная, и ей хватит самой маленькой конфигурации; в линейке это, например, Ba с 1 vCPU, 2 ГБ памяти и 40 ГБ NVMe. Всё иначе, если точка запускает сценарий в настоящем браузере: он существенно тяжелее, и ему уместно взять следующий тариф, например Uab с 2 vCPU и 4 ГБ. Но эти цифры — ориентир для старта, а не обещание ёмкости и не минимум: реальную потребность вы узнаете, только понаблюдав за загрузкой своего набора проверок.

Если проверка — сценарий в браузере

Простой запрос показывает, что сервер отвечает. Сценарий в браузере показывает, что страница реально работает: загрузилась, форма отправилась, нужная кнопка появилась. Для такого режима подходит Playwright, и его документация по запуску в CI даёт несколько практичных подсказок, применимых и к точкам мониторинга (Playwright: Continuous Integration).

Во-первых, документация советует начинать с одного worker ради воспроизводимости; параллельный запуск уместен на мощной собственной машине. Для нас это ещё один довод в пользу простоты: на небольшом VPS последовательный запуск даёт честные тайминги, а параллельные сценарии начнут соперничать за процессор и исказят время, причём по-разному на двух точках. Во-вторых, там описано разбиение набора тестов на части для разных CI-задач. Для двух точек это не нужно: каждая должна выполнять весь набор целиком, иначе наборы перестанут быть одинаковыми. В-третьих, у Playwright есть глобальный таймаут, по которому он сам завершает зависший прогон и успевает подготовить отчёт. Это как раз тот общий дедлайн, о котором мы говорили выше: зависшая проверка превращается в записанный результат «не уложились», а не в тишину.

Одинаковый сценарий на обеих точках и одинаковые таймауты по-прежнему обязательны, иначе мы вернёмся к сравнению разных вещей. Браузерные проверки полезно запускать реже простых: простая проверка отвечает на вопрос «жив ли путь», браузерная — «работает ли страница».

Как выглядит сводка двух точек

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

12:00 ru-1  dns=ok(203.0.113.10)  connect=timeout   tls=-    app=-
12:00 fr-1  dns=ok(203.0.113.10)  connect=ok        tls=ok   app=200
12:01 ru-1  dns=ok(203.0.113.10)  connect=timeout   tls=-    app=-
12:01 fr-1  dns=ok(203.0.113.10)  connect=ok        tls=ok   app=200
12:02 ru-1  dns=ok(203.0.113.10)  connect=ok        tls=ok   app=200
12:02 fr-1  dns=ok(203.0.113.10)  connect=ok        tls=ok   app=200

Что здесь можно утверждать? Обе точки получили один и тот же адрес, так что DNS не причина расхождения. У российской точки две минуты подряд не установилось соединение, у французской всё было нормально, на третьей минуте оба результата совпали. Утверждать, что это блокировка, нельзя. Нельзя и сказать, что «сайт работал», потому что одна точка его не достигла. Можно сказать ровно то, что записано: на этапе соединения в окне 12:00–12:01 UTC различие между точками было, потом пропало.

Теперь другой вариант: обе точки получили соединение и TLS, а потом по 502 в одно и то же окно. Здесь причина с большой вероятностью внутри сервиса, и разбор идёт по цепочке прокси, приложения и базы. Один и тот же вопрос «упал ли сайт?» в двух ситуациях получает разные ответы, причём из одних и тех же записей.

Сообщение для поддержки: факты вместо догадок

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

  1. Окно. Начало и конец в UTC и в местном времени клиента, если он указал город.
  2. Кто видел сбой и кто нет. Перечень точек с результатами по каждому этапу.
  3. Адрес. В какой IP разрешилось имя у каждой точки.
  4. Что не проверено. Например, что у нас нет наблюдения из сети конкретного оператора клиента.
  5. Что просим у клиента. Время обращения, адрес из сообщения об ошибке, способ подключения, и если возможно, результат запроса с другого канала связи.

Пример формулировки: «С 12:00 по 12:01 UTC проверка из точки в России не смогла установить TCP-соединение с адресом 203.0.113.10, проверка из Франции в то же время получила ответ 200; DNS у обеих точек вернул один адрес; с 12:02 обе точки получают 200. Наблюдений из сети клиента у нас нет». Такой текст не обвиняет и не оправдывает, он описывает.

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

Как расширять схему, не теряя ясности

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

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

И последнее: храните историю. Единичные региональные сбои без повторения кажутся мелочью, но на длинном отрезке по ним видно закономерности: сбои в одно и то же время суток, всегда у одного резолвера, всегда на одном этапе. Сырые записи занимают мало места, и хранить их полезнее, чем агрегированные проценты доступности, из которых этапы уже не восстановить.

Формулировка, которую можно проверить

Хорошая запись об инциденте в такой схеме похожа на показание свидетеля, а не на приговор: где (какая точка и какой адрес), когда (окно в UTC) и на каком этапе (DNS, соединение, TLS или ответ приложения) возникло различие и когда оно исчезло. Любой, кто откроет ваши записи, должен суметь воспроизвести это утверждение по сырым данным, не веря на слово.

Две точки, одинаковые запросы и одни часы не отвечают на вопрос «виноват регулятор, провайдер или приложение». Они делают более скромную и более полезную вещь: превращают «у кого-то не открывается» в точное «в 12:00–12:01 UTC соединение с этого адреса не устанавливалось из России и устанавливалось из Франции». Остальное — следующий шаг расследования, и его стоит делать, имея под рукой именно такую фразу.