feat: 新增隧道管理功能,前后端完整实现

- 新增统一 ApiResponse 类型定义,与 Rust 端响应结构对齐
- 新增 Rust 后端隧道数据库表、模型、命令和 API 接口
- 新增前端隧道类型定义、API 调用、卡片组件和表单弹窗
- 新增中英双语隧道相关国际化文案
- 更新服务器类型定义,引入共享的 ApiResponse
This commit is contained in:
Yuhang Wu
2026-10-13 14:59:16 +08:00
parent 30ddf583e5
commit 3b153e32c9
15 changed files with 1556 additions and 10 deletions
+10
View File
@@ -0,0 +1,10 @@
/**
* 与 Rust 端统一响应结构 `models::ApiResponse<T>` 一一对应的通用类型。
*/
export interface ApiResponse<T = unknown> {
success: boolean
code: number
msg: string
data: T | null
}
+4
View File
@@ -14,6 +14,8 @@ declare module 'vue' {
AButton: typeof import('ant-design-vue/es')['Button']
ACard: typeof import('ant-design-vue/es')['Card']
ACol: typeof import('ant-design-vue/es')['Col']
ACollapse: typeof import('ant-design-vue/es')['Collapse']
ACollapsePanel: typeof import('ant-design-vue/es')['CollapsePanel']
AConfigProvider: typeof import('ant-design-vue/es')['ConfigProvider']
ADivider: typeof import('ant-design-vue/es')['Divider']
ADropdown: typeof import('ant-design-vue/es')['Dropdown']
@@ -44,6 +46,8 @@ declare module 'vue' {
ServerCard: typeof import('./../components/server/ServerCard.vue')['default']
ServerFormModal: typeof import('./../components/server/ServerFormModal.vue')['default']
TitleBarActions: typeof import('./../components/TitleBarActions.vue')['default']
TunnelCard: typeof import('./../components/tunnel/TunnelCard.vue')['default']
TunnelFormModal: typeof import('./../components/tunnel/TunnelFormModal.vue')['default']
WindowsTitleBar: typeof import('./../components/WindowsTitleBar.vue')['default']
}
}
+1 -7
View File
@@ -2,13 +2,7 @@
* 服务器相关的类型定义,字段与 Rust 端 `models::Server` / `models::ServerPayload` 一一对应。
*/
/** 统一响应结构,对应 Rust 端 `models::ApiResponse<T>` */
export interface ApiResponse<T = unknown> {
success: boolean
code: number
msg: string
data: T | null
}
export type { ApiResponse } from "./api"
/** 传输协议,对应 frpc 的 transport.protocol */
export type ServerProtocol = "tcp" | "kcp" | "quic" | "websocket"
+121
View File
@@ -0,0 +1,121 @@
/**
* 隧道相关的类型定义,字段与 Rust 端 `models::Tunnel` / `models::TunnelPayload` 一一对应。
* 字段命名参考 frpc 的 proxy 配置(如 localIP / remotePort / customDomains 等)。
*/
/** 代理类型,对应 frpc 的 proxy type */
export type TunnelType =
| "tcp"
| "udp"
| "http"
| "https"
| "stcp"
| "xtcp"
| "sudp"
| "tcpmux"
/** 隧道配置 */
export interface Tunnel {
id: number
/** 隧道名称,对应 frpc 的 proxy name */
name: string
/** 代理类型,对应 frpc 的 type */
type: TunnelType
/** 本地 IP,对应 localIP */
local_ip: string
/** 本地端口,对应 localPort */
local_port: number
/** 远程端口,对应 remotePort(tcp / udp 必填) */
remote_port: number | null
/** 自定义域名,对应 customDomains(多个以英文逗号分隔) */
custom_domains: string | null
/** 子域名,对应 subdomain */
subdomain: string | null
/** URL 前缀,对应 locations(多个以英文逗号分隔) */
locations: string | null
/** 密钥,对应 secretKey(stcp / xtcp / sudp) */
secret_key: string | null
/** 传输加密,对应 transport.useEncryption */
use_encryption: boolean
/** 传输压缩,对应 transport.useCompression */
use_compression: boolean
/** 带宽限制,对应 transport.bandwidthLimit */
bandwidth_limit: string | null
/** Proxy Protocol 版本,对应 transport.proxyProtocolVersion */
proxy_protocol_version: string | null
/** 健康检查类型,对应 healthCheck.type:tcp / http */
health_check_type: string | null
/** 健康检查超时(秒),对应 healthCheck.timeoutSeconds */
health_check_timeout: number | null
/** 健康检查最大失败次数,对应 healthCheck.maxFailed */
health_check_max_failed: number | null
/** 健康检查间隔(秒),对应 healthCheck.intervalSeconds */
health_check_interval: number | null
/** 健康检查路径,对应 healthCheck.path */
health_check_path: string | null
/** 负载均衡组,对应 loadBalancer.group */
load_balancer_group: string | null
/** 负载均衡组密钥,对应 loadBalancer.groupKey */
load_balancer_group_key: string | null
/** 备注 */
remark: string | null
/** 排序(越小越靠前) */
sort: number
/** 是否置顶 */
pinned: boolean
/** 是否启用(可同时启用多个) */
enabled: boolean
created_at: string
updated_at: string
}
/** 新增 / 编辑隧道提交数据 */
export interface TunnelPayload {
/** 编辑时携带,新增时省略 */
id?: number
name: string
type: TunnelType
local_ip: string
local_port: number
remote_port?: number | null
custom_domains?: string | null
subdomain?: string | null
locations?: string | null
secret_key?: string | null
use_encryption: boolean
use_compression: boolean
bandwidth_limit?: string | null
proxy_protocol_version?: string | null
health_check_type?: string | null
health_check_timeout?: number | null
health_check_max_failed?: number | null
health_check_interval?: number | null
health_check_path?: string | null
load_balancer_group?: string | null
load_balancer_group_key?: string | null
remark?: string | null
sort: number
pinned: boolean
enabled: boolean
}
/** 代理类型列表 */
export const TUNNEL_TYPES: TunnelType[] = [
"tcp",
"udp",
"http",
"https",
"stcp",
"xtcp",
"sudp",
"tcpmux",
]
/** 需要填写远程端口的代理类型 */
export const TYPES_WITH_REMOTE_PORT: TunnelType[] = ["tcp", "udp"]
/** 需要填写自定义域名 / 子域名的代理类型 */
export const TYPES_WITH_DOMAIN: TunnelType[] = ["http", "https", "tcpmux"]
/** 需要填写密钥的代理类型 */
export const TYPES_WITH_SECRET: TunnelType[] = ["stcp", "xtcp", "sudp"]