Snowflake proxy (Tor): как поднять свой узел
Классические Tor-мосты банят по IP пачками — их список конечен, а DPI научился их вычислять. Snowflake решает эту проблему иначе: вместо постоянного адреса моста трафик прыгает через тысячи временных волонтёрских узлов поверх WebRTC, и заблокировать их все — то же самое, что заблокировать видеозвонки во всём интернете. Ниже — как устроен этот pluggable transport и как поднять свой узел-прокси на сервере, чтобы помогать чужому трафику доходить до Tor.
Содержание
Обсудить статью, задать вопрос или начать новую тему
Есть вопрос по этой статье, идея для обсуждения или просто хотите поделиться опытом? Сообщество MAATRIX ждёт. Для общения, пожалуйста, зарегистрируйтесь в нашем личном кабинете.
Перейти в сообщество →Что такое Snowflake и зачем он Tor
Snowflake — один из pluggable transports проекта Tor, наравне с obfs4 и meek. Его задача не в том, чтобы скрыть содержимое трафика (это и так делает сама луковичная маршрутизация), а в том, чтобы спрятать сам факт подключения к Tor от DPI-систем, которые блокируют по сигнатурам и IP-адресам известных мостов.
Идея в том, чтобы вообще не иметь постоянного адреса моста. Клиент из страны с блокировками через служебный канал (broker) находит один из множества добровольческих прокси — обычных браузеров с открытой вкладкой snowflake.torproject.org, браузерных расширений или отдельно запущенных демонов на серверах — и устанавливает с ним соединение по протоколу WebRTC, тому же самому, что используют видеозвонки в браузере. Прокси просто перекидывает байты между клиентом и фиксированным Snowflake-мостом Tor Project, который уже полноценно вводит трафик в сеть Tor.
Для DPI это выглядит как обычный WebRTC-трафик — тот же, что генерируют десятки легитимных сервисов видеосвязи. Заблокировать конкретный IP волонтёра можно, но толку немного: через минуту клиент получит от broker'а адрес другого прокси. Список добровольцев меняется постоянно, поэтому системная блокировка Snowflake требует банить WebRTC как класс — а это уже удар по легальным сервисам.
Как устроена цепочка: broker, ICE и WebRTC
Три роли в этой схеме:
- Клиент — человек в стране с блокировками, у которого Tor Browser настроен на transport
snowflake. - Прокси (proxy) — доброволец, который выделяет немного своей полосы и делает трафик клиента доступным Tor. Именно этот узел мы будем поднимать.
- Broker — координационный сервер Tor Project, который сводит клиентов и прокси между собой, не участвуя в передаче самого трафика.
Работает это так: запущенный прокси периодически «отмечается» на broker'е — сообщает, что готов принять клиента, и указывает тип своего NAT. Когда появляется клиент, broker подбирает подходящий свободный прокси и обменивает между ними SDP-офферы через WebRTC ICE (тот же механизм, что находит прямой путь между двумя компьютерами для видеозвонка, пробуя STUN и, если нужно, TURN-релей). После этого клиент и прокси устанавливают WebRTC data channel напрямую, а прокси просто транслирует эти данные на постоянный Snowflake-мост Tor, который уже разворачивает их в обычную Tor-цепочку.
Само обращение клиента к broker'у — тоже уязвимое место для блокировки, поэтому его прячут за доменным фронтингом или AMP Cache: с точки зрения наблюдателя запрос выглядит как обращение к крупному CDN, а не к инфраструктуре Tor. Это тот же принцип маскировки «под чужой большой сайт», что используется в VLESS Reality — только применительно не к прокси-протоколу, а к самому сигнальному каналу.
Арендуйте сервер под свои задачи!
Разверните VPS MAATRIX за пару минут: NVMe, AMD EPYC, root-доступ, локации UK, США, Франция и РФ. Оплата картой РФ и по СБП.
Арендовать серверЧем отдельный сервер лучше браузерного расширения
Проще всего стать волонтёром — поставить расширение Snowflake в Chrome или Firefox или просто держать открытой вкладку snowflake.torproject.org. Но у этого способа два ограничения: прокси живёт, пока открыт браузер, и домашний интернет почти всегда сидит за NAT, из-за которого WebRTC-соединению нужен TURN-релей — а это лишняя нагрузка на инфраструктуру Tor Project, у которой TURN-серверов немного.
Сервер с публичным IP снимает обе проблемы разом. Во-первых, standalone-демон snowflake-proxy работает постоянно как systemd-сервис, а не только пока открыта вкладка. Во-вторых, у VPS обычно нет NAT между сервером и интернетом («unrestricted» или «easy NAT» в терминах Snowflake) — а это значит, что WebRTC-соединение с клиентом устанавливается напрямую, без TURN-релея. Broker сознательно приоритизирует именно такие узлы при подборе прокси клиенту, потому что они не расходуют дефицитный ресурс TURN. Один сервер с чистым внешним IP в этом смысле полезнее для сети, чем десяток открытых вкладок в браузерах за домашними роутерами.
Установка snowflake-proxy на сервере
Есть два рабочих пути: контейнер Docker (быстрее всего) или сборка из исходников на Go.
Через Docker:
docker run -d \
--name snowflake-proxy \
--restart unless-stopped \
--network host \
thetorproject/snowflake-proxy \
-capacity 20 \
-summary-interval 24h
--network host упрощает жизнь WebRTC — без него придётся вручную пробрасывать диапазон UDP-портов в контейнер.
Сборка из исходников:
apt update && apt install -y golang-go git
git clone https://gitlab.torproject.org/tpo/anti-censorship/pluggable-transports/snowflake.git
cd snowflake/proxy
go build
./proxy -capacity 20 -summary-interval 24h
Ключевые флаги бинарника:
| Флаг | Назначение |
|---|---|
-capacity N | максимум одновременных клиентов (без флага — не ограничено, на слабом канале стоит явно выставить разумное число) |
-summary-interval | как часто писать в лог статистику по трафику |
-ephemeral-ports-range "lo:hi" | сузить диапазон UDP-портов для WebRTC — полезно, если фаервол разрешает не весь эфемерный диапазон |
-relay | адрес Snowflake-моста; менять не нужно, если вы не поднимаете тестовый стенд |
-unsafe-logging | не маскировать IP-адреса в логах (для отладки, в проде лучше не включать) |
Проверить, что демон вообще стартовал и видит broker, можно по логу: строка broker: {"Status":"client match"} при первом же подключённом клиенте подтверждает, что цепочка «прокси → broker → клиент» рабочая.
Автозапуск и файрвол
Чтобы прокси переживал перезагрузку, оформите его как systemd-юнит (вариант для собранного из исходников бинарника):
# /etc/systemd/system/snowflake-proxy.service
[Unit]
Description=Snowflake volunteer proxy for Tor
After=network-online.target
Wants=network-online.target
[Service]
ExecStart=/opt/snowflake/proxy/proxy -capacity 20 -summary-interval 24h
Restart=on-failure
RestartSec=10
DynamicUser=yes
NoNewPrivileges=yes
[Install]
WantedBy=multi-user.target
systemctl daemon-reload
systemctl enable --now snowflake-proxy
systemctl status snowflake-proxy
WebRTC использует UDP на случайных эфемерных портах для ICE/STUN — если на сервере включён строгий файрвол, открытие «всего диапазона» обычно избыточно и неудобно для аудита. Практичнее сузить диапазон флагом -ephemeral-ports-range и открыть в фаерволе ровно его:
ufw allow 60000:61000/udp
и передать демону -ephemeral-ports-range 60000:61000. Так вы контролируете, что именно открыто наружу, вместо того чтобы разрешать весь эфемерный диапазон ОС.
Легальность и риски: чем это отличается от Tor exit-узла
Частый вопрос — не станет ли сервер точкой, откуда «выходит» чужой Tor-трафик, со всеми вытекающими abuse-жалобами. Нет: это принципиальное отличие Snowflake proxy от Tor exit relay. Прокси не расшифровывает и не выпускает трафик в открытый интернет — он лишь перекидывает зашифрованные байты между клиентом и фиксированным Snowflake-мостом по WebRTC. Внешний сайт, который посещает пользователь Tor, никогда не увидит IP вашего сервера в качестве источника запроса — это делает роль volunteer-прокси заметно менее рискованной, чем роль exit-узла, у которого именно такой сценарий и есть основной источник жалоб.
Это не значит, что риск нулевой. Стоит явно проверить условия использования у хостинг-провайдера — часть площадок в принципе не приветствует любой Tor-related трафик, независимо от роли узла. Разумная гигиена: держать -capacity в разумных пределах, не запускать прокси на сервере с другими чувствительными сервисами на том же IP, и быть готовым быстро остановить демон, если провайдер попросит. Отдельно порт для сравнения: даже SOCKS5-прокси на сервере в обычном понимании ближе по модели ответственности к exit-узлу, чем Snowflake — там сервер действительно выступает точкой выхода в интернет от имени клиента.
Мониторинг вклада и типичные проблемы
Свой вклад в сеть проще всего смотреть через -summary-interval — раз в заданный интервал демон пишет в лог агрегированную статистику: сколько клиентов подключалось и сколько трафика прошло. Точных цифр по каждому конкретному прокси в публичной статистике нет — Snowflake устроен так, чтобы broker не хранил долгую историю по отдельным волонтёрам. Общую динамику использования канала по всей сети Snowflake можно посмотреть на metrics.torproject.org — это агрегированные графики, не привязанные к вашему серверу лично.
Если демон запущен, но в логах долго нет ни одного client match — чаще всего дело в NAT-типе, который прокси о себе сообщает: если сервер всё же находится за NAT (например, вы в облаке с приватным адресом и NAT на уровне провайдера), broker будет реже подбирать вас клиентам с похожим ограниченным NAT, поскольку без TURN-релея такое соединение установить сложнее. Проверьте curl ifconfig.me изнутри сервера и сравните с адресом, который слушает демон, — если они не совпадают напрямую (а идут через NAT-прокладку провайдера), это объясняет низкую частоту подключений. Вторая частая причина — файрвол режет эфемерные UDP-порты ICE; сверьте открытый диапазон с тем, что передан флагом -ephemeral-ports-range.
Арендуйте сервер под свои задачи!
Разверните VPS MAATRIX за пару минут: NVMe, AMD EPYC, root-доступ, локации UK, США, Франция и РФ. Оплата картой РФ и по СБП.
Арендовать серверНужны сами нейросети для контента?
Генерируйте изображения, видео и озвучку нейросетями на falapi.io — десятки моделей в одном окне. Оплата картой РФ и по СБП.
Частые вопросы
Снижает ли Snowflake-прокси скорость моего интернета?
Заметно — вряд ли, если явно выставить -capacity на разумное число одновременных клиентов. Без ограничения демон теоретически может принять больше сессий, чем удобно на слабом канале, поэтому лимит стоит поставить сразу.
Чем отличается прокси от того, что настраивает сам Tor Browser как клиент?
Это разные роли одного и того же transport. Клиентская настройка (UseBridges 1, ClientTransportPlugin snowflake ...) нужна тому, кто сам подключается к Tor через Snowflake. Демон snowflake-proxy, о котором эта статья, — наоборот, помогает чужим клиентам, отдавая часть полосы своего сервера.
Нужен ли отдельный домен или сертификат для прокси?
Нет. Прокси не поднимает свой HTTPS-сайт и не участвует в доменном фронтинге сам — этим занимается broker на стороне Tor Project. От вас нужен только сервер с публичным IP и открытым диапазоном UDP-портов.
Можно ли ограничить прокси, чтобы он не работал круглые сутки?
Да — самый простой способ — таймер systemd, включающий и выключающий сервис по расписанию (systemctl edit --full для юнита плюс .timer-файл), либо просто ручной systemctl stop snowflake-proxy, когда канал нужен для другого.
Как понять, что мой прокси вообще кому-то пригодился?
По логам с -summary-interval: там видно число подключений и переданный трафик за период. Привязанной к серверу публичной статистики Tor Project не публикует — только агрегированные графики по всей сети на metrics.torproject.org.
Обсудить статью, задать вопрос или начать новую тему
Есть вопрос по этой статье, идея для обсуждения или просто хотите поделиться опытом? Сообщество MAATRIX ждёт. Для общения, пожалуйста, зарегистрируйтесь в нашем личном кабинете.
Перейти в сообщество →