TypeScript SDK
XLADA 并没有一个以 XLADA 为名单独发布的 SDK。这并不妨碍使用: 该分支的 API 与 Remnawave 的 API 完全一致 —— 相同的路径,相同的请求与 响应结构。因此 Remnawave 的类型和契约是兼容的,HTTP 客户端 只需几行代码就能搭好。
安装
下面的示例用标准的 fetch 就够了,Node.js 18+ 和
浏览器中都有它。如果你更习惯 axios:
npm install axios
Remnawave 的官方 SDK —— @remnawave/backend-contract —— 只包含类型
和 zod 结构,没有 HTTP 客户端:
npm install @remnawave/backend-contract
在面板的源代码中,同一个契约库位于
apps/backend/libs/contract(前端的副本位于
apps/frontend/vendor/backend-contract),名为 @xlada/backend-contract。
它不会发布到 npm:请把它作为仓库的本地依赖引入
("@xlada/backend-contract": "file:./vendor/backend-contract")。
请把契约版本与面板版本绑定。契约和面板按不同的周期演进, 因此「最新」的类型版本并不总能描述你实际运行的那台 服务器。
基础客户端
面板要求 Authorization: Bearer <token>。如果你从内网直接访问
面板,请加上代理请求头 —— 没有 X-Forwarded-For 和
X-Forwarded-Proto: https 时,面板的 middleware 会断开连接。
const PANEL_URL = process.env.XLADA_PANEL_URL ?? 'https://panel.example.com';
const API_TOKEN = process.env.XLADA_API_TOKEN ?? '';
async function api<T>(path: string, init: RequestInit = {}): Promise<T> {
const res = await fetch(`${PANEL_URL}${path}`, {
...init,
headers: {
'Content-Type': 'application/json',
Authorization: `Bearer ${API_TOKEN}`,
'X-Forwarded-For': '127.0.0.1',
'X-Forwarded-Proto': 'https',
...init.headers,
},
});
if (!res.ok) {
throw new Error(`${res.status} ${res.statusText}: ${await res.text()}`);
}
return (await res.json()) as T;
}
身份验证
有两种获取令牌的方式。
管理员 JWT —— 有效期有限(JWT_AUTH_LIFETIME,12 到
168 小时),由 POST /api/auth/login 签发:
curl -sX POST https://panel.example.com/api/auth/login \
-H 'Content-Type: application/json' \
-d '{"username": "admin", "password": "password"}'
响应中包含 accessToken:
{
"response": {
"accessToken": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9..."
}
}
API 令牌 —— 用于脚本和集成。通过 POST /api/tokens
创建(界面中为 Settings → API Tokens),并在同一个 Authorization
请求头中传递:
curl -sX POST https://panel.example.com/api/tokens \
-H "Authorization: Bearer $ACCESS_TOKEN" \
-H 'Content-Type: application/json' \
-d '{"name": "ci", "expiresInDays": 365}'
生成好的令牌位于 response.token 字段,并且只显示一次。可用范围的
列表由 GET /api/tokens/scopes 返回。
用户列表
分页输出:start —— 偏移量,size —— 每页大小(1 到 1000,
默认为 25)。
interface GetUsersResponse {
response: {
users: Array<{
id: number;
username: string;
status: 'ACTIVE' | 'DISABLED' | 'LIMITED' | 'EXPIRED';
shortUuid: string;
expireAt: string;
}>;
total: number;
};
}
const { response } = await api<GetUsersResponse>('/api/users?start=0&size=25');
for (const user of response.users) {
console.log(user.username, user.status, user.expireAt);
}
console.log(`总计: ${response.total}`);
创建用户
POST /api/users 接受 username(3–36 个字符,仅限拉丁字母、数字、
_ 和 -)以及必填的、ISO 8601 格式的 expireAt。
const created = await api<{ response: { id: number; shortUuid: string } }>(
'/api/users',
{
method: 'POST',
body: JSON.stringify({
username: 'john_doe',
status: 'ACTIVE',
expireAt: '2026-01-17T15:38:45.065Z',
trafficLimitBytes: 0,
trafficLimitStrategy: 'NO_RESET',
}),
},
);
console.log(created.response.shortUuid);
获取节点
单个节点 —— 通过它的 uuid;列表 —— 无需参数:
const { response: node } = await api<{
response: { name: string; address: string; port: number | null; isConnected: boolean };
}>(`/api/nodes/${nodeUuid}`);
console.log(node.name, `${node.address}:${node.port}`, node.isConnected);
从哪里获取类型
完整规范 —— 162 个路径和 29 个标签 —— 位于
API Specification 页面以及面板仓库的 static/openapi.json 文件中。
可以据此生成 .d.ts:
npx openapi-typescript ./openapi.json -o ./src/xlada-api.d.ts
请从你实际部署的那个面板版本的规范生成类型:不同版本之间字段集合会 变化。
接下来
- Go SDK —— 基于 Go 标准库的客户端。
- Python SDK —— 基于
requests的客户端。 - API Specification —— OpenAPI 中的全部端点。
- 环境变量 ——
JWT_AUTH_LIFETIME及其他设置。