NoctisNode
← ГайдыСети2026-10-239 мин

Приватный кластер VPS на mesh-сети WireGuard

Объедините VPS-узлы в приватный кластер полной mesh-сетью WireGuard: единый план адресов, один [Peer] на узел, AllowedIPs /32, строгий файрвол и сервисы, привязанные к wg0.

Коротко: чтобы превратить несколько VPS в приватный кластер, дайте каждому узлу интерфейс WireGuard с адресом из одной приватной подсети, добавьте каждый другой узел как `[Peer]` с его публичным `Endpoint` и `/32` в `AllowedIPs`, разрешите UDP 51820 только с ваших узлов и привяжите базы данных и внутренние сервисы к адресу `wg0`, а не к публичному IP. Примерно до десяти узлов это легко поддерживать вручную или по шаблону; дальше используйте инструменты, которые генерируют и раздают конфиги.

Руководство предполагает, что вы уже знаете основы из руководства по WireGuard VPN и укрепили SSH на каждом узле по руководству по защите SSH; как заходить на узлы через бастион без проброса агента — в руководстве по StrictModes и пробросу агента.

План адресов для VPN-узлов

Выберите один приватный диапазон, который не пересекается ни с чем, что вы используете (домашняя LAN, Docker, диапазоны подов Kubernetes). Для небольшого кластера хватит `/24`, и адреса останутся читаемыми. Назначьте каждому узлу фиксированный адрес и храните план в системе контроля версий, потому что из него выводится каждый конфиг.

УзелРольПубличный IPАдрес wg0ListenPort
node1приложение203.0.113.1110.88.0.1/2451820
node2приложение203.0.113.1210.88.0.2/2451820
node3база данных203.0.113.1310.88.0.3/2451820
node4мониторинг203.0.113.1410.88.0.4/2451820

Конфиг пиров на каждом узле

В полной mesh-сети каждый узел общается напрямую с каждым другим, поэтому в каждом конфиге одна секция `[Interface]` и N-1 секций `[Peer]`. Четыре узла — это всего шесть туннелей; десять узлов — 45. У каждого узла публичный IP, так что `PersistentKeepalive` обычно не нужен; подробности — в руководстве по keepalive и PresharedKey.

  1. 01.На каждом узле выполните `apt install wireguard`, затем `umask 077; wg genkey | tee /etc/wireguard/wg0.key | wg pubkey > /etc/wireguard/wg0.pub`.
  2. 02.Соберите все публичные ключи и план адресов в одном месте.
  3. 03.При желании сгенерируйте по одному ключу `wg genpsk` на каждую пару узлов для постквантовой страховки.
  4. 04.Напишите `/etc/wireguard/wg0.conf` на каждом узле, как показано ниже.
  5. 05.Выполните `systemctl enable --now wg-quick@wg0` и проверьте в `wg show`, что с каждым пиром есть свежее рукопожатие.
# /etc/wireguard/wg0.conf on node1
[Interface]
Address = 10.88.0.1/24
ListenPort = 51820
PrivateKey = <node1 private key>

[Peer]
# node2
PublicKey = <node2 public key>
Endpoint = 203.0.113.12:51820
AllowedIPs = 10.88.0.2/32

[Peer]
# node3
PublicKey = <node3 public key>
Endpoint = 203.0.113.13:51820
AllowedIPs = 10.88.0.3/32

[Peer]
# node4
PublicKey = <node4 public key>
Endpoint = 203.0.113.14:51820
AllowedIPs = 10.88.0.4/32

Как работает AllowedIPs в mesh-сети

`AllowedIPs` выполняет сразу две задачи. На выходе это таблица маршрутизации: пакеты для `10.88.0.3` идут пиру, у которого указан `10.88.0.3/32`. На входе это список доступа: пакет от этого пира принимается, только если его адрес источника входит в `AllowedIPs` этого пира. Поэтому каждый пир получает ровно свой `/32`, а не весь `/24`.

`/24` в строке `Address` лишь создаёт маршрут ядра для подсети на `wg0`; дальше WireGuard сам выбирает нужного пира по адресу назначения.

  • ▹У двух пиров на одном интерфейсе никогда не должно быть пересекающихся диапазонов `AllowedIPs`; побеждает последний.
  • ▹Если узел ещё и маршрутизирует приватную подсеть (например, Docker на node3), добавьте эту подсеть в `AllowedIPs` для node3 на остальных узлах.
  • ▹Не указывайте `0.0.0.0/0` у пира в mesh-сети, если только действительно не хотите, чтобы весь трафик уходил через этот узел.

