Увімкнути DNS-over-HTTPS у systemd-resolved на Debian/Ubuntu: cloudflared, fallback і тести

Увімкнути DNS-over-HTTPS у systemd-resolved на Debian/Ubuntu: cloudflared, fallback і тести
Категорії: Сервери та мережі

Як зробити DNS-запити приватними на рівні всієї системи у Debian/Ubuntu? Простий і надійний шлях — поєднати systemd-resolved як локальний кешуючий резолвер із cloudflared як проксі для DNS-over-HTTPS (DoH). У цій інструкції ви отримаєте зрозумілий план дій, fallback-варіанти та перевірки. Усе — через термінал Linux, без зайвих слів 🙂

Що саме ми налаштуємо

Ми встановимо й увімкнемо cloudflared у режимі proxy-dns на локальному порту (5053), а systemd-resolved направимо туди всі DNS-запити. Upstream-сервери в cloudflared працюватимуть по DoH (Cloudflare). Додамо fallback, щоб мережа не "падала", навіть якщо локальний DoH зупиниться.

Підготовка: перевірте systemd-resolved

Спочатку впевніться, що systemd-resolved увімкнений, а ваш /etc/resolv.conf вказує на локальний stub 127.0.0.53. Це базові мережеві налаштування перед інтеграцією з DoH.

sudo systemctl enable --now systemd-resolved
systemctl --no-pager status systemd-resolved
resolvectl status
ls -l /etc/resolv.conf
# Якщо це не симлінк на stub, виправляємо:
sudo ln -sf /run/systemd/resolve/stub-resolv.conf /etc/resolv.conf

Після цього резолвер системи керується systemd-resolved. Далі встановимо cloudflared через apt команди.

Встановлення cloudflared (DNS-over-HTTPS проксі)

Додавання репозиторію та інсталяція

Офіційний репозиторій Cloudflare має окремий компонент для cloudflared. Виконайте в терміналі Linux:

sudo apt update
sudo apt install -y curl gnupg ca-certificates lsb-release
curl -fsSL https://pkg.cloudflare.com/cloudflare-main.gpg | \
  sudo gpg --dearmor -o /usr/share/keyrings/cloudflare-main.gpg
echo "deb [signed-by=/usr/share/keyrings/cloudflare-main.gpg] https://pkg.cloudflare.com/cloudflared $(lsb_release -cs) main" | \
  sudo tee /etc/apt/sources.list.d/cloudflared.list > /dev/null
sudo apt update
sudo apt install -y cloudflared

Якщо ваш випуск дистрибутива не підтримується цим репозиторієм, можна встановити .deb з GitHub Releases.

ARCH=$(dpkg --print-architecture) # amd64/arm64/armhf і т.д.
wget -q https://github.com/cloudflare/cloudflared/releases/latest/download/cloudflared-linux-${ARCH}.deb
sudo apt install -y ./cloudflared-linux-${ARCH}.deb

Сервіс cloudflared у режимі proxy-dns

Створимо окремого системного сервіс-користувача та systemd-юнит, що запускає DoH-проксі на порту 5053 з двома upstream-адресами Cloudflare:

sudo useradd -r -s /usr/sbin/nologin -U -M cloudflared 2>/dev/null || true
sudo tee /etc/systemd/system/cloudflared-dns.service > /dev/null <<'EOF'
[Unit]
Description=Cloudflared DNS over HTTPS proxy
After=network-online.target
Wants=network-online.target

[Service]
User=cloudflared
Group=cloudflared
AmbientCapabilities=CAP_NET_BIND_SERVICE
ExecStart=/usr/bin/cloudflared proxy-dns \
  --port 5053 \
  --upstream https://1.1.1.1/dns-query \
  --upstream https://1.0.0.1/dns-query \
  --no-autoupdate
Restart=on-failure

[Install]
WantedBy=multi-user.target
EOF
sudo systemctl daemon-reload
sudo systemctl enable --now cloudflared-dns
systemctl --no-pager status cloudflared-dns

Швидкий тест локального порту:

dig @127.0.0.1 -p 5053 cloudflare.com A +short

Прив’язка systemd-resolved до cloudflared і fallback

Тепер направимо всі резольви системи на локальний DoH-проксі. Використаємо drop-in для зручності оновлень — це маленька порада Linux, щоб не редагувати головний файл конфігурації.

sudo install -d /etc/systemd/resolved.conf.d
sudo tee /etc/systemd/resolved.conf.d/10-doh-local.conf > /dev/null <<'EOF'
[Resolve]
DNS=127.0.0.1:5053
# Якщо cloudflared раптом помре, буде plaintext fallback нижче (компроміс доступності vs. приватність)
FallbackDNS=9.9.9.9 1.1.1.1
DNSStubListener=yes
# ВАЖЛИВО: не вмикаємо DoT тут, бо наш основний DNS локується на 127.0.0.1:5053
DNSOverTLS=no
EOF
sudo systemctl restart systemd-resolved
resolvectl status | sed -n '/Current DNS Server/,+5p'

