Afina

Скачать приложение

AppleWindows
RU

WebSocket и локальные порты: как антифрод выявляет признаки среды

WebSocket timing attack и локальные порты антифрода

WebSocket локальные порты означают канал, через который сайт может косвенно оценить сервисы на localhost по времени ответа. Его используют, чтобы заметить открытые отладочные порты, локальные агенты, proxy-клиенты или следы автоматизации.

Для команд, которые работают с несколькими профилями, эта тема стоит рядом с проверкой WebRTC-утечек и UDP-поведения. Внешний IP и прокси могут выглядеть аккуратно, но браузер все равно остается процессом на локальной машине. Если страница видит косвенные признаки этой среды, цифровой отпечаток становится шире, чем Canvas, WebGL и User-Agent.

Именно поэтому WebSocket timing attack стоит рассматривать как часть браузерного fingerprinting. Он не читает файлы, не получает список процессов и не показывает название программы. Но он может дать сигнал: порт быстро отказал, ответил с задержкой или вообще завис до timeout. В сочетании с Canvas, WebGL и video fingerprinting и поведенческими метриками такой сигнал помогает антифроду оценивать среду сессии.

Отдельно стоит порт 9222, который часто связывают с Chrome DevTools Protocol. Если в браузере включено удаленное управление через CDP, а сайт фиксирует нетипичную разницу времени на этом порту, это может стать дополнительным сигналом среды. Для понимания смежных утечек полезно держать рядом материал про CDP-утечки Puppeteer, потому что обе темы касаются не внешнего IP, а того, как автоматизация проявляется внутри браузерной среды.

Почему веб-страница может обращаться к локальному адресу

Веб-страница может создать WebSocket-соединение не только с удаленным сервером, но и с адресом вроде 127.0.0.1 или localhost. Это не значит, что сайт автоматически читает локальные данные. Суть в попытке установить соединение и измерить время до браузерного события ошибки, которое может косвенно зависеть от сетевого состояния локального порта.

WebSocket был создан для постоянной двусторонней связи: чаты, биржевые графики, live-статусы, игры в браузере. На старте браузер делает TCP-соединение, отправляет HTTP Upgrade и ждет, согласится ли сервер перейти в WebSocket-протокол. Если адресом является localhost, трафик не выходит во внешнюю сеть. Он идет в loopback-интерфейс той же операционной системы.

Проблема в том, что даже неудачная попытка дает побочную информацию. Страница не должна видеть ответ MySQL, SSH или локального прокси. И в нормальной модели безопасности она его не видит. Но JavaScript может фиксировать разницу во времени до события ошибки. На нее могут влиять быстрый отказ ОС, установка TCP-соединения с последующей неудачей WebSocket Upgrade или более длинный timeout.

Это не классическое сканирование портов в стиле nmap. Браузерный скрипт не имеет сырого доступа к TCP-пакетам, не видит SYN/ACK напрямую и не получает баннер сервиса. Он работает грубее: пробует несколько портов, фиксирует время до события onerror и сравнивает результат с базовым значением.

Для антифрод-системы локальный тайминг получает значение в сочетании с другими признаками. Если в сессии одновременно видны подозрительный User-Agent, нетипичный WebGL renderer, нестабильный IP и тайминг, похожий на открытый CDP-порт, совокупность сигналов может повлиять на оценку риска.

Как время ответа помогает оценить состояние порта

Временная атака WebSocket опирается на статистические отличия во времени ошибки, которые при определенных условиях могут соответствовать закрытому, открытому или отфильтрованному firewall порту. Сайт не читает локальный сервис, а тайминг не дает гарантированной классификации состояния порта.

Типичный сценарий выглядит просто. Скрипт берет высокоточный таймер, запускает new WebSocket("ws://127.0.0.1:9222"), ждет ошибку и считает разницу. Затем он повторяет попытку для нескольких портов и сравнивает их с контрольным портом, который почти наверняка закрыт.