Файрвол: до туннеля добираются только ваши узлы

WireGuard не отвечает на неаутентифицированные пакеты, но ограничение UDP 51820 известными IP узлов всё равно уменьшает шум. Внутри туннеля открывайте только те порты, что нужны каждому сервису. Этот пример nftables для Debian 12/13 и Ubuntu 24.04 кладётся в `/etc/nftables.conf`; загрузите его через `nft -f /etc/nftables.conf` и включите `nftables.service`. Во время проверки держите открытой SSH-сессию.

table inet filter {
  set mesh_peers {
    type ipv4_addr
    elements = { 203.0.113.11, 203.0.113.12, 203.0.113.13, 203.0.113.14 }
  }
  chain input {
    type filter hook input priority 0; policy drop;
    ct state established,related accept
    iif lo accept
    meta l4proto { icmp, ipv6-icmp } accept
    tcp dport 22 accept
    udp dport 51820 ip saddr @mesh_peers accept
    iifname "wg0" ip saddr 10.88.0.0/24 tcp dport { 5432, 6379, 9100 } accept
  }
}

Привязывайте сервисы к интерфейсу wg

Файрвол — один слой; второй — вообще не слушать публичный адрес. Привязывайте внутренние сервисы к адресу `wg0` узла, чтобы ошибка в файрволе не открыла их наружу. Поскольку `wg0` должен существовать до того, как сервис займёт адрес, упорядочьте unit-ы через drop-in systemd или разрешите привязку к ещё не поднятым адресам через `net.ipv4.ip_nonlocal_bind = 1`.

# PostgreSQL on node3: postgresql.conf
listen_addresses = '10.88.0.3'
# pg_hba.conf
host  all  all  10.88.0.0/24  scram-sha-256

# Redis: /etc/redis/redis.conf
bind 10.88.0.3

# systemctl edit postgresql  (repeat for other services)
[Unit]
[email protected]
[email protected]

Note · Проверьте результат через `ss -tlnp`: внутренние сервисы должны показывать `10.88.0.x`, но никогда `0.0.0.0` или публичный IP.

Масштабирование: когда переходить на инструменты

Mesh-сеть, написанная вручную, годится, пока узлов мало и изменения редки. Каждый новый узел означает правку всех существующих конфигов, так что объём работы растёт квадратично. Когда это становится рутиной, генерируйте конфиги, а не пишите их.

В NoctisNode все новые VPS-узлы разворачиваются в FI-1 (Финляндия), у каждого выделенный IPv4 и безлимитный порт 1 Gbps, а почасовой биллинг и агентский API (с автоудалением по TTL) делают добавление и удаление тестовых узлов дешёвым. Тарифы начинаются с Wisp; см. тарифы VPS.

Размер кластераПодход
2–5 узловКонфиги вручную, план адресов в текстовом файле
5–15 узловAnsible или другой инструмент конфигурации, генерирующий wg0.conf по шаблону из одного инвентаря
15+ узлов или частые измененияMesh-менеджер, автоматически раздающий ключи и пиров, или схема hub-and-spoke

FAQ

QКак объединить несколько VPS в приватную сеть?

AУстановите WireGuard на каждый VPS, дайте каждому узлу адрес из одной приватной подсети и укажите каждый другой узел как пира с его публичным endpoint и AllowedIPs /32. Затем привяжите внутренние сервисы к адресу WireGuard.

QНужен ли VPN-узлам в mesh-сети WireGuard PersistentKeepalive?

AОбычно нет: у каждого VPS-узла публичный IP, и до него можно достучаться напрямую. Добавляйте `PersistentKeepalive = 25` только для узла за NAT.

QКаким должен быть AllowedIPs для каждого VPS-узла?

AКаждый пир получает только свой адрес WireGuard как /32, плюс подсети, которые маршрутизирует этот узел. Если указать всю подсеть кластера для каждого пира, маршруты пересекутся и mesh-сеть сломается.

QСколько узлов может быть в mesh-сети WireGuard?

AСам WireGuard справляется с множеством пиров, но полная mesh-сеть, поддерживаемая вручную, становится утомительной примерно после десяти узлов, потому что каждому узлу нужны конфиги всех остальных. Дальше генерируйте конфиги автоматически или используйте mesh-менеджер.

Приватный кластер VPS на mesh-сети WireGuard · NoctisNode