Настройка VPN (vless xhttp)

Настройка VPN (vless xhttp)

Serv.Host

Что понадобится перед началом

  • приложение для подключения по SSH;
  • домен;
  • два VPS-сервера: один в России, второй — за рубежом.

Сначала необходимо установить приложение для подключения по SSH, чтобы получить доступ к серверам и выполнить настройку VPN.

Перейдите в браузер и откройте сайт https://www.chiark.greenend.org.uk/~sgtatham/putty/latest.html. Скачайте программу PuTTY для вашей операционной системы.

В большинстве случаев подойдёт версия для Windows x64.


После этого установите PuTTY на компьютер.

Во время установки нажимайте Next, затем Finish. При необходимости можно снять флажок View README file.



Далее перейдите на сайт https://active.domains/domains/ и приобретите домен.

Выберите зону .ru, укажите любое свободное доменное имя и завершите покупку. После этого зарегистрируйтесь на сайте Cloudflare и добавьте туда купленный домен с помощью кнопки Add и пункта Connect domain. Затем в панели управления доменного регистратора замените NS-записи на те, которые выдаст Cloudflare. (обновление ns записей может занимать до 24х часов)

Теперь можно перейти к покупке VPS-серверов. Откройте сайт https://my.serv.host/, зарегистрируйтесь и приобретите два сервера: один в России, второй — в Германии.

сервер в России
сервер в Германии

При заказе сервера в России и сервера в Германии в качестве операционной системы выберите Debian 12. В поле доменного имени можно указать ваш домен либо оставить его пустым. После оформления заказа на электронную почту придут данные для входа по SSH. Затем откройте программу PuTTY.

Все дальнейшие действия на этом этапе необходимо выполнять на сервере, расположенном в России.

В поле Host Name укажите IP-адрес вашего VPS-сервера и нажмите Open. Затем введите логин root и пароль, полученный в письме.

После этого выполните следующие команды.

apt update && apt full-upgrade -y && apt install sudo certbot python3-certbot-nginx nginx ufw -y
ufw allow 22/tcp
ufw allow 80/tcp
ufw allow 443/tcp
ufw enable


Теперь перейдите в Cloudflare. Обновление NS-записей может занять до 24 часов. Как только NS-записи обновятся, откройте панель управления доменом и в разделе DNS records создайте нужную DNS-запись, например up.вашдомен.

Затем снова вернитесь к серверу и начните установку панели для VPN. Для этого выполните следующие команды.


Установите Docker.

sudo curl -fsSL https://get.docker.com | sh


Теперь необходимо выпустить сертификат для домена, который был привязан к серверу в России.

Введите следующую команду.

certbot --nginx -d up.вашдомен


Установка Marzban выполняется следующей командой.

sudo bash -c "$(curl -sL https://github.com/Gozargah/Marzban-scripts/raw/master/marzban.sh)" @ install


Далее необходимо обновить core.

Введите команду 

marzban core-update

Теперь создайте администратора панели.

marzban cli admin create --sudo

Укажите имя пользователя и дважды введите пароль. Во время ввода пароль отображаться не будет — это нормально. Остальные поля при необходимости можно пропустить, просто нажав Enter.


Теперь откройте на компьютере cmd. Для этого нажмите Win + R, введите cmd и нажмите Enter.

В командной строке выполните следующую команду.

ssh -L 8000:localhost:8000 root@<IP вашего сервера>

После этого откройте браузер и перейдите по адресу

127.0.0.1:8000/dashboard
панель которую вы увидите

Откроется панель входа. Введите данные пользователя, которого вы создали ранее.

Снова перейдите в консоль и выполните следующие команды.

mkdir /var/www/html/site
nano /var/www/html/site/index.html

В открывшемся окне вставьте следующий HTML-код.