Условный алгоритм проверки такой:

  1. выберите контрольный высокий порт, который не используется локальными сервисами
  2. измерьте среднее время ошибки для этого контрольного порта
  3. попробуйте WebSocket-соединение с портами, которые имеют смысл для риск-модели
  4. сравните задержку каждого порта с базовым значением
  5. отбросьте единичные выбросы, которые могли появиться из-за нагрузки процессора или garbage collection
  6. передайте не сырой вывод, а скоринговый сигнал с уровнем уверенности

Цифры не стоит читать как универсальный закон. На localhost закрытый порт часто дает очень быстрый отказ, открытый порт может отвечать заметно дольше из-за TCP handshake и неудачного WebSocket Upgrade, а filtered-порт может ждать до системного timeout. Но точные миллисекунды зависят от ОС, браузера, нагрузки процессора, политик таймера и того, что именно слушает порт.

Состояние портаЧто происходит на уровне TCPЧто видит скриптПочему это полезно антифроду
закрытыйОС быстро возвращает RSTкороткая задержка до onerrorбазовая линия нормального отказа
открытыйhandshake проходит, но WebSocket Upgrade ломаетсябольшая задержка до ошибкивозможный локальный сервис или агент
filteredfirewall может отбрасывать пакет без быстрого ответавозможна более длинная задержка или timeoutпотенциальный признак фильтрации или нетипичного правила
нестабильныйрезультат плавает между попыткамишум в измеренияхсигнал низкой уверенности

После таблицы легко сделать неправильный вывод: если порт открыт, пользователь виноват. На самом деле нет. Локальные порты открывают легальные программы: IDE, Docker, VPN-клиенты, менеджеры паролей, криптокошельки, корпоративные агенты безопасности. Технический сигнал становится антифрод-риском только в контексте всей сессии.

маршруты WebSocket timing для состояний портов

Антифрод-модели могут не опираться на один порог срабатывания. Они калибруют время на текущей машине, повторяют попытки, смотрят на разброс значений и сопоставляют локальные признаки с браузерным отпечатком. Здесь начинается зона оценки, а не прямого доказательства.

Что ограничивают браузеры и операционные системы

Браузеры ограничивают доступ веб-страницы к локальным ресурсам несколькими разными механизмами. Same-Origin Policy и CORS прежде всего регулируют доступ к ответам обычных веб-запросов, Secure Context определяет доступность отдельных возможностей, а Private Network Access добавляет проверки для обращений к приватным сетям. Эти механизмы не следует считать одинаковой защитой от WebSocket-таймингов: время до браузерного события ошибки при определенных условиях может оставаться побочным каналом.

Это важная граница. Если сайт попробует прочитать ответ локального HTTP-сервера через fetch, браузер должен заблокировать доступ к телу ответа без нужных CORS-заголовков. WebSocket работает иначе: сервер может проверять Origin. Но сам факт успешного или неудачного пути к ошибке все равно возникает.

Операционная система тоже не всегда устраняет такой побочный канал. Loopback-трафик не выходит за пределы устройства, а поведение firewall относительно него зависит от ОС и конфигурации. Правила DROP и REJECT также могут создавать разные временные характеристики.

Когда Вы настраиваете защиту, разница между этими действиями практична:

  • REJECT обычно быстро возвращает отказ, но конкретный тайминг зависит от ОС, firewall и сетевой конфигурации
  • DROP может отбрасывать пакет без быстрого ответа и вызывать более длинный timeout
  • полное блокирование localhost может ломать легальные локальные агенты
  • список разрешенных сервисов уменьшает шум, но требует поддержки
  • отдельная среда профиля лучше изолирует локальные сервисы от браузерной сессии