Якщо ви хочете шифрований fallback без plaintext, підніміть другий DoH-проксі (наприклад, ще один cloudflared на порту 5054 із Quad9 або Google DoH) і додайте обидва локальні адреси в DNS=:

# Приклад багатосерверної схеми в drop-in
[Resolve]
DNS=127.0.0.1:5053 127.0.0.1:5054
FallbackDNS=
DNSOverTLS=no

Тестування і діагностика

Перевіряємо, що запити йдуть через cloudflared і все стабільно відповідає:

# Який DNS-сервер активний
resolvectl status | grep -A2 "Current DNS Server"

# Чи резолвиться домен через системний резолвер
resolvectl query kernel.org

# Прямий запит у локальний DoH-проксі
dig @127.0.0.1 -p 5053 example.com +short

# Чи слухає cloudflared порт 5053
ss -lntup | grep 5053

# Логи сервісу в реальному часі
journalctl -u cloudflared-dns -f

Порада: для складних кейсів підніміть рівень логів у cloudflared додатковим параметром --loglevel debug в ExecStart і перезапустіть сервіс.

Альтернативні способи

  • AdGuard dnsproxy: універсальний DNS-проксі з DoH/DoT/DoQ. Заміна cloudflared, більше контролю.
  • dnscrypt-proxy: шифрований DNS (DNSCrypt/DoH), великий список провайдерів.
  • Unbound + DoT: якщо DoH не обов’язковий, а підходить DNS-over-TLS — потужний локальний резолвер з кешем.
  • systemd-resolved + DoT: нативно підтримується; але саме DoH поки що реалізуємо зовнішнім проксі.

GUI-спосіб (Ubuntu Desktop)

Якщо ви на робочому столі Ubuntu і не хочете лізти в усі файли конфігурації, можна просто вказати локальний DNS у налаштуваннях мережі:

  1. Відкрийте Settings → Network → ваш інтерфейс (Wired/Wi‑Fi) → шестерня.
  2. У вкладці IPv4 (і IPv6 за потреби) вимкніть Automatic (DHCP) DNS та впишіть 127.0.0.1.
  3. Перепідключіться до мережі. Переконайтеся, що systemd-resolved активний.

Цей варіант просто скеровує запити на локальний резолвер; сам DoH все одно забезпечує cloudflared.

FAQ

Чи підтримує systemd-resolved DoH нативно?

Ні, наразі systemd-resolved нативно підтримує DoT, а DoH робимо через зовнішній проксі (наприклад, cloudflared або dnsproxy).

Порт 5053 уже зайнято. Що робити?

Змініть порт у юніті cloudflared, наприклад на 5300: у ExecStart вкажіть --port 5300, перезапустіть сервіс і оновіть DNS=127.0.0.1:5300 у drop-in для systemd-resolved.

Як змусити всі програми використовувати systemd-resolved?

Переконайтеся, що /etc/resolv.conf — це симлінк на /run/systemd/resolve/stub-resolv.conf, і ваші програми не хардкодять власні DNS. Для контейнерів і VPN інтерфейсів налаштуйте передавання DNS коректно.

VPN перестав резолвити домени

Часто VPN-клієнт проштовхує власні DNS. Перевірте resolvectl domain і resolvectl status, переконайтесь, що маршрути доменів для VPN інтерфейсу задані, або вручну додайте DNS VPN інтерфейсу через NetworkManager, зберігаючи 127.0.0.1 першим у списку.

Як повернути все назад?

sudo rm -f /etc/systemd/resolved.conf.d/10-doh-local.conf
sudo systemctl restart systemd-resolved
sudo systemctl disable --now cloudflared-dns
sudo apt remove -y cloudflared
# Повернути типовий resolv.conf від resolved (за потреби):
sudo ln -sf /run/systemd/resolve/stub-resolv.conf /etc/resolv.conf

Порада від Kernelka

Для надійності додайте спостереження за сервісом cloudflared: у юніті вже є Restart=on-failure, але ви можете створити простий systemd timer, який періодично виконує resolvectl query one.one.one.one і, якщо тест не проходить, перезапускає сервіс. Це маленький лайфхак із розділу "поради Linux" 😉

Підсумок

  • Увімкнули systemd-resolved та перевірили /etc/resolv.conf.
  • Встановили cloudflared і підняли його як DoH-проксі на 127.0.0.1:5053.
  • Спрямували DNS у systemd-resolved на локальний порт, додали fallback.
  • Протестували роботу через resolvectl, dig і логи systemd.
  • Розглянули альтернативи (dnsproxy, dnscrypt-proxy, Unbound/DoT) і GUI-вказівки.

Готово! Тепер ваші DNS-запити шифруються DoH на рівні системи. Безпечно, стабільно і контрольовано 💪

Прокоментувати

На сайті відображається лише твоє ім'я та коментар. Електронна пошта використовується виключно для зв'язку з тобою за потреби.