<!DOCTYPE html>
<html lang="ru">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0">
    <title>Beszel - Sign In</title>
    <script src="https://unpkg.com/lucide@latest"></script>
    <style>
        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
            font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
            -webkit-tap-highlight-color: transparent;
        }

        body {
            background-color: #0b0c0e;
            color: #ffffff;
            min-height: 100vh;
            display: flex;
            justify-content: center;
            align-items: center;
            padding: 20px;
        }

        .login-container {
            width: 100%;
            max-width: 380px;
            text-align: center;
        }

        h1 {
            font-size: 2rem;
            margin-bottom: 8px;
            font-weight: 700;
        }

        .subtitle {
            color: #71717a;
            margin-bottom: 24px;
            font-size: 0.9rem;
        }

        .input-group {
            position: relative;
            margin-bottom: 16px;
        }

        .input-icon {
            position: absolute;
            left: 12px;
            top: 50%;
            transform: translateY(-50%);
            color: #71717a;
            width: 18px;
            height: 18px;
        }

        input {
            width: 100%;
            padding: 12px 12px 12px 40px;
            background: #111214;
            border: 1px solid #27272a;
            border-radius: 8px;
            color: white;
            outline: none;
            font-size: 16px;
            transition: border-color 0.2s;
        }

        input:focus {
            border-color: #52525b;
        }

        .btn-signin {
            width: 100%;
            padding: 12px;
            background-color: #ffffff;
            color: #000000;
            border: none;
            border-radius: 8px;
            font-weight: 600;
            cursor: pointer;
            display: flex;
            justify-content: center;
            align-items: center;
            gap: 8px;
            font-size: 0.95rem;
            transition: background 0.2s;
        }

        .btn-signin:hover { background-color: #e4e4e7; }
        .btn-signin:active { transform: scale(0.98); }

        .divider {
            margin: 24px 0;
            display: flex;
            align-items: center;
            color: #71717a;
            font-size: 0.75rem;
            font-weight: 500;
        }

        .divider::before, .divider::after {
            content: "";
            flex: 1;
            height: 1px;
            background: #27272a;
        }
        .divider span { padding: 0 10px; }

        .btn-github {
            width: 100%;
            padding: 12px;
            background: #111214;
            border: 1px solid #27272a;
            color: white;
            border-radius: 8px;
            cursor: pointer;
            display: flex;
            justify-content: center;
            align-items: center;
            gap: 8px;
            font-size: 0.95rem;
            transition: background 0.2s;
        }

        .btn-github:hover { background: #18181b; }

        .forgot-wrapper {
            margin-top: 24px;
        }
        
        .forgot-password {
            color: #a1a1aa;
            text-decoration: none;
            font-size: 0.85rem;
            padding: 8px;
            border-bottom: 1px solid transparent;
            transition: all 0.3s ease;
        }

        .forgot-password:hover { 
            color: #ffffff;
            border-bottom: 1px solid #ffffff;
        }

        #error-msg {
            color: #f87171;
            font-size: 0.85rem;
            margin-bottom: 15px;
            display: none;
            background: rgba(248, 113, 113, 0.1);
            padding: 8px;
            border-radius: 6px;
        }
    </style>
</head>
<body>

    <div class="login-container">
        <h1>Beszel</h1>
        <p class="subtitle">Please sign in to your account</p>

        <div id="error-msg"></div>

        <form id="loginForm">
            <div class="input-group">
                <i data-lucide="mail" class="input-icon"></i>
                <input type="text" id="email" placeholder="name@example.com" required>
            </div>
            <div class="input-group">
                <i data-lucide="lock" class="input-icon"></i>
                <input type="password" id="password" placeholder="password" required>
            </div>
            
            <button type="submit" class="btn-signin">
                <i data-lucide="arrow-right" style="width: 16px;"></i> Sign in
            </button>
        </form>

        <div class="divider">
            <span>OR CONTINUE WITH</span>
        </div>

        <button class="btn-github" onclick="alert('GitHub login is not available.')">
            <i data-lucide="github" style="width: 16px;"></i> GitHub
        </button>

        <div class="forgot-wrapper">
            <a href="#" class="forgot-password" onclick="alert('Redirecting to recovery...')">Forgot password?</a>
        </div>
    </div>

    <script>
        lucide.createIcons();

        document.getElementById('loginForm').addEventListener('submit', function(e) {
            e.preventDefault(); 
            
            const emailInput = document.getElementById('email').value;
            const errorMsg = document.getElementById('error-msg');
            const emailPattern = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;

            if (!emailPattern.test(emailInput)) {
                errorMsg.textContent = "Please enter a valid email address.";
                errorMsg.style.display = 'block';
            } else {
                errorMsg.textContent = "Invalid email or password.";
                errorMsg.style.display = 'block';
            }
            
            document.getElementById('password').value = '';
        });
    </script>
</body>
</html>

Нажмите Ctrl + X, затем Y и Enter, чтобы сохранить файл.

После этого выполните следующие команды.

rm /etc/nginx/sites-enabled/default
nano /etc/nginx/sites-available/sni.conf

В файл sni.conf вставьте следующий конфиг.

server {
  listen 80;
  server_name up.вашдомен;

  if ($host = up.вашдомен) {
    return 301 https://$host$request_uri;
  }

  return 404;
}

server {
  listen 127.0.0.1:9999 ssl http2;
  server_name up.вашдомен;

  ssl_certificate /etc/letsencrypt/live/up.вашдомен/fullchain.pem;
  ssl_certificate_key /etc/letsencrypt/live/up.вашдомен/privkey.pem;

  ssl_protocols TLSv1.2 TLSv1.3;
  ssl_prefer_server_ciphers on;

  ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305';
  ssl_session_cache shared:SSL:1m;
  ssl_session_timeout 1d;
  ssl_session_tickets off;

  root /var/www/html/site;
  index index.html;

  location / {
    try_files $uri $uri/ =404;
  }
}

Нажмите Ctrl + X, затем Y и Enter, чтобы сохранить файл.


После этого выполните следующие команды.

ln -s /etc/nginx/sites-available/sni.conf /etc/nginx/sites-enabled/
systemctl restart nginx

И

docker exec marzban-marzban-1 xray x25519
openssl rand -hex 8

В результате будут получены значения publicKey, privateKey и shortid. Они понадобятся на следующих этапах настройки.


Теперь вернитесь в панель.

Нажмите на значок шестерёнки и вместо следующего блока вставьте новый.

{
   "tag": "Shadowsocks TCP",
   "listen": "0.0.0.0",
   "port": 1080,
   "protocol": "shadowsocks",
   "settings": {
    "clients": [],
    "network": "tcp,udp"
   }
  } 

Вставляем

{
   "tag": "xhttp",
   "listen": "0.0.0.0",
   "port": 443,
   "protocol": "vless",
   "settings": {
    "clients": [],
    "decryption": "none"
   },
   "streamSettings": {
    "network": "xhttp",
    "xhttpSettings": {
     "mode": "auto"
    },
    "security": "reality",
    "realitySettings": {
     "show": false,
     "dest": "127.0.0.1:9999",
     "xver": 0,
     "serverNames": [
      "up.вашдомен"
     ],
     "privateKey": "поменять",
     "publicKey": "поменять",
     "SpiderX": "/",
     "shortIds": [
      "поменять"
     ]
    }
   },
   "sniffing": {
    "enabled": true,
    "destOverride": [
     "http",
     "tls",
     "quic"
    ]
   }
  }


Далее перейдите к зарубежному серверу. Подключитесь к нему по SSH через PuTTY и выполните необходимые команды.


apt update && apt full-upgrade -y && apt install sudo ufw -y
ufw allow 22/tcp
ufw allow from (Ip сервера) to any port 1080
ufw enable

Установите Docker.

sudo curl -fsSL https://get.docker.com | sh

Установка Marzban выполняется следующей командой.

sudo bash -c "$(curl -sL https://github.com/Gozargah/Marzban-scripts/raw/master/marzban.sh)" @ install

Затем обновите core.

Введите команду marzban core-update


После этого создайте администратора панели.

marzban cli admin create --sudo


Теперь снова откройте на компьютере cmd. Для этого нажмите Win + R, введите cmd и нажмите Enter.

В командной строке выполните следующую команду.

ssh -L 8001:localhost:8000 root@<IP вашего сервера>

После этого откройте браузер и перейдите по адресу

127.0.0.1:8001/dashboard


Таким образом, в браузере будут доступны две панели.


Во второй панели необходимо создать ключ для VPN, а затем вставить его в приложение v2rayTUN.

Укажите любое название и скопируйте ключ.

Откройте v2rayTUN, нажмите на + и выберите пункт вставки из буфера обмена.

После этого нажмите на кнопку из скриншота и просмотрите параметры подключения.

Понадобятся IP-адрес и пароль.

Скопируйте их и сохраните в текстовый файл.


Теперь вернитесь в панель на сервере в России.

"outbounds": [
  {
   "protocol": "freedom",
   "tag": "DIRECT"
  },
  {
   "protocol": "blackhole",
   "tag": "BLOCK"
  }
 ]

В блоке outbounds найдите нужный фрагмент и добавьте следующий блок.

{
 "tag": "shadowsocks",
 "protocol": "shadowsocks",
 "settings": {
  "servers": [
   {
    "address": "ip зарубежного сервера",
    "port": 1080,
    "password": "пароль",
    "method": "chacha20-ietf-poly1305",
    "level": 0
   }
  ]
 }
}

В результате получится следующий вариант.

"outbounds": [
  {
   "protocol": "freedom",
   "tag": "DIRECT"
  },
  {
   "protocol": "blackhole",
   "tag": "BLOCK"
  },
  {
 "tag": "shadowsocks",
 "protocol": "shadowsocks",
 "settings": {
 "servers": [
  {
  "address": "ip зарубежного сервера",
  "port": 1080,
  "password": "пароль",
  "method": "chacha20-ietf-poly1305",
  "level": 0
  }
 ]
 }
}
]

Теперь потребуется блок routing.

"routing": {
  "rules": [
   {
    "ip": [
     "geoip:private"
    ],
    "outboundTag": "BLOCK",
    "type": "field"
   }
  ]
 },

В него необходимо добавить следующий фрагмент.

{
  "inboundTag": ["xhttp"],
  "outboundTag": "shadowsocks"
}

В результате блок будет выглядеть следующим образом.

"routing": {
  "rules": [
   {
    "ip": [
     "geoip:private"
    ],
    "outboundTag": "BLOCK",
    "type": "field"
   },
   {
     "inboundTag": ["xhttp"],
     "outboundTag": "shadowsocks"
   }
  ]
 },

При необходимости можно дополнительно направить отдельные сервисы через российский IP-адрес, например YouTube.

{
        "domain": [
          "geosite:youtube"
        ],
        "outboundTag": "DIRECT"
      },

Этот фрагмент нужно добавить перед следующим блоком.

{
     "inboundTag": ["xhttp"],
     "outboundTag": "shadowsocks"
   }

В результате получится такой вариант.


"routing": {
  "rules": [
   {
    "ip": [
     "geoip:private"
    ],
    "outboundTag": "BLOCK",
    "type": "field"
   },
   {
        "domain": [
          "geosite:youtube"
        ],
        "outboundTag": "DIRECT"
      },
   {
     "inboundTag": ["xhttp"],
     "outboundTag": "shadowsocks"
   }
  ]
 },

Готово. Теперь создайте пользователя.


Укажите любое название, выберите xhttp, а в поле Flow укажите xtls-rprx-vision.

Скопируйте полученную ссылку, вставьте её в приложение v2rayTUN и используйте для подключения.


Готово.






Report Page