Если у Вас несколько рабочих ролей на одной машине, не стоит открывать все в одном обычном браузере и надеяться, что прокси решит локальные утечки. Прокси меняет внешний маршрут, но не убирает локальный Docker daemon, CDP endpoint или корпоративный агент, который слушает порт на loopback.

Private Network Access частично закрывает классические сценарии доступа с публичных сайтов к приватным сетевым ресурсам. Но PNA не является универсальным ответом на timing side-channel. Если браузеру нужно попробовать соединение, чтобы затем отклонить его политикой, сама разница времени может остаться полезной для скоринга.

браузерные и системные слои защиты WebSocket

Для практической безопасности это означает одно: не стоит полагаться на один слой. Браузерная политика уменьшает доступ к данным, firewall контролирует реакцию ОС, а изоляция среды убирает лишние локальные сервисы из поля зрения рабочей сессии.

Как такие сигналы могут входить в антифрод

Антифрод может использовать локальные WebSocket-тайминги как один из сигналов среды. Конкретное использование зависит от платформы, ее риск-модели и правил.

Сигнал локального порта потенциально может быть полезен в трех ситуациях:

  1. система проверяет признаки автоматизации через CDP, Playwright, Puppeteer или Selenium
  2. оценивает нетипичную серверную среду, где на localhost открыты базы данных, SSH, панели управления или локальные прокси
  3. сопоставляет якобы независимые профили по повторяющемуся набору локальных признаков

Здесь WebSocket timing attack пересекается с темой headless browser detection. Headless-режим может иметь заметные признаки в WebDriver, canvas-параметрах или поведении API. Локальный порт добавляет еще один слой: не то, как браузер рисует страницу, а то, что рядом с браузером работает на машине.

Условный пример того, как такой сигнал теоретически может выглядеть в скоринговой системе:

СигналНизкий рискБолее высокий рискКомментарий
9222 или другой CDP-портпорт закрыт или недоступенв теоретической модели есть задержка, похожая на открытый endpointтребует сопоставления с другими сигналами автоматизации
порты локального проксимогут быть ожидаемыми в корпоративном сценариив теоретической модели повторяются во многих аккаунтахпотенциально могут быть одним из кластерных сигналов
порты SSH или баз данныхмогут быть нетипичными для обычной потребительской средыв теоретической модели повторяются между сессиямимогут быть признаком серверной или рабочей среды
filtered-таймингиединичные и нестабильныесистемные для многих портовможет выдать агрессивное firewall-правило
одинаковый набор локальных портовслучайное совпадениеповторяется в десятках профилейпотенциальный сигнал для кластерного анализа

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

Важно учитывать не только браузер, но и сетевой маршрут. Если профили работают через разные прокси, но все они запускаются на одной машине с одинаковыми локальными сервисами, прокси не разделяет этот слой. Для QUIC, UDP и SOCKS5 это отдельная тема, которую стоит сопоставить с материалом про UDP через SOCKS5 и маршрутизацию QUIC.

WebSocket timing signal в антифрод скоринге

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

Как проверить локальную среду и уменьшить утечку данных

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

На macOS и Linux базовую картину дают lsof -iTCP -sTCP:LISTEN -n -P или ss -ltnp. На Windows можно начать с netstat -ano и сопоставить PID с процессами в Task Manager или PowerShell. Дальше список нужно не просто сохранить, а разделить на нормальные, служебные и рискованные порты.

Практический порядок аудита такой:

  1. проверьте список прослушиваемых портов перед запуском рабочего браузера
  2. закройте IDE, локальные серверы, Docker-контейнеры и debug-сессии, если они не нужны для задачи
  3. убедитесь, что CDP-порт не открыт наружу без реальной необходимости
  4. ограничьте доступ к ненужным локальным сервисам с помощью firewall и оставьте доступными только необходимые для работы соединения
  5. протестируйте один и тот же профиль в обычном браузере и в изолированной среде
  6. повторите измерения несколько раз, чтобы отделить стабильный сигнал от шума
  7. задокументируйте, какие локальные агенты разрешены в командном SOP

