This project is not affiliated with or endorsed by MikroTik / SIA Mikrotikls
Легковесный Docker-контейнер, который позволяет MikroTik подключаться к серверам AmneziaWG. Весь трафик шифруется нативным WireGuard-клиентом роутера, а контейнер только преобразует формат пакетов.
- Как это работает
- Быстрый старт (конфигуратор)
- Требования
- Ручная установка
- Получение параметров AWG
- Дополнительные настройки
- Запуск на Windows (Standalone)
- Удаление
- Устранение неполадок
- Сборка из исходников
- Лицензия
MikroTik WG-клиент ──UDP──> [awg-proxy] ──UDP──> сервер AmneziaWG
(шифрование) (преобразование) (обфускация)
Прокси заменяет заголовки пакетов, добавляет паддинг и мусорные пакеты так, чтобы сервер AmneziaWG принял трафик. Ключи и данные не затрагиваются.
Совместим с AWG v1 и v2 -- версия определяется автоматически по переменным окружения.
- Экспортируйте
.conf-файл из AmneziaVPN (см. Получение параметров AWG) - Откройте конфигуратор
- Вставьте содержимое
.conf-файла - Скопируйте сгенерированные команды и выполните их в терминале MikroTik
Готово. Конфигуратор работает оффлайн, данные не отправляются на сервер.
awg-proxy-test1.mp4
Замеры скорости на устройстве MikroTik AX3
- Сервер AmneziaWG с известными параметрами обфускации
- Файл конфигурации
.conf, экспортированный из AmneziaVPN - MikroTik RouterOS 7.4+ с пакетом container
- RouterOS 7.21+: стандартные образы
awg-proxy-{arch}.tar.gz(OCI-формат) - RouterOS 7.20 и ниже: образы
awg-proxy-{arch}-7.20-Docker.tar.gz(Docker-формат) - Конфигуратор определяет версию автоматически
- RouterOS 7.21+: стандартные образы
- Архитектура: ARM64, ARM (v7) или x86_64 (проверить устройство)
- Минимум 5 МБ свободного места на диске (или USB-накопитель)
- Минимум 16 МБ свободной оперативной памяти (RAM)
Установите пакет container с mikrotik.com, загрузите на роутер и перезагрузитесь. Затем:
/system/device-mode/update container=yes
Роутер попросит подтверждение (кнопка или перезагрузка, зависит от модели).
Скачайте awg-proxy-{arch}.tar.gz со страницы Releases и загрузите на роутер через Winbox или SCP. Для RouterOS 7.20 и ниже используйте файлы с суффиксом -7.20-Docker (Docker-формат).
Или скачайте прямо на роутер (замените URL на актуальный):
/tool/fetch url="https://github.com/timbrs/amneziawg-mikrotik/releases/latest/download/awg-proxy-arm64.tar.gz" dst-path=awg-proxy-arm64.tar.gz
/interface/veth/add name=veth-awg-proxy address=172.18.0.2/30 gateway=172.18.0.1
/ip/address/add address=172.18.0.1/30 interface=veth-awg-proxy
/ip/firewall/nat/add chain=srcnat action=masquerade src-address=172.18.0.0/30
/interface/wireguard/add name=wg-awg-proxy private-key="YOUR_PRIVATE_KEY" listen-port=12429
/interface/wireguard/peers/add interface=wg-awg-proxy public-key="SERVER_PUBLIC_KEY" \
preshared-key="YOUR_PRESHARED_KEY" endpoint-address=172.18.0.2 endpoint-port=51820 \
allowed-address=0.0.0.0/0 persistent-keepalive=25
/ip/address/add address=YOUR_TUNNEL_IP interface=wg-awg-proxy
Замените:
YOUR_PRIVATE_KEY-- PrivateKey из[Interface]SERVER_PUBLIC_KEY-- PublicKey из[Peer]YOUR_PRESHARED_KEY-- PresharedKey из[Peer](если есть)YOUR_TUNNEL_IP-- Address из[Interface](например,10.8.0.2/32)
/container/envs/add list=awg-proxy-env key=AWG_LISTEN value=":51820"
/container/envs/add list=awg-proxy-env key=AWG_REMOTE value="SERVER_IP:PORT"
/container/envs/add list=awg-proxy-env key=AWG_JC value="5"
/container/envs/add list=awg-proxy-env key=AWG_JMIN value="30"
/container/envs/add list=awg-proxy-env key=AWG_JMAX value="500"
/container/envs/add list=awg-proxy-env key=AWG_S1 value="20"
/container/envs/add list=awg-proxy-env key=AWG_S2 value="20"
/container/envs/add list=awg-proxy-env key=AWG_H1 value="1234567890"
/container/envs/add list=awg-proxy-env key=AWG_H2 value="1234567891"
/container/envs/add list=awg-proxy-env key=AWG_H3 value="1234567892"
/container/envs/add list=awg-proxy-env key=AWG_H4 value="1234567893"
/container/envs/add list=awg-proxy-env key=AWG_SERVER_PUB value="SERVER_PUBLIC_KEY"
/container/envs/add list=awg-proxy-env key=AWG_CLIENT_PUB value=[/interface/wireguard/get [find name=wg-awg-proxy] public-key]
Замените все значения на параметры из вашего .conf-файла. AWG_CLIENT_PUB берется автоматически из WireGuard-интерфейса.
/container/add file=awg-proxy-arm64.tar.gz interface=veth-awg-proxy envlist=awg-proxy-env \
hostname=awg-proxy root-dir=disk1/awg-proxy logging=yes shm-size=4M start-on-boot=yes
/container/start [find where tag~"awg-proxy"]
Проверьте работу:
/container/print
/interface/wireguard/peers/print
Контейнер должен быть в статусе running, а у пира должно появиться значение last-handshake.
- Откройте приложение AmneziaVPN
- Выберите нужное подключение
- Нажмите Поделиться (Share)
- Выберите: Протокол: AmneziaWG, Формат: AmneziaWG Format
- Сохраните
.conf-файл
Параметры обфускации (Jc, Jmin, Jmax, S1, S2, H1--H4) находятся в секции [Interface], а Endpoint и PublicKey -- в секции [Peer].
| Переменная | Обязательная | Описание |
|---|---|---|
AWG_LISTEN |
Да | Адрес прослушивания (например, :51820) |
AWG_REMOTE |
Да | Адрес AWG-сервера -- Endpoint из [Peer] (например, 1.2.3.4:443) |
AWG_JC |
Да | Количество мусорных пакетов (Jc из .conf) |
AWG_JMIN |
Да | Минимальный размер мусорного пакета (Jmin) |
AWG_JMAX |
Да | Максимальный размер мусорного пакета (Jmax) |
AWG_S1 |
Да | Паддинг handshake init в байтах (S1) |
AWG_S2 |
Да | Паддинг handshake response в байтах (S2) |
AWG_H1 |
Да | Тип handshake init (H1); может быть диапазоном min-max для v2 |
AWG_H2 |
Да | Тип handshake response (H2); может быть диапазоном для v2 |
AWG_H3 |
Да | Тип cookie reply (H3); может быть диапазоном для v2 |
AWG_H4 |
Да | Тип transport data (H4); может быть диапазоном для v2 |
AWG_SERVER_PUB |
Да | Публичный ключ сервера, base64 (PublicKey из [Peer]) |
AWG_CLIENT_PUB |
Да | Публичный ключ клиента, base64 |
AWG_S3 |
Нет | Паддинг cookie reply в байтах (v2) |
AWG_S4 |
Нет | Паддинг transport data в байтах (v2) |
AWG_I1--AWG_I5 |
Нет | CPS-шаблоны (v1.5/v2); до 5 шаблонов |
AWG_SRC_PORT |
Нет | Source-порт для подключения к серверу. Не задан или 0 -- auto-режим: порт берётся из первого пакета клиента (MikroTik WG). 1--65535 -- статический порт. Используется для NAT hole punching: прокси подключается к серверу с тем же src-портом, что и MikroTik, что позволяет потом переключиться на прямое соединение без прокси (по умолчанию: auto) |
AWG_TIMEOUT |
Нет | Таймаут бездействия в секундах (по умолчанию: 180) |
AWG_LOG_LEVEL |
Нет | none, error, info, debug (по умолчанию: info) |
AWG_SOCKET_BUF |
Нет | Размер буфера сокета в байтах (по умолчанию: 16777216 = 16 МБ) |
AWG_GOMAXPROCS |
Нет | Количество потоков Go (по умолчанию: 2) |
Версия протокола определяется автоматически: v2 если заданы S3/S4 или H в виде диапазонов, v1.5 если заданы CPS-шаблоны (I1-I5), иначе v1.
Конкретный хост:
/ip/route/add dst-address=8.8.8.8/32 gateway=wg-awg-proxy
Подсеть:
/ip/route/add dst-address=10.0.0.0/8 gateway=wg-awg-proxy
Просмотр маршрутов:
/ip/route/print where gateway=wg-awg-proxy
Удаление маршрута:
/ip/route/remove [find where dst-address="8.8.8.8/32" gateway="wg-awg-proxy"]
Чтобы DNS-запросы шли через туннель, укажите DNS-сервер и добавьте маршрут к нему:
/ip/dns/set servers=8.8.8.8,8.8.4.4
/ip/route/add dst-address=8.8.8.8/32 gateway=wg-awg-proxy
/ip/route/add dst-address=8.8.4.4/32 gateway=wg-awg-proxy
Для выборочной маршрутизации трафика через туннель используйте routing table и mangle rules.
Создание routing table:
/routing/table/add disabled=no fib name=r_to_vpn
Маршрут по умолчанию через туннель для этой таблицы:
/ip/route/add dst-address=0.0.0.0/0 gateway=wg-awg-proxy routing-table=r_to_vpn
Address-list с адресами, которые нужно направить через туннель:
/ip/firewall/address-list/add address=8.8.8.8 list=to_vpn
/ip/firewall/address-list/add address=1.1.1.1 list=to_vpn
Mangle rules для маркировки трафика:
# Пропускаем локальный трафик
/ip/firewall/mangle/add chain=prerouting action=accept dst-address=10.0.0.0/8
/ip/firewall/mangle/add chain=prerouting action=accept dst-address=172.16.0.0/12
/ip/firewall/mangle/add chain=prerouting action=accept dst-address=192.168.0.0/16
# Маркируем соединения к адресам из списка
/ip/firewall/mangle/add chain=prerouting action=mark-connection \
dst-address-list=to_vpn connection-mark=no-mark \
new-connection-mark=to-vpn-conn passthrough=yes
# Маркируем маршрутизацию для отмеченных соединений
/ip/firewall/mangle/add chain=prerouting action=mark-routing \
connection-mark=to-vpn-conn new-routing-mark=r_to_vpn passthrough=yes
NAT для маркированного трафика:
/ip/firewall/nat/add chain=srcnat action=masquerade routing-mark=r_to_vpn
Теперь весь трафик к адресам из списка to_vpn будет идти через туннель. Добавляйте адреса в список по мере необходимости.
Если на роутере нет поддержки контейнеров (RouterOS Lite, мало памяти) или нужно сохранить существующий WireGuard-интерфейс, awg-proxy можно запустить на любом Windows-компьютере в локальной сети.
MikroTik WG-клиент ──UDP──> [awg-proxy на Windows] ──UDP──> сервер AmneziaWG
(192.168.1.1) (192.168.1.100:51820) (внешний IP:порт)
Скачайте awg-proxy-windows-amd64.exe со страницы Releases.
Все параметры берутся из .conf-файла AmneziaWG. Замените значения на свои.
PowerShell:
$env:AWG_LISTEN = ":51820"
$env:AWG_REMOTE = "SERVER_IP:PORT"
$env:AWG_JC = "5"
$env:AWG_JMIN = "30"
$env:AWG_JMAX = "500"
$env:AWG_S1 = "20"
$env:AWG_S2 = "20"
$env:AWG_H1 = "1234567890"
$env:AWG_H2 = "1234567891"
$env:AWG_H3 = "1234567892"
$env:AWG_H4 = "1234567893"
$env:AWG_SERVER_PUB = "SERVER_PUBLIC_KEY_BASE64"
$env:AWG_CLIENT_PUB = "CLIENT_PUBLIC_KEY_BASE64"
.\awg-proxy-windows-amd64.exeCMD:
set AWG_LISTEN=:51820
set AWG_REMOTE=SERVER_IP:PORT
set AWG_JC=5
set AWG_JMIN=30
set AWG_JMAX=500
set AWG_S1=20
set AWG_S2=20
set AWG_H1=1234567890
set AWG_H2=1234567891
set AWG_H3=1234567892
set AWG_H4=1234567893
set AWG_SERVER_PUB=SERVER_PUBLIC_KEY_BASE64
set AWG_CLIENT_PUB=CLIENT_PUBLIC_KEY_BASE64
awg-proxy-windows-amd64.exe
AWG_CLIENT_PUB-- публичный ключ WireGuard-клиента на MikroTik. Его можно получить командой/interface/wireguard/printна роутере.
Используйте конфигуратор в режиме MikroTik + Server (Standalone), указав IP Windows-машины. Конфигуратор сгенерирует все нужные команды для роутера.
Или вручную: создайте WireGuard-интерфейс с endpoint-address=IP_WINDOWS_МАШИНЫ и endpoint-port=51820.
Разрешите входящий UDP-трафик на порт 51820. В PowerShell от администратора:
New-NetFirewallRule -DisplayName "awg-proxy" -Direction Inbound -Protocol UDP -LocalPort 51820 -Action AllowДля автоматического запуска при старте Windows создайте bat-файл с переменными окружения и командой запуска, затем добавьте его в планировщик задач или в автозагрузку.
Или создайте Windows-службу через NSSM:
nssm install awg-proxy "C:\path\to\awg-proxy-windows-amd64.exe"
nssm set awg-proxy AppEnvironmentExtra AWG_LISTEN=:51820 AWG_REMOTE=SERVER_IP:PORT ...
nssm start awg-proxyЕсли установка была через конфигуратор:
/system/script/run awg-proxy-uninstall
Скрипт удалит контейнер, WireGuard-интерфейс, правила NAT, маршруты, переменные окружения, восстановит DNS и удалит себя.
Контейнер не запускается -- проверьте установку пакета container (/system/package/print), режим устройства (/system/device-mode/print) и свободное место (/system/resource/print).
Нет рукопожатия -- убедитесь, что все параметры AWG (Jc, Jmin, Jmax, S1, S2, H1--H4) точно совпадают с сервером. Проверьте AWG_REMOTE, AWG_SERVER_PUB и AWG_CLIENT_PUB.
Нет трафика после рукопожатия -- проверьте правило NAT (/ip/firewall/nat/print), маршрутизацию и endpoint-address пира (должен быть 172.18.0.2).
Контейнер перезапускается -- установите AWG_LOG_LEVEL=info и проверьте логи. Частая причина -- отсутствующие переменные окружения.
Если при установке появляется ошибка Storage device usb1 not found or has 0 free space -- диск не отформатирован или имя точки монтирования не совпадает.
- Проверьте доступные диски:
/disk/print
- Если диск виден как block-устройство, но без раздела -- отформатируйте его в ext4:
/disk/format-drive usb1 file-system=ext4 label=usb1
- После форматирования диск будет доступен как mount-point (обычно
usb1). Проверьте имя через/disk/printи используйте его в конфигураторе (поле "Container storage").
Важно: Контейнеры требуют файловую систему ext4. FAT32 не подходит.
Если при установке контейнера возникает ошибка Insufficient disk space, а на внешнем накопителе (USB, SD, NVMe) есть свободное место -- перенастройте директорию для загрузки образов:
/container/config set tmpdir=usb1/pull ram-high=200M
Замените usb1 на mount-point вашего накопителя (см. /disk/print).
После установки контейнера можно вернуть значение обратно:
/container/config set tmpdir="" ram-high=0
Если используете конфигуратор -- выберите нужный накопитель в поле "Container storage", и tmpdir будет настроен автоматически.
Если при загрузке образа или создании контейнера появляется ошибка not allowed by device-mode, значит контейнеры не активированы. Выполните:
/system/device-mode/update container=yes
Роутер попросит подтверждение -- нажмите кнопку Reset или Mode на корпусе (зависит от модели) в течение нескольких минут, либо дождитесь автоматической перезагрузки. После перезагрузки повторите установку.
На устройствах с 16 МБ flash (hAP ac2, hEX и др.) контейнер может не запускаться с ошибками:
child spawn failed: container run errorилиexited with status 255(RouterOS 7.20)download/extract error: could not load next layer(RouterOS 7.21+)
Чек-лист:
-
Формат образа -- убедитесь, что используете правильный формат:
- RouterOS 7.21+:
awg-proxy-{arch}.tar.gz(OCI) - RouterOS 7.20 и ниже:
awg-proxy-{arch}-7.20-Docker.tar.gz(Docker)
- RouterOS 7.21+:
-
tmpdir на USB -- без этого RouterOS распаковывает образ на внутреннюю flash, которой не хватает (замените
usb1на ваш mount-point из/disk/print):/container/config set tmpdir=usb1/pull -
root-dir -- указывайте путь к папке на USB, но не создавайте её вручную (RouterOS создаст её сам):
/container add ... root-dir=usb1/awg-proxy -
Формат USB -- отформатируйте накопитель в ext4:
/disk/format-drive usb1 file-system=ext4 label=usb1 -
Загрузка из файла -- на устройствах с 16 МБ flash загружайте образ через файл, а не remote-image:
/container add file=awg-proxy-arm.tar.gz ...
Требуется Go 1.25+, Docker (для контейнерных образов) и make.
# Тесты
make test
# Локальная сборка бинарника
make build
# Docker-образы (OCI, для RouterOS 7.21+)
make docker-arm64 # ARM64
make docker-arm # ARM v7
make docker-armv5 # ARM v5
make docker-amd64 # x86_64
make docker-all # Все архитектуры
# Docker-образы (классический формат, для RouterOS 7.20 и ниже)
make docker-arm64-7.20-docker
make docker-arm-7.20-docker
make docker-armv5-7.20-docker
make docker-amd64-7.20-docker
make docker-all-7.20-docker
# Windows-бинарник (Standalone)
make binary-windows-amd64Артефакты создаются в директории builds/.
$env:CGO_ENABLED = "0"
go build -trimpath -ldflags="-s -w" -o builds/awg-proxy.exe .Для кросс-компиляции Linux-бинарников на Windows:
$env:CGO_ENABLED = "0"; $env:GOOS = "linux"; $env:GOARCH = "arm64"
go build -trimpath -ldflags="-s -w" -o builds/awg-proxy-linux-arm64 .MIT -- см. LICENSE.
