Карточка кейса
| Параметр | Значение |
|---|---|
| Тип проекта | Собственный внутренний сервис |
| Процесс | Диагностика доступности клиентских сайтов |
| Проблема | Сайты периодически не открывались у части пользователей, но серверные данные не объясняли причину |
| Решение | Центральное приложение и точки наблюдения в разных географических и сетевых сегментах |
| Первая рабочая версия | Два дня, затем несколько итераций на реальных данных |
| Роль | Постановка задачи, архитектура, разработка, развертывание и эксплуатация |
| Статус | Рабочая MVP-система |
1. Сайт мог работать на сервере и оставаться недоступным для клиента
Первоисточником проекта стала серия жалоб.
Сначала один клиент сообщил, что его сайт не открывается. В это же время сайт отвечал из другой сети и нормально отдавал контент.
Через несколько дней похожая ситуация возникла у другого клиента из другого региона. Затем начали появляться новые случаи с другими сайтами.
Недоступность могла продолжаться некоторое время, а затем исчезать без изменений в приложении или конфигурации сервера.
Самым важным наблюдением было отсутствие следов проблемных обращений. Если клиент видел ошибку запроса, соответствующего посещения могло не быть:
- в access logs;
- в error logs;
- в системе веб-аналитики.
Запрос, вероятно, не доходил до веб-сервера. Но по данным самого сервера определить место сбоя было невозможно.
Сайты сопровождались одним специалистом, без отдельной команды эксплуатации. Поэтому решение должно было не создавать новый сложный процесс, а давать понятные данные для самостоятельной диагностики.
2. Одной проверки было недостаточно
Проверка сайта со своего компьютера отвечала только на один вопрос:
Открывается ли сайт из этой сети прямо сейчас?
Она не объясняла, что происходит у клиента в другом регионе или у другого интернет-провайдера.
Проверка через VPN также не давала надежной картины. В таком случае запрос идет через инфраструктуру VPN-провайдера и показывает доступность из его сети, а не обязательно из той сети, где возникла проблема.
На старте было несколько возможных объяснений:
- сбой приложения или веб-сервера;
- проблема конкретного хостинга;
- ошибка DNS или TLS;
- нарушение маршрутизации;
- проблема интернет-провайдера;
- региональная фильтрация трафика;
- локальная проблема на стороне пользователя.
Одной из гипотез была связь с действиями Роскомнадзора и возможным расширением тестирования ограничений на проводной интернет.
Однако отдельные жалобы и отсутствие запросов в серверных логах не доказывали эту гипотезу. Для вывода требовались независимые наблюдения, выполненные в одно и то же время из разных сетей.
3. Нужно было не угадать причину, а сузить область поиска
Цель системы состояла не в автоматической постановке диагноза.
Нужно было собирать данные, по которым можно определить следующий шаг:
- проверять сервер и приложение;
- изучать инфраструктуру хостинга;
- сравнивать маршруты;
- проверять конкретный регион или сеть;
- искать общее между несколькими сайтами.
Минимально полезный результат должен был позволять:
- проверять сайты из нескольких независимых точек;
- видеть точное время каждого события;
- различать HTTP- и сетевые ошибки;
- сравнивать результаты разных регионов;
- сохранять историю для последующего анализа;
- замечать одновременные события на нескольких сайтах.
Система не должна была объявлять причину доказанной на основании одной неудачной проверки. Ее задача — превратить отдельные жалобы в сопоставимые наблюдения.
4. Решение должно было оставаться небольшим
Проект создавался для ограниченного рабочего контура:
- один оператор;
- небольшой список сайтов;
- несколько уже доступных серверов в разных странах;
- одна проверка в минуту;
- один центральный VPS;
- отсутствие необходимости в публичном SaaS;
- минимальная нагрузка на проверяемые сайты;
- простой и воспроизводимый запуск.
Отдельным ограничением был тип точек наблюдения. В первой версии использовались серверы дата-центров.
Они позволяют сравнивать страны, сети и маршруты, но не полностью воспроизводят поведение:
- мобильного интернета;
- домашнего подключения;
- конкретного регионального провайдера;
- residential-сети.
Поэтому PING может показать характер распределения проблемы, но не всегда способен установить конкретного участника сетевого ограничения.
5. Готовые решения не давали нужного уровня контроля
| Вариант | Преимущества | Ограничения | Решение |
|---|---|---|---|
| Ручные проверки | Не требуют разработки | Нет истории, результат зависит от текущей сети и момента проверки | Не подходит |
| VPN | Позволяет быстро менять страну выхода | Показывает инфраструктуру VPN-провайдера и может искажать маршрут | Только как вспомогательный инструмент |
| Готовый SaaS | Быстрый старт, готовые уведомления и интерфейс | Меньше контроля над конкретными точками, маршрутом и классификацией ошибок | Не выбран для MVP |
| Тяжелая monitoring-платформа | Большой набор метрик и интеграций | Избыточная инфраструктура для одного оператора и небольшого списка сайтов | Не выбрана |
| Собственная система | Контроль точек, данных и правил проверки | Нужно разработать и развернуть центральный сервис и исполнителей | Выбрана |
Критерием выбора была не максимальная функциональность, а минимально достаточная архитектура.
Уже имеющиеся серверы можно было использовать как независимые источники данных. Поэтому небольшой собственный сервис оказался рациональнее, чем адаптация большой платформы мониторинга.
6. Проверки были вынесены в независимые точки наблюдения
Система состоит из центрального приложения и нескольких точек наблюдения.
Точка наблюдения — небольшой сервис, установленный на отдельном сервере. В коде такой компонент называется probe, но в пользовательском описании используется функциональное русское название.
Сайты клиентов
▲
│ HTTP GET
│
┌────────────┼────────────┐
│ │ │
┌────────────┐ ┌────────────┐ ┌────────────┐
│ Россия │ │ Европа │ │ США │
│ │ │ │ │ │
│ Точка │ │ Точка │ │ Точка │
│ наблюдения │ │ наблюдения │ │ наблюдения │
└──────┬─────┘ └──────┬─────┘ └──────┬─────┘
│ │ │
└───────────────┼──────────────┘
│ HTTPS
▼
┌─────────────────────────┐
│ Центральное приложение │
│ │
│ API конфигурации │
│ API результатов │
│ Классификация ошибок │
│ Dashboard │
└────────────┬────────────┘
│
▼
┌──────────┐
│ SQLite │
│ История │
└──────────┘
Центральное приложение
Центральный сервис размещен на VPS в России.
Он:
- хранит список сайтов и точек наблюдения;
- передает актуальную конфигурацию;
- принимает результаты проверок;
- хранит историю;
- формирует данные для dashboard;
- удаляет сырые результаты старше 90 дней.
Backend реализован на FastAPI. Для хранения данных в масштабе MVP используется SQLite.
Точки наблюдения
Основные точки были развернуты:
- в России;
- в Нидерландах как европейская точка;
- в США.
Каждая точка самостоятельно выполняет проверки из своей локальной сети. Входящие соединения ей не требуются: вся связь инициируется в сторону центрального API.
Такой подход позволяет сравнивать не виртуально выбранную страну, а фактический результат с конкретного сервера и сетевого маршрута.
7. Каждая проверка превращается в структурированное событие
- Точка наблюдения получает с центрального сервера список активных сайтов.
- Конфигурация сохраняется локально.
- Каждые 60 секунд выполняется HTTP
GET. - Редиректы не выполняются автоматически.
- Чтение тела ответа ограничивается, чтобы не скачивать страницу полностью.
- Результат классифицируется по детерминированным правилам.
- Данные отправляются в центральное приложение.
- Central сохраняет их в SQLite.
- Dashboard объединяет результаты разных точек на одной временной шкале.
Результаты делятся на группы:
| Группа | Что произошло |
|---|---|
2xx |
Сайт вернул успешный HTTP-ответ |
3xx |
Получен редирект |
4xx |
Сервер вернул клиентскую HTTP-ошибку |
5xx |
Сервер или upstream вернул серверную ошибку |
network_error |
Возникла DNS-, TLS-, connection-ошибка или timeout |
probe_error |
Ошибка возникла внутри точки наблюдения или ее конфигурации |
Если HTTP-ответ получен, сохраняется точный статус. Если ответ не был получен, сохраняется тип сетевой ошибки.
Ответ 503 означает, что запрос дошел до HTTP-уровня. DNS-ошибка или timeout означают, что сбой произошел раньше и запрос мог вообще не попасть в логи сайта.
8. Почему здесь не понадобился AI
AI в основной логике PING не используется.
Система работает со структурированными и проверяемыми данными:
- HTTP-код;
- тип исключения;
- время ответа;
- идентификатор точки;
- время проверки.
Для этих данных нужна точная и повторяемая классификация.
Ответ 503 должен каждый раз попадать в 5xx. Timeout должен каждый раз считаться сетевой ошибкой. Вероятностная модель не повысила бы точность такого процесса, но добавила бы недетерминированность и новый источник отказа.
Поэтому была выбрана обычная детерминированная логика.
AI можно использовать поверх собранных данных — например, для подготовки текстового резюме инцидента. Но он не должен заменять первичные измерения и правила их классификации.
9. Система продолжает наблюдение даже без связи с центром
Важным архитектурным решением стало разделение двух процессов:
- выполнение проверки;
- доставка результата.
Если центральный API временно недоступен, точка наблюдения не прекращает работу.
Она использует сохраненную конфигурацию и складывает неотправленные результаты в локальную очередь. После восстановления связи накопленные данные отправляются на центральный сервер.
Это предотвращает ситуацию, когда сбой самого PING создает искусственный пробел в наблюдениях за всеми сайтами.
Компактный стек
| Слой | Решение |
|---|---|
| Центральный API | FastAPI |
| Хранилище MVP | SQLite |
| Интерфейс | Server-rendered HTML, Jinja2 |
| Точки наблюдения | Легковесный Python-сервис |
| Запуск | Docker Compose |
| Внешний доступ | Nginx и HTTPS |
| Проверки качества | Pytest и ручные runtime-проверки |
Технологии выбирались после определения процесса и масштаба.
SQLite позволил не добавлять отдельный сервер базы данных. Docker Compose сделал запуск компонентов воспроизводимым. Server-rendered интерфейс закрыл операторский сценарий без отдельного frontend-приложения.
10. Полнота данных сначала мешала их читать
Первая версия dashboard показывала нужную информацию, но полный дневной график с минутными проверками нескольких точек быстро становился плотным.
Проект создавался без отдельного визуального прототипа, поэтому интерфейс дорабатывался уже на реальных данных.
За несколько итераций были добавлены:
- выбор участка дня;
- отдельные серии для точек наблюдения;
- фильтры точек и групп статусов;
- среднее время ответа;
- uptime и покрытие данных;
- отметка устаревших результатов;
- компактная таблица деталей;
- навигация по датам и страницам.
Задача этих изменений состояла не в украшении dashboard, а в сокращении времени между обнаружением события и пониманием его характера.
Архитектура интерфейса при этом не усложнялась. Проект сохранил server-rendered подход без перехода на SPA или отдельную библиотеку графиков.
Отдельное практическое ограничение проявилось при обновлениях production через нестабильное SSH-соединение. Файлы сначала загружались в промежуточную область и проверялись до замены рабочей версии.
Канал доставки также является частью надежности системы, но подробная история развертывания в кейсе не требуется.
11. Два сайта одного хостинга показали разные сценарии
Одним из первых показательных эпизодов стали два клиентских сайта одного хостинг-провайдера.
Они находились на разных серверах, но периодические проблемы наблюдались у обоих.
Первый сайт: ошибки из всех точек
Для первого сайта доля успешных проверок была близкой во всех трёх регионах:
| Точка наблюдения | Получено проверок | Успешные 2xx |
Сетевые ошибки | Uptime |
|---|---|---|---|---|
| Москва | 544 | 457 | 87 | 84,0% |
| Амстердам | 522 | 434 | 88 | 83,1% |
| Нью-Йорк | 497 | 413 | 84 | 83,1% |
| Общий показатель | — | — | — | 83,4% |
Примерно каждая шестая проверка завершалась сетевой ошибкой независимо от региона.
Такая картина не была похожа на локальную проблему одного российского или зарубежного провайдера. Возможную причину нужно было искать в общей для всех маршрутов части: инфраструктуре сайта, сервере, подсети, TLS-конфигурации или хостинге.
Второй сайт: Россия без ошибок, зарубежные точки — с потерями
У второго сайта распределение было другим:
| Точка наблюдения | Получено проверок | Успешные 2xx |
Сетевые ошибки | Uptime |
|---|---|---|---|---|
| Москва | 544 | 544 | 0 | 100,0% |
| Амстердам | 522 | 454 | 68 | 87,0% |
| Нью-Йорк | 497 | 436 | 61 | 87,7% |
Из российской точки сайт отвечал во всех полученных проверках. В зарубежных точках около 12–13% запросов завершались сетевой ошибкой.
Один хостинг и похожий характер ошибок могли указывать на общую инфраструктурную проблему. Но разное географическое распределение показывало, что сайты нельзя объединить в один простой сценарий:
- у первого ошибки возникали из всех трёх точек;
- у второго российский маршрут работал стабильно, а зарубежные — нет;
- сайты размещались на разных серверах одного кластера.
Без независимых точек наблюдения обе ситуации выглядели бы одинаково: «сайт иногда не открывается».
12. Ответ поддержки связал проблему с ECH
Собранные данные были переданы в техническую поддержку SpaceWeb.
В ответе поддержка сообщила:
19.06 в 15:30 МСК мы отключили протокол ECH на всём кластере серверов, чтобы устранить ошибку с недоступностью сайтов у клиентов. Теперь сайт должен загружаться стабильнее.
После отключения ECH новые проблемные события перестали поступать.
Это важный результат по двум причинам.
Во-первых, первоначальная гипотеза о действиях Роскомнадзора не подтвердилась как основная причина данного эпизода. Проблема оказалась связана с конфигурацией на стороне хостинг-провайдера.
Во-вторых, отсутствие запросов в логах сайта получило технически правдоподобное объяснение: соединение завершалось до того, как HTTP-запрос доходил до веб-сервера.
При этом PING не определил ECH автоматически. Система выполнила другую задачу:
- зафиксировала масштаб проблемы;
- показала долю сетевых ошибок;
- разделила результаты по регионам;
- позволила сравнить два сервера одного хостинга;
- сохранила историю до и после изменения;
- дала данные для предметного обращения в поддержку.
Именно поддержка хостинга назвала конкретное изменение в инфраструктуре.
13. Вместо отдельных жалоб появилась история наблюдений
PING не определяет причину инцидента автоматически. Он формирует матрицу фактов, которая помогает выбрать направление дальнейшей проверки.
| Наблюдение | Что стоит проверять |
|---|---|
5xx одновременно из всех точек |
Приложение, сервер, upstream или хостинг |
| Сетевая ошибка одновременно из всех точек | Сервер, сеть хостинга, DNS или TLS |
| Ошибка только из одной точки | Сеть, маршрут или инфраструктура этой точки |
| Ошибки только из российских точек | Региональная маршрутизация или сетевые ограничения |
| Ошибки только из зарубежных точек | Международные маршруты, фильтрация или инфраструктура хостинга |
| Ошибки у нескольких сайтов одного провайдера | Общая инфраструктура, кластер или сеть хостинга |
| Ошибка самой точки наблюдения | Состояние исполнителя, а не сайта |
Это не таблица готовых диагнозов. Одна и та же картина может иметь несколько объяснений. Но область поиска становится значительно уже.
Измеримые параметры
В рабочей версии:
- сайты проверяются каждые 60 секунд;
- сырые результаты хранятся 90 дней;
- основной контур включает точки в России, Европе и США;
- один из сайтов в проблемный период показал общий uptime 83,4%;
- у второго сайта российская точка показала 100%, а зарубежные — 87,0% и 87,7%;
- после изменения на стороне хостинга новые сетевые ошибки перестали наблюдаться.
Точные показатели сокращения времени диагностики не собирались. Поэтому экономический эффект не выражается в неподтвержденных процентах.
Качественные изменения
До появления PING основными источниками были:
- жалоба клиента;
- ручная проверка;
- серверные логи;
- данные веб-аналитики.
Если запрос не доходил до сервера, эта картина оставалась неполной.
После запуска системы появилась независимая история:
- из какой точки выполнялась проверка;
- в какой момент произошла ошибка;
- был ли получен HTTP-ответ;
- какой тип сетевой ошибки возник;
- сколько точек увидели проблему одновременно;
- затронула ли она другие сайты;
- как изменилось состояние после действий провайдера.
Ответ «у меня открывается» перестал быть единственным доступным контраргументом к жалобе клиента.
14. Первая версия не пыталась воспроизвести весь интернет
В MVP осознанно не вошли:
- проверки из мобильных сетей;
- residential- и ISP-specific точки;
- Telegram- и email-уведомления;
- клиентские кабинеты;
- публичная регистрация;
- управление сайтами через интерфейс;
- browser automation;
- проверка JavaScript-сценариев;
- многошаговые пользовательские проверки;
- автоматическое устранение проблем;
- автоматическая постановка окончательного диагноза.
Эти функции увеличили бы объем проекта, но не были обязательны для проверки основной гипотезы: можно ли получить полезную диагностическую картину из нескольких независимых источников.
15. Следующая версия должна приблизить наблюдение к реальным пользователям
Главное ограничение текущей архитектуры — точки в дата-центрах.
Чтобы точнее исследовать проблемы проводного и мобильного интернета, нужны дополнительные источники:
- серверы или устройства у разных российских провайдеров;
- residential-сети;
- мобильные подключения;
- точки в отдельных регионах.
Второе направление — формальные правила инцидентов.
Одиночный timeout не должен автоматически создавать тревогу. Уведомление имеет смысл, если учитываются:
- несколько последовательных ошибок;
- количество затронутых точек;
- сочетание HTTP- и сетевых статусов;
- продолжительность события;
- свежесть данных.
Третье направление — корреляция сайтов по инфраструктуре. Связь с хостингом, сервером, кластером и регионом размещения позволит быстрее замечать общие события.
Переход с SQLite на PostgreSQL нужен не сам по себе, а после достижения измеримых порогов: роста базы, увеличения числа точек или замедления dashboard-запросов.
16. Наблюдение должно находиться вне проверяемой системы
Состояние сервера не равно доступности сайта для пользователя.
Приложение может работать, процесс — быть запущен, а внутренняя метрика — оставаться зеленой. Если соединение завершается раньше, сервер об этом ничего не узнает.
Поэтому диагностика доступности требует внешних и независимых источников.
Для небольшого рабочего контура не понадобилась тяжелая observability-платформа. Центрального приложения, SQLite и нескольких легковесных точек наблюдения оказалось достаточно, чтобы превратить разрозненные жалобы в структурированные данные.
Первый реальный инцидент показал практическую ценность такого подхода. Два сайта одного хостинга имели сетевые ошибки, но их географическое распределение заметно различалось. Данные позволили передать провайдеру не общую жалобу, а измеримую картину.
Поддержка связала проблему с ECH и отключила его на всём кластере. После этого новые ошибки перестали поступать.
Главный результат проекта — не график и не набор HTTP-проверок.
Результатом стала наблюдаемость там, где раньше оставалась только неопределенность.
Системный разбор разделил задачу на независимые точки наблюдения, центральное хранение, правила интерпретации событий и будущие ограничения. Поэтому систему можно развивать по частям: добавлять новые регионы, уточнять правила инцидентов и менять хранилище без полной переделки логики проверок.
Темы и технологии
- Проблема
- Решение
- Архитектура
- Технологии
Что дальше?
Сайт работает на сервере, но периодически не открывается у части клиентов? Опишите, какие данные уже собираются и откуда выполняются проверки. Это поможет определить, каких точек наблюдения не хватает и какой первый шаг будет разумным.