
Портативный DNS-резолвер на Rust — локальные домены .numa, блокировка рекламы, переопределения для разработчиков
Свой DNS. Везде, где ты. — numa.rs
Портативный DNS-резолвер в одном бинарнике. Блокируйте рекламу в любой сети, называйте свои локальные сервисы (frontend.numa), переопределяйте любые имена хостов с авто-откатом и шифруйте каждый исходящий запрос с помощью ODoH (RFC 9230) — ни одна сторона не увидит одновременно, кто вы и что вы спросили. Всё с ноутбука: ни облачных аккаунтов, ни Raspberry Pi не нужно.
Создан с нуля на Rust. Никаких DNS-библиотек. Кэширование, блокировка рекламы и домены локальных сервисов из коробки. Опционально — рекурсивное разрешение от корневых серверов с полной проверкой цепочки доверия DNSSEC, плюс DNS-over-TLS-слушатель для зашифрованных клиентских соединений (iOS Private DNS, systemd-resolved и др.). Запустите numa relay — и тот же бинарник станет публичной ODoH-ретрансляцией. В списке DNSCrypt сейчас остался один рабочий ретранслятор, так что каждый развёрнутый Numa реально расширяет экосистему. Один бинарник ~8 МБ — всё встроено.

# macOS
brew install razvandimescu/tap/numa
# Linux
curl -fsSL https://raw.githubusercontent.com/razvandimescu/numa/main/install.sh | sh
# Arch Linux
pacman -S numa
# Windows — скачать с GitHub Releases
# Все платформы
cargo install numa
# Docker
docker run -d --name numa --network host ghcr.io/razvandimescu/numa
# Nix
nix run github:razvandimescu/numa
sudo numa # запустить в фоне (порт 53 требует root/admin)
Откройте панель: http://numa.numa (или http://localhost:5380)
Установка как системного DNS:
На macOS и Linux numa работает как системный сервис (launchd/systemd). На Windows numa запускается автоматически при входе в систему через реестр. Windows также привязывается к 127.0.0.2:53 (встроенный Dnscache занимает 127.0.0.1:53) и устанавливает правило NRPT для маршрутизации запросов к нему — поэтому настраивайте bind_addr/api_bind_addr на 127.0.0.2, а не на 127.0.0.1.
Дайте имена своим dev-сервисам, а не запоминайте номера портов:
curl -X POST localhost:5380/services \
-d '{"name":"frontend","target_port":5173}'
Теперь https://frontend.numa работает в браузере — зелёный замок, валидный сертификат, WebSocket-прокси для HMR. Ни mkcert, ни nginx, ни /etc/hosts.
Добавляйте маршрутизацию на основе пути (app.numa/api → :5001), делитесь сервисами между машинами через LAN-обнаружение или настраивайте всё в numa.toml.
Блокируется 385К+ доменов через Hagezi Pro. Работает в любой сети — кофейни, отели, аэропорты. Путешествует с вашим ноутбуком.
Три режима разрешения:
forward (по умолчанию) — прозрачный прокси к существующему системному DNS. Всё работает как раньше, только с кэшированием и блокировкой рекламы сверху. Учитываются captive-порталы, VPN, корпоративные DNS.recursive — разрешение напрямую от корневых серверов. Никакой зависимости от вышестоящего, ни одна сторона не видит полный шаблон ваших запросов. Добавьте [dnssec] enabled = true для полной проверки цепочки доверия.auto — при запуске проверяет доступность корневых серверов: если есть — рекурсивный режим, если блокируются — зашифрованный DoH-запасной вариант.DNSSEC проверяет полную цепочку доверия: подписи RRSIG, проверку DNSKEY, делегирование DS, доказательства отрицания NSEC/NSEC3. Читайте как работает →
DNS-over-TLS-слушатель (RFC 7858) — принимает зашифрованные запросы на порту 853 от строгих клиентов, таких как iOS Private DNS, systemd-resolved или stubby. Два режима:
numa install добавляет его в системное хранилище доверия на macOS, Linux (Debian/Ubuntu, Fedora/RHEL/SUSE, Arch) и Windows. На iOS установите .mobileconfig из numa setup-phone. Firefox хранит собственное хранилище NSS и игнорирует системное — добавьте CA вручную, если вам нужен HTTPS для .numa-сервисов в Firefox.[dot] cert_path / key_path на публично доверенный сертификат (например, Let's Encrypt с DNS-01-челленджем на домене, указывающем на ваш экземпляр numa). Клиенты подключаются без настройки хранилища — такой же UX, как у AdGuard Home или Cloudflare 1.1.1.1.ALPN "dot" объявляется и применяется в обоих режимах; рукопожатие с несовпадающим ALPN отклоняется для защиты от путаницы протоколов.
Настройка телефона — подключите iPhone или Android к Numa одним шагом:
numa setup-phone
Печатает QR-код. Сканируйте, установите профиль, включите доверие к сертификату — DNS вашего телефона теперь маршрутизируется через Numa по TLS. Требует [mobile] enabled = true в numa.toml.
Запустите Numa на нескольких машинах. Они находят друг друга автоматически через mDNS:
Machine A (192.168.1.5) Machine B (192.168.1.20)
┌──────────────────────┐ ┌──────────────────────┐
│ Numa │ mDNS │ Numa │
│ - api (port 8000) │◄───────────►│ - grafana (3000) │
│ - frontend (5173) │ discovery │ │
└──────────────────────┘ └──────────────────────┘
С машины B: curl http://api.numa → проксируется на порт 8000 машины A. Включите с помощью numa lan on.
Режим хаба: запустите один экземпляр с bind_addr = "0.0.0.0:53" и направьте DNS других устройств на него — они получат блокировку рекламы + разрешение .numa без установки чего-либо. bind_addr также принимает список для привязки к определённому набору интерфейсов.
# Рекомендуется — host-сеть (Linux)
docker run -d --name numa --network host ghcr.io/razvandimescu/numa
# Проброс портов (macOS/Windows Docker Desktop)
docker run -d --name numa -p 53:53/udp -p 53:53/tcp -p 5380:5380 ghcr.io/razvandimescu/numa
Панель по адресу http://localhost:5380. По умолчанию образ привязывает API и прокси к 0.0.0.0. Переопределите пользовательской конфигурацией:
docker run -d --name numa --network host \
-v /path/to/numa.toml:/root/.config/numa/numa.toml \
ghcr.io/razvandimescu/numa
Multi-arch: linux/amd64 и linux/arm64.
Готовые compose-рецепты:
packaging/client/ — режим ODoH-клиента (анонимный DNS), Numa + стартовый numa.toml.packaging/relay/ — публичная ODoH-ретрансляция, Numa + Caddy + ACME.Запросы из кэша за 0.1 мс — наравне с Unbound и AdGuard Home. Кэш на уровне сырых байтов с прямым патчем TTL. Request hedging устраняет p99-всплески: холодный рекурсивный p99 538 мс против 748 мс у Unbound (−28%), σ в 4 раза уже. Бенчмарки →
.numa — авто TLS, маршрутизация по пути, WebSocket-проксиtls://)numa relay, RFC 9230)MIT
| Платформа | Установка | Удаление |
|---|
| macOS | sudo numa install | sudo numa uninstall |
| Linux | sudo numa install | sudo numa uninstall |
| Windows | numa install (администратор) + перезагрузка | numa uninstall (администратор) + перезагрузка |
| Pi-hole | AdGuard Home | Unbound | Numa |
|---|
| Прокси локальных сервисов + авто TLS | — | — | — | Домены .numa, HTTPS, WebSocket |
| LAN-обнаружение сервисов | — | — | — | mDNS, без настройки |
| Переопределения разработчика (REST API) | — | — | — | Авто-откат, скриптуемо |
| Рекурсивный резолвер | — | — | Да | Да, с выбором по SRTT |
| Валидация DNSSEC | — | — | Да | Да (RSA, ECDSA, Ed25519) |
| Блокировка рекламы | Да | Да | — | 385К+ доменов |
| Веб-интерфейс | Полный | Полный | — | Панель управления |
| Шифрованный апстрим (DoH/DoT) | Через cloudflared | Только DoH | Только DoT | DoH + DoT (tls://) |
| Шифрованные клиенты (DoT-слушатель) | Нужен stunnel sidecar | Да | Да | Встроенный (RFC 7858) |
| Серверная точка DoH | — | Да | — | Да (RFC 8484) |
| Request hedging | — | — | — | Все протоколы (UDP, DoH, DoT) |
| Serve-stale + prefetch | — | — | Prefetch при 90% TTL | RFC 8767, prefetch при 90% TTL |
| Условное перенаправление | — | Да | Да | Да (правила по суффиксам) |
| Портативность (ноутбук) | Нет (аппаратный) | Нет (аппаратный) | Сервер | Один бинарник, macOS/Linux/Windows |
| Зрелость сообщества | 56K звёзд, 10 лет | 33K звёзд | 20 лет | Новый |
setup-phone, мобильное API, профили mobileconfig.numa — DHT, без регистратора