В рабочих процессах с большим количеством аккаунтов та же логика переходит в кластерный риск. Один профиль с открытым локальным портом может быть случайностью. Пятьдесят профилей с одинаковым набором локальных портов могут указывать на общую инфраструктуру. Именно здесь уместно вспомнить Sybil-детекцию и кластерный анализ, потому что системы оценки риска могут учитывать не один отдельный сигнал, а повторяющуюся структуру признаков.

Что делать на практике, если Вы управляете командной инфраструктурой:

  • разделяйте рабочие роли по отдельным профилям и средам
  • не запускайте automation-debugging в той же среде, где входите в важные аккаунты
  • используйте список разрешенных локальных агентов, которые действительно нужны
  • отличайте блокировку от быстрого отказа, потому что для тайминга это разные сигналы
  • фиксируйте изменения в SOP, чтобы команда не открывала случайные порты перед рабочей сменой
  • проверяйте не только IP и fingerprint, но и локальный сетевой контур

Afina уместна в таком процессе как инфраструктура для изолированных браузерных профилей, управления fingerprint-параметрами, прокси и командными доступами. Изоляция профилей позволяет разделять cookies, сессии, настройки прокси и рабочие роли, но не заменяет аудит локальной ОС, firewall и сервисов на localhost. Материал предоставлен исключительно в ознакомительных и образовательных целях.

Для командного SOP удобно держать отдельный чеклист: какие локальные сервисы разрешены, какие порты не должны быть открыты перед запуском профиля, кто отвечает за обновление правил firewall и где хранятся результаты тестов. Такая документация помогает отслеживать изменения среды и анализировать причины дополнительных проверок риска для отдельных профилей.

Скачать

FAQ — Часто задаваемые вопросы

Что такое WebSocket timing attack?

WebSocket timing attack позволяет оценить состояние локального порта по времени ошибки при попытке соединения. Скрипт не читает локальные данные, но сравнивает задержки между закрытыми, открытыми и фильтрованными портами.

Может ли сайт сканировать localhost через браузер?

Сайт может попытаться обратиться к localhost через браузерные API, включая WebSocket. Браузер ограничивает доступ к ответу, но само время ошибки может оставаться побочным сигналом.

Почему порт 9222 считается рискованным?

Порт 9222 часто связывают с Chrome DevTools Protocol и управлением браузером для автоматизации. Сам по себе открытый порт не доказывает нарушение, но в антифрод-скоринге он может усилить другие automation-сигналы.

Защищает ли CORS от WebSocket port scanning?

CORS ограничивает чтение ответов в обычных веб-запросах, но не убирает все тайминговые побочные каналы. Для WebSocket также важны TCP-handshake, ошибка Upgrade и время до onerror.

Решает ли Private Network Access проблему локальных портов?

Private Network Access добавляет ограничения для части обращений с публичных сайтов к приватным сетевым ресурсам. Его поведение зависит от браузера, типа запроса и актуальной реализации, поэтому PNA не стоит считать универсальной защитой от всех тайминговых побочных каналов.

Как проверить открытые локальные порты?

На macOS и Linux используйте lsof или ss, а на Windows начните с netstat -ano. После этого сопоставьте порты с процессами и закройте сервисы, которые не нужны для рабочей сессии.

Достаточно ли прокси для защиты от localhost-сигналов?

Нет, прокси меняет внешний сетевой маршрут, но не убирает локальные сервисы на машине. Для localhost-сигналов важны изоляция среды, firewall и контроль debug-портов.

Можно ли полностью запретить браузеру доступ к localhost?

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

Похожие термины

Читать дальше:Антидетект-браузер — анонимность профилей | Afina Browser
Кирилл Кученёв-Полодиенко

Привет! Я Кирилл Кученёв-Полодиенко — Technical Product Manager (Automation) в команде Afina.