Apply inbounds on nodes via Xray with Reality settings and client sync.
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -456,6 +456,21 @@ textarea { resize: vertical; font-family: var(--mono); font-size: 0.85rem; }
|
||||
max-width: 360px;
|
||||
}
|
||||
.actions { width: 1%; white-space: nowrap; }
|
||||
.section-sub {
|
||||
margin: 1.25rem 0 0.35rem;
|
||||
font-size: 1rem;
|
||||
font-weight: 600;
|
||||
}
|
||||
.check-row {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 0.5rem;
|
||||
margin: 1rem 0;
|
||||
}
|
||||
input.mono, .mono {
|
||||
font-family: "JetBrains Mono", ui-monospace, monospace;
|
||||
font-size: 0.85rem;
|
||||
}
|
||||
|
||||
@keyframes rise {
|
||||
from { opacity: 0; transform: translateY(12px); }
|
||||
|
||||
@@ -0,0 +1,141 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="ru">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||
<title>{{.Title}} · VPN Panel</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=DM+Sans:ital,opsz,wght@0,9..40,400;0,9..40,500;0,9..40,600;0,9..40,700&family=JetBrains+Mono:wght@400;500&display=swap" rel="stylesheet">
|
||||
<link rel="stylesheet" href="/static/css/app.css">
|
||||
</head>
|
||||
<body class="page-admin">
|
||||
<aside class="sidebar">
|
||||
<a class="brand" href="/admin">VPN Panel</a>
|
||||
<nav>
|
||||
<a href="/admin">Обзор</a>
|
||||
<a href="/admin/clients">Пользователи</a>
|
||||
<a href="/admin/nodes">Ноды</a>
|
||||
<a class="active" href="/admin/profiles">Профили</a>
|
||||
<a href="/admin/protocols">Протоколы</a>
|
||||
</nav>
|
||||
<div class="sidebar-foot">
|
||||
<span class="user-chip">{{.UserName}}</span>
|
||||
<form method="POST" action="/logout"><button type="submit" class="link-btn">Выйти</button></form>
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<main class="admin-main">
|
||||
<header class="admin-header row-head">
|
||||
<div>
|
||||
<h1>Inbound <code>{{.Inbound.Tag}}</code></h1>
|
||||
<p class="muted">Профиль {{.Profile.Name}}</p>
|
||||
</div>
|
||||
<a class="btn btn-ghost" href="/admin/profiles/{{.Profile.ID}}">К профилю</a>
|
||||
</header>
|
||||
|
||||
{{if .Flash}}<div class="alert ok">{{.Flash}}</div>{{end}}
|
||||
{{if .Error}}<div class="alert">{{.Error}}</div>{{end}}
|
||||
|
||||
<section class="panel-section">
|
||||
<form class="form-card" method="POST" action="/admin/profiles/{{.Profile.ID}}/inbounds/{{.Inbound.ID}}">
|
||||
<div class="form-grid">
|
||||
<label>Протокол
|
||||
<select name="protocol_id" required>
|
||||
{{range .Protocols}}
|
||||
<option value="{{.ID}}" {{if eq .ID $.Inbound.ProtocolID}}selected{{end}}>{{.Name}} ({{.Code}})</option>
|
||||
{{end}}
|
||||
</select>
|
||||
</label>
|
||||
<label>Tag
|
||||
<input name="tag" required value="{{.Inbound.Tag}}">
|
||||
</label>
|
||||
<label>Порт
|
||||
<input name="port" type="number" value="{{.Inbound.Port}}">
|
||||
</label>
|
||||
<label>Listen
|
||||
<input name="listen" value="{{.Inbound.Listen}}">
|
||||
</label>
|
||||
<label>Network
|
||||
<select name="network">
|
||||
<option value="tcp" {{if eq .Inbound.Network "tcp"}}selected{{end}}>tcp</option>
|
||||
<option value="ws" {{if eq .Inbound.Network "ws"}}selected{{end}}>ws</option>
|
||||
<option value="grpc" {{if eq .Inbound.Network "grpc"}}selected{{end}}>grpc</option>
|
||||
<option value="quic" {{if eq .Inbound.Network "quic"}}selected{{end}}>quic</option>
|
||||
<option value="udp" {{if eq .Inbound.Network "udp"}}selected{{end}}>udp</option>
|
||||
</select>
|
||||
</label>
|
||||
<label>Security
|
||||
<select name="security">
|
||||
<option value="none" {{if eq .Inbound.Security "none"}}selected{{end}}>none</option>
|
||||
<option value="tls" {{if eq .Inbound.Security "tls"}}selected{{end}}>tls</option>
|
||||
<option value="reality" {{if eq .Inbound.Security "reality"}}selected{{end}}>reality</option>
|
||||
</select>
|
||||
</label>
|
||||
<label>Path / serviceName
|
||||
<input name="path" value="{{.Inbound.Path}}" placeholder="/ws или grpc service">
|
||||
</label>
|
||||
<label>Host header
|
||||
<input name="host" value="{{.Inbound.Host}}">
|
||||
</label>
|
||||
<label>SNI
|
||||
<input name="sni" value="{{.Inbound.SNI}}">
|
||||
</label>
|
||||
<label>Fingerprint
|
||||
<input name="fingerprint" value="{{.Inbound.Fingerprint}}" placeholder="chrome">
|
||||
</label>
|
||||
<label>Flow
|
||||
<input name="flow" value="{{.Inbound.Flow}}" placeholder="xtls-rprx-vision">
|
||||
</label>
|
||||
<label>ALPN
|
||||
<input name="alpn" value="{{.Inbound.ALPN}}" placeholder="h2,http/1.1">
|
||||
</label>
|
||||
<label>Порядок
|
||||
<input name="sort_order" type="number" value="{{.Inbound.SortOrder}}">
|
||||
</label>
|
||||
<label>Заметка
|
||||
<input name="remark" value="{{.Inbound.Remark}}">
|
||||
</label>
|
||||
<label>SS method
|
||||
<input name="ss_method" value="{{.Inbound.SSMethod}}" placeholder="aes-128-gcm">
|
||||
</label>
|
||||
<label>Password (trojan shared, optional)
|
||||
<input name="password" value="{{.Inbound.Password}}">
|
||||
</label>
|
||||
</div>
|
||||
|
||||
<h3 class="section-sub">Reality</h3>
|
||||
<p class="muted">Пустые ключи сгенерируются автоматически при security=reality.</p>
|
||||
<div class="form-grid">
|
||||
<label>Dest
|
||||
<input name="reality_dest" value="{{.Inbound.RealityDest}}" placeholder="www.microsoft.com:443">
|
||||
</label>
|
||||
<label>Server names
|
||||
<input name="reality_server_names" value="{{.Inbound.RealityServerNames}}" placeholder="www.microsoft.com">
|
||||
</label>
|
||||
<label>Private key
|
||||
<input name="reality_private_key" value="{{.Inbound.RealityPrivateKey}}" class="mono">
|
||||
</label>
|
||||
<label>Public key (для клиентов)
|
||||
<input name="reality_public_key" value="{{.Inbound.RealityPublicKey}}" class="mono">
|
||||
</label>
|
||||
<label>Short ID
|
||||
<input name="reality_short_id" value="{{.Inbound.RealityShortID}}" class="mono">
|
||||
</label>
|
||||
</div>
|
||||
|
||||
<label class="check-row">
|
||||
<input type="hidden" name="enabled" value="off">
|
||||
<input type="checkbox" name="enabled" value="on" {{if .Inbound.Enabled}}checked{{end}}>
|
||||
Включён в профиле
|
||||
</label>
|
||||
|
||||
<div class="cta-row">
|
||||
<button class="btn btn-primary" type="submit">Сохранить</button>
|
||||
<a class="btn btn-ghost" href="/admin/profiles/{{.Profile.ID}}">Отмена</a>
|
||||
</div>
|
||||
</form>
|
||||
</section>
|
||||
</main>
|
||||
</body>
|
||||
</html>
|
||||
@@ -81,6 +81,7 @@
|
||||
<td>{{.Security}}</td>
|
||||
<td><span class="badge {{if .Enabled}}on{{else}}off{{end}}">{{if .Enabled}}ON{{else}}OFF{{end}}</span></td>
|
||||
<td class="actions actions-multi">
|
||||
<a class="btn btn-sm btn-ghost" href="/admin/profiles/{{$.Profile.ID}}/inbounds/{{.ID}}">Изменить</a>
|
||||
<form method="POST" action="/admin/profiles/{{$.Profile.ID}}/inbounds/{{.ID}}/toggle">
|
||||
<button class="btn btn-sm btn-ghost" type="submit">{{if .Enabled}}Выкл{{else}}Вкл{{end}}</button>
|
||||
</form>
|
||||
@@ -130,16 +131,44 @@
|
||||
<select name="security">
|
||||
<option value="none">none</option>
|
||||
<option value="tls">tls</option>
|
||||
<option value="reality">reality</option>
|
||||
<option value="reality" selected>reality</option>
|
||||
</select>
|
||||
</label>
|
||||
<label>Path / serviceName
|
||||
<input name="path" placeholder="/ws или grpc service">
|
||||
</label>
|
||||
<label>Host header
|
||||
<input name="host" placeholder="для ws">
|
||||
</label>
|
||||
<label>SNI
|
||||
<input name="sni" placeholder="авто из reality names">
|
||||
</label>
|
||||
<label>Fingerprint
|
||||
<input name="fingerprint" value="chrome">
|
||||
</label>
|
||||
<label>Flow
|
||||
<input name="flow" placeholder="xtls-rprx-vision для VLESS+Reality">
|
||||
</label>
|
||||
<label>ALPN
|
||||
<input name="alpn" placeholder="h2,http/1.1">
|
||||
</label>
|
||||
<label>Порядок
|
||||
<input name="sort_order" type="number" value="0">
|
||||
</label>
|
||||
<label>Заметка
|
||||
<input name="remark" placeholder="опционально">
|
||||
</label>
|
||||
<label>Reality dest
|
||||
<input name="reality_dest" placeholder="www.microsoft.com:443">
|
||||
</label>
|
||||
<label>Reality server names
|
||||
<input name="reality_server_names" placeholder="www.microsoft.com">
|
||||
</label>
|
||||
<label>SS method
|
||||
<input name="ss_method" value="aes-128-gcm">
|
||||
</label>
|
||||
</div>
|
||||
<p class="muted">Для Reality ключи и shortId генерируются автоматически. После назначения профиля ноде Xray поднимется на агенте.</p>
|
||||
<button class="btn btn-primary" type="submit">Добавить inbound</button>
|
||||
</form>
|
||||
</section>
|
||||
|
||||
Reference in New Issue
Block a user