bailian-cli-core 1.4.2 → 1.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.mjs CHANGED
@@ -1,2466 +1,16 @@
1
- import { createRequire } from "node:module";
2
- import { appendFileSync, existsSync, mkdirSync, readFileSync, renameSync, statSync, unlinkSync, writeFileSync } from "fs";
3
- import { homedir } from "os";
4
- import { basename, join } from "path";
5
- import { stringify } from "yaml";
6
- import { createHash, createHmac, randomUUID } from "crypto";
7
- import { cpSync, existsSync as existsSync$1, mkdirSync as mkdirSync$1, readFileSync as readFileSync$1, readdirSync, writeFileSync as writeFileSync$1 } from "node:fs";
8
- import { dirname, join as join$1 } from "node:path";
9
- import { fileURLToPath } from "node:url";
10
- //#region \0rolldown/runtime.js
11
- var __create = Object.create;
12
- var __defProp = Object.defineProperty;
13
- var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
14
- var __getOwnPropNames = Object.getOwnPropertyNames;
15
- var __getProtoOf = Object.getPrototypeOf;
16
- var __hasOwnProp = Object.prototype.hasOwnProperty;
17
- var __commonJSMin = (cb, mod) => () => (mod || (cb((mod = { exports: {} }).exports, mod), cb = null), mod.exports);
18
- var __copyProps = (to, from, except, desc) => {
19
- if (from && typeof from === "object" || typeof from === "function") for (var keys = __getOwnPropNames(from), i = 0, n = keys.length, key; i < n; i++) {
20
- key = keys[i];
21
- if (!__hasOwnProp.call(to, key) && key !== except) __defProp(to, key, {
22
- get: ((k) => from[k]).bind(null, key),
23
- enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable
24
- });
25
- }
26
- return to;
27
- };
28
- var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", {
29
- value: mod,
30
- enumerable: true
31
- }) : target, mod));
32
- var __require = /* @__PURE__ */ createRequire(import.meta.url);
33
- //#endregion
34
- //#region src/errors/codes.ts
35
- const ExitCode = {
36
- SUCCESS: 0,
37
- GENERAL: 1,
38
- USAGE: 2,
39
- AUTH: 3,
40
- QUOTA: 4,
41
- TIMEOUT: 5,
42
- NETWORK: 6,
43
- CONTENT_FILTER: 10
44
- };
45
- //#endregion
46
- //#region src/errors/base.ts
47
- var BailianError = class extends Error {
48
- exitCode;
49
- hint;
50
- api;
51
- constructor(message, exitCode = ExitCode.GENERAL, hint, options) {
52
- super(message, options?.cause !== void 0 ? { cause: options.cause } : void 0);
53
- this.name = "BailianError";
54
- this.exitCode = exitCode;
55
- this.hint = hint;
56
- this.api = options?.api;
57
- }
58
- toJSON() {
59
- const causeJson = serializeCause(this.cause);
60
- return { error: {
61
- code: this.exitCode,
62
- message: this.message,
63
- ...this.hint ? { hint: this.hint } : {},
64
- ...this.api?.httpStatus !== void 0 ? { http_status: this.api.httpStatus } : {},
65
- ...this.api?.apiCode ? { api_code: this.api.apiCode } : {},
66
- ...this.api?.requestId ? { request_id: this.api.requestId } : {},
67
- ...causeJson ? { cause: causeJson } : {}
68
- } };
69
- }
70
- };
71
- function serializeCause(cause) {
72
- if (cause == null) return void 0;
73
- if (cause instanceof Error) {
74
- const out = { message: cause.message };
75
- const code = cause.code;
76
- if (code) out.code = code;
77
- return out;
78
- }
79
- if (typeof cause === "string" || typeof cause === "number" || typeof cause === "boolean") return { message: String(cause) };
80
- try {
81
- return { message: JSON.stringify(cause) };
82
- } catch {
83
- return;
84
- }
85
- }
86
- //#endregion
87
- //#region src/errors/api.ts
88
- function mapApiError(status, body, _url) {
89
- const apiMsg = body.error?.message || body.message || `HTTP ${status}`;
90
- const rawCode = body.error?.type ?? body.code;
91
- const apiCode = typeof rawCode === "string" ? rawCode : typeof rawCode === "number" ? String(rawCode) : void 0;
92
- return new BailianError(apiMsg, ExitCode.GENERAL, void 0, { api: {
93
- httpStatus: status,
94
- apiCode,
95
- requestId: body.request_id
96
- } });
97
- }
98
- //#endregion
99
- //#region src/config/schema.ts
100
- const REGIONS = {
101
- cn: "https://dashscope.aliyuncs.com",
102
- us: "https://dashscope-us.aliyuncs.com",
103
- intl: "https://dashscope-intl.aliyuncs.com"
104
- };
105
- const DOCS_HOSTS = {
106
- cn: "https://help.aliyun.com/zh/model-studio",
107
- us: "https://help.aliyun.com/zh/model-studio",
108
- intl: "https://help.aliyun.com/zh/model-studio"
109
- };
110
- const BAILIAN_HOST = "https://bailian.cn-beijing.aliyuncs.com";
111
- const VALID_OUTPUTS = new Set(["text", "json"]);
112
- const VALID_CONSOLE_SITES = new Set(["domestic", "international"]);
113
- /**
114
- * A syntactically valid absolute http(s) URL. Used to validate `base_url`
115
- * from the config file: the credential-bearing client
116
- * sends the Bearer token to these origins, so a bare `startsWith("http")` check
117
- * (which also accepts e.g. "httpfoo://…") is too loose.
118
- */
119
- function isHttpUrl(value) {
120
- try {
121
- const u = new URL(value);
122
- return u.protocol === "http:" || u.protocol === "https:";
123
- } catch {
124
- return false;
125
- }
126
- }
127
- function parseConfigFile(raw) {
128
- if (!raw || typeof raw !== "object" || Array.isArray(raw)) return {};
129
- const obj = raw;
130
- const out = {};
131
- if (typeof obj.api_key === "string") out.api_key = obj.api_key;
132
- if (typeof obj.access_token === "string" && obj.access_token.length > 0) out.access_token = obj.access_token;
133
- else if (typeof obj.accessToken === "string" && obj.accessToken.length > 0) out.access_token = obj.accessToken;
134
- if (typeof obj.base_url === "string" && isHttpUrl(obj.base_url)) out.base_url = obj.base_url;
135
- if (typeof obj.output === "string" && VALID_OUTPUTS.has(obj.output)) out.output = obj.output;
136
- if (typeof obj.output_dir === "string" && obj.output_dir.length > 0) out.output_dir = obj.output_dir;
137
- if (typeof obj.timeout === "number" && obj.timeout > 0) out.timeout = obj.timeout;
138
- if (typeof obj.default_text_model === "string" && obj.default_text_model.length > 0) out.default_text_model = obj.default_text_model;
139
- if (typeof obj.default_video_model === "string" && obj.default_video_model.length > 0) out.default_video_model = obj.default_video_model;
140
- if (typeof obj.default_image_model === "string" && obj.default_image_model.length > 0) out.default_image_model = obj.default_image_model;
141
- if (typeof obj.default_speech_model === "string" && obj.default_speech_model.length > 0) out.default_speech_model = obj.default_speech_model;
142
- if (typeof obj.default_omni_model === "string" && obj.default_omni_model.length > 0) out.default_omni_model = obj.default_omni_model;
143
- if (typeof obj.access_key_id === "string" && obj.access_key_id.length > 0) out.access_key_id = obj.access_key_id;
144
- if (typeof obj.access_key_secret === "string" && obj.access_key_secret.length > 0) out.access_key_secret = obj.access_key_secret;
145
- if (typeof obj.workspace_id === "string" && obj.workspace_id.length > 0) out.workspace_id = obj.workspace_id;
146
- if (typeof obj.console_site === "string" && VALID_CONSOLE_SITES.has(obj.console_site)) out.console_site = obj.console_site;
147
- if (typeof obj.console_region === "string" && obj.console_region.length > 0) out.console_region = obj.console_region;
148
- if (typeof obj.console_switch_agent === "number" && obj.console_switch_agent > 0) out.console_switch_agent = obj.console_switch_agent;
149
- if (typeof obj.telemetry === "boolean") out.telemetry = obj.telemetry;
150
- return out;
151
- }
152
- //#endregion
153
- //#region src/config/paths.ts
154
- const CONFIG_DIR_NAME = ".bailian";
155
- function getConfigDir() {
156
- if (process.env.BAILIAN_CONFIG_DIR) return process.env.BAILIAN_CONFIG_DIR;
157
- return join(homedir(), CONFIG_DIR_NAME);
158
- }
159
- function getConfigPath() {
160
- return join(getConfigDir(), "config.json");
161
- }
162
- function getCredentialsPath() {
163
- return join(getConfigDir(), "credentials.json");
164
- }
165
- async function ensureConfigDir() {
166
- const dir = getConfigDir();
167
- const fs = await import("fs/promises");
168
- await fs.mkdir(dir, {
169
- recursive: true,
170
- mode: 448
171
- });
172
- try {
173
- await fs.chmod(dir, 448);
174
- } catch {}
175
- }
176
- //#endregion
177
- //#region src/output/text.ts
178
- function formatText(data) {
179
- return stringify(data).replace(/\n$/, "");
180
- }
181
- //#endregion
182
- //#region src/output/json.ts
183
- function formatJson(data) {
184
- return JSON.stringify(data, null, 2);
185
- }
186
- function formatErrorJson(code, message, hint) {
187
- return JSON.stringify({ error: {
188
- code,
189
- message,
190
- ...hint ? { hint } : {}
191
- } }, null, 2);
192
- }
193
- //#endregion
194
- //#region src/output/formatter.ts
195
- function detectOutputFormat(flagValue) {
196
- if (flagValue === "json" || flagValue === "text") return flagValue;
197
- if (!process.stdout.isTTY) return "json";
198
- return "text";
199
- }
200
- function formatOutput(data, format) {
201
- switch (format) {
202
- case "json": return formatJson(data);
203
- case "text": return formatText(data);
204
- }
205
- }
206
- //#endregion
207
- //#region src/config/loader.ts
208
- function readConfigFile() {
209
- const path = getConfigPath();
210
- if (!existsSync(path)) return {};
211
- try {
212
- return parseConfigFile(JSON.parse(readFileSync(path, "utf-8")));
213
- } catch (err) {
214
- const e = err;
215
- if (e instanceof SyntaxError || e.message.includes("JSON")) console.warn("Warning: config file is corrupted; using defaults.");
216
- return {};
217
- }
218
- }
219
- async function writeConfigFile(data) {
220
- await ensureConfigDir();
221
- const path = getConfigPath();
222
- const tmp = path + ".tmp";
223
- writeFileSync(tmp, JSON.stringify(data, null, 2) + "\n", { mode: 384 });
224
- renameSync(tmp, path);
225
- }
226
- function loadConfig(flags) {
227
- const file = readConfigFile();
228
- const apiKey = flags.apiKey || void 0;
229
- const fileApiKey = file.api_key;
230
- const accessTokenEnv = process.env.DASHSCOPE_ACCESS_TOKEN?.trim() || void 0;
231
- const fileAccessToken = file.access_token?.trim() || void 0;
232
- const baseUrl = flags.baseUrl || file.base_url || process.env.DASHSCOPE_BASE_URL || REGIONS.cn;
233
- const output = detectOutputFormat(flags.output || process.env.DASHSCOPE_OUTPUT || file.output);
234
- const envTimeout = process.env.DASHSCOPE_TIMEOUT ? Number(process.env.DASHSCOPE_TIMEOUT) : void 0;
235
- const validEnvTimeout = envTimeout !== void 0 && Number.isFinite(envTimeout) && envTimeout > 0 ? envTimeout : void 0;
236
- const timeout = flags.timeout ?? validEnvTimeout ?? file.timeout ?? 300;
237
- if (!Number.isFinite(timeout) || timeout <= 0) throw new BailianError("Timeout must be a positive finite number.", ExitCode.USAGE);
238
- return {
239
- apiKey,
240
- accessTokenEnv,
241
- fileAccessToken,
242
- fileApiKey,
243
- configPath: getConfigPath(),
244
- baseUrl,
245
- output,
246
- outputDir: file.output_dir || void 0,
247
- timeout,
248
- defaultTextModel: file.default_text_model,
249
- defaultVideoModel: file.default_video_model,
250
- defaultImageModel: file.default_image_model,
251
- defaultSpeechModel: file.default_speech_model,
252
- defaultOmniModel: file.default_omni_model,
253
- accessKeyId: process.env.ALIBABA_CLOUD_ACCESS_KEY_ID || file.access_key_id || void 0,
254
- accessKeySecret: process.env.ALIBABA_CLOUD_ACCESS_KEY_SECRET || file.access_key_secret || void 0,
255
- workspaceId: process.env.BAILIAN_WORKSPACE_ID || file.workspace_id || void 0,
256
- consoleSite: flags.consoleSite || file.console_site || void 0,
257
- consoleRegion: flags.consoleRegion || file.console_region || void 0,
258
- consoleSwitchAgent: flags.consoleSwitchAgent || file.console_switch_agent || void 0,
259
- verbose: flags.verbose || process.env.DASHSCOPE_VERBOSE === "1",
260
- quiet: flags.quiet || false,
261
- noColor: flags.noColor || process.env.NO_COLOR !== void 0 || !process.stdout.isTTY,
262
- yes: flags.yes || false,
263
- dryRun: flags.dryRun || false,
264
- nonInteractive: flags.nonInteractive || false,
265
- async: flags.async || false,
266
- telemetry: process.env.DO_NOT_TRACK === "1" ? false : file.telemetry ?? true
267
- };
268
- }
269
- //#endregion
270
- //#region src/auth/credentials.ts
271
- function loadApiKeyFromConfig() {
272
- const path = getConfigPath();
273
- if (!existsSync(path)) return null;
274
- try {
275
- const raw = readFileSync(path, "utf-8");
276
- const data = JSON.parse(raw);
277
- if (typeof data.api_key === "string" && data.api_key.length > 0) return data.api_key;
278
- return null;
279
- } catch {
280
- return null;
281
- }
282
- }
283
- async function saveApiKeyToConfig(apiKey) {
284
- await ensureConfigDir();
285
- const path = getConfigPath();
286
- let existing = {};
287
- try {
288
- existing = JSON.parse(readFileSync(path, "utf-8"));
289
- } catch {}
290
- existing.api_key = apiKey;
291
- const tmp = path + ".tmp";
292
- writeFileSync(tmp, JSON.stringify(existing, null, 2) + "\n", { mode: 384 });
293
- renameSync(tmp, path);
294
- }
295
- async function clearApiKey() {
296
- const path = getConfigPath();
297
- if (!existsSync(path)) return;
298
- try {
299
- const existing = JSON.parse(readFileSync(path, "utf-8"));
300
- delete existing.api_key;
301
- delete existing.access_token;
302
- const tmp = path + ".tmp";
303
- writeFileSync(tmp, JSON.stringify(existing, null, 2) + "\n", { mode: 384 });
304
- renameSync(tmp, path);
305
- } catch {}
306
- }
307
- //#endregion
308
- //#region src/auth/resolver.ts
309
- async function resolveCredential(config) {
310
- if (config.apiKey) return {
311
- token: config.apiKey,
312
- method: "api-key",
313
- source: "flag"
314
- };
315
- if (config.fileApiKey) return {
316
- token: config.fileApiKey,
317
- method: "api-key",
318
- source: "config.json"
319
- };
320
- if (config.accessTokenEnv) return {
321
- token: config.accessTokenEnv,
322
- method: "access-token",
323
- source: "DASHSCOPE_ACCESS_TOKEN"
324
- };
325
- if (config.fileAccessToken) return {
326
- token: config.fileAccessToken,
327
- method: "access-token",
328
- source: "config.json"
329
- };
330
- if (process.env.DASHSCOPE_API_KEY) return {
331
- token: process.env.DASHSCOPE_API_KEY,
332
- method: "api-key",
333
- source: "DASHSCOPE_API_KEY"
334
- };
335
- throw new BailianError("No credentials found.", ExitCode.AUTH, "Set DASHSCOPE_API_KEY environment variable, pass --api-key, or configure a key.");
336
- }
337
- /**
338
- * Credential for Bailian **console** CLI gateway only (`callConsoleGateway`).
339
- * DashScope API keys are not valid Bearer tokens for this gateway — use env/file
340
- * `access_token` even when `api_key` is also present in config.
341
- */
342
- /** Thrown when `callConsoleGateway` has no usable console session token. */
343
- const CONSOLE_GATEWAY_NO_TOKEN_MESSAGE = "No console access token found.";
344
- async function resolveConsoleGatewayCredential(config) {
345
- if (config.accessTokenEnv) return {
346
- token: config.accessTokenEnv,
347
- method: "access-token",
348
- source: "DASHSCOPE_ACCESS_TOKEN"
349
- };
350
- if (config.fileAccessToken) return {
351
- token: config.fileAccessToken,
352
- method: "access-token",
353
- source: "config.json"
354
- };
355
- throw new BailianError(CONSOLE_GATEWAY_NO_TOKEN_MESSAGE, ExitCode.AUTH, "Run `bl auth login --console` or set DASHSCOPE_ACCESS_TOKEN.");
356
- }
357
- //#endregion
358
- //#region src/client/ak-sign.ts
359
- /**
360
- * Alibaba Cloud V3 Signature (ROA style) for Bailian Cloud API.
361
- *
362
- * Used by Knowledge Base Retrieve API which requires AK/SK authentication
363
- * instead of Bearer token.
364
- *
365
- * Reference: https://help.aliyun.com/document_detail/2712195.html
366
- */
367
- function signRequest(cfg) {
368
- const method = cfg.method ?? "POST";
369
- const dateISO = (/* @__PURE__ */ new Date()).toISOString().replace(/\.\d{3}Z$/, "Z");
370
- const nonce = randomUUID();
371
- const hashedBody = sha256Hex(cfg.body);
372
- const headers = {
373
- host: cfg.host,
374
- "x-acs-action": cfg.action,
375
- "x-acs-version": cfg.version,
376
- "x-acs-date": dateISO,
377
- "x-acs-signature-nonce": nonce,
378
- "x-acs-content-sha256": hashedBody,
379
- "content-type": "application/json"
380
- };
381
- const signedHeaderKeys = Object.keys(headers).filter((k) => k === "host" || k === "content-type" || k.startsWith("x-acs-")).sort();
382
- const canonicalHeaders = signedHeaderKeys.map((k) => `${k}:${headers[k]}`).join("\n") + "\n";
383
- const signedHeadersStr = signedHeaderKeys.join(";");
384
- const canonicalRequest = [
385
- method,
386
- cfg.pathname,
387
- "",
388
- canonicalHeaders,
389
- signedHeadersStr,
390
- hashedBody
391
- ].join("\n");
392
- const algorithm = "ACS3-HMAC-SHA256";
393
- const stringToSign = `${algorithm}\n${sha256Hex(canonicalRequest)}`;
394
- const signature = hmacSHA256Hex(cfg.accessKeySecret, stringToSign);
395
- headers["authorization"] = `${algorithm} Credential=${cfg.accessKeyId},SignedHeaders=${signedHeadersStr},Signature=${signature}`;
396
- return headers;
397
- }
398
- function sha256Hex(data) {
399
- return createHash("sha256").update(data, "utf8").digest("hex");
400
- }
401
- function hmacSHA256Hex(key, data) {
402
- return createHmac("sha256", key).update(data, "utf8").digest("hex");
403
- }
404
- //#endregion
405
- //#region src/client/endpoints.ts
406
- function chatEndpoint(baseUrl) {
407
- return `${baseUrl}/compatible-mode/v1/chat/completions`;
408
- }
409
- function imageEndpoint(baseUrl) {
410
- return `${baseUrl}/api/v1/services/aigc/image-generation/generation`;
411
- }
412
- function imageSyncEndpoint(baseUrl) {
413
- return `${baseUrl}/api/v1/services/aigc/multimodal-generation/generation`;
414
- }
415
- function videoGenerateEndpoint(baseUrl) {
416
- return `${baseUrl}/api/v1/services/aigc/video-generation/video-synthesis`;
417
- }
418
- function taskEndpoint(baseUrl, taskId) {
419
- return `${baseUrl}/api/v1/tasks/${encodeURIComponent(taskId)}`;
420
- }
421
- function appCompletionEndpoint(baseUrl, appId) {
422
- return `${baseUrl}/api/v1/apps/${encodeURIComponent(appId)}/completion`;
423
- }
424
- function memoryAddEndpoint(baseUrl) {
425
- return `${baseUrl}/api/v2/apps/memory/add`;
426
- }
427
- function memorySearchEndpoint(baseUrl) {
428
- return `${baseUrl}/api/v2/apps/memory/memory_nodes/search`;
429
- }
430
- function memoryListEndpoint(baseUrl) {
431
- return `${baseUrl}/api/v2/apps/memory/memory_nodes`;
432
- }
433
- function memoryNodeEndpoint(baseUrl, nodeId) {
434
- return `${baseUrl}/api/v2/apps/memory/memory_nodes/${encodeURIComponent(nodeId)}`;
435
- }
436
- function speechSynthesizeEndpoint(baseUrl) {
437
- return `${baseUrl}/api/v1/services/audio/tts/SpeechSynthesizer`;
438
- }
439
- function speechRecognizeEndpoint(baseUrl) {
440
- return `${baseUrl}/api/v1/services/audio/asr/transcription`;
441
- }
442
- function profileSchemaEndpoint(baseUrl) {
443
- return `${baseUrl}/api/v2/apps/memory/profile_schemas`;
444
- }
445
- function userProfileEndpoint(baseUrl, schemaId) {
446
- return `${baseUrl}/api/v2/apps/memory/profile_schemas/${encodeURIComponent(schemaId)}/profiles`;
447
- }
448
- function knowledgeRetrieveEndpoint(baseUrl) {
449
- return `${baseUrl}/api/v1/indices/rag/index/retrieve`;
450
- }
451
- function mcpWebSearchEndpoint(baseUrl) {
452
- return `${baseUrl}/api/v1/mcps/WebSearch/mcp`;
453
- }
454
- //#endregion
455
- //#region src/client/headers.ts
456
- /**
457
- * Shared HTTP request headers for all outgoing requests.
458
- *
459
- * Centralises the `x-dashscope-source-config` header so every fetch call
460
- * (both via the central http client and the bypass paths) uses the
461
- * same values from a single source of truth.
462
- */
463
- const CHANNEL = "bailian-cli";
464
- const TAGS = {
465
- t1: "public",
466
- t2: ""
467
- };
468
- const SOURCE_CONFIG = JSON.stringify({
469
- channel: CHANNEL,
470
- tags: TAGS
471
- });
472
- /** Standard tracking headers required on every outbound request. */
473
- function trackingHeaders() {
474
- return { "x-dashscope-source-config": SOURCE_CONFIG };
475
- }
476
- //#endregion
477
- //#region src/utils/token.ts
478
- function maskToken(token) {
479
- return token.length > 8 ? `${token.slice(0, 4)}...${token.slice(-4)}` : "***";
480
- }
481
- //#endregion
482
- //#region src/client/http.ts
483
- /**
484
- * Bailian requires `X-DashScope-OssResourceResolve: enable` on any request whose body
485
- * references an `oss://` URL (returned by the upload API). Detected automatically here
486
- * so callers don't need to track it manually.
487
- */
488
- function bodyReferencesOssUrl(body) {
489
- if (body == null || typeof body !== "object") return false;
490
- if (body instanceof FormData) return false;
491
- return JSON.stringify(body).includes("oss://");
492
- }
493
- async function request(config, opts) {
494
- const isFormData = typeof FormData !== "undefined" && opts.body instanceof FormData;
495
- const headers = {
496
- "User-Agent": `${config.clientName ?? "bailian-cli-core"}/${config.clientVersion ?? "0.0.0-dev"}`,
497
- ...trackingHeaders(),
498
- ...opts.headers
499
- };
500
- if (!isFormData && !headers["Content-Type"]) headers["Content-Type"] = "application/json";
501
- if (opts.async) headers["X-DashScope-Async"] = "enable";
502
- if (bodyReferencesOssUrl(opts.body)) headers["X-DashScope-OssResourceResolve"] = "enable";
503
- if (!opts.noAuth) {
504
- const credential = await resolveCredential(config);
505
- headers["Authorization"] = `Bearer ${credential.token}`;
506
- if (config.verbose) {
507
- console.error(`> ${opts.method ?? "GET"} ${opts.url}`);
508
- console.error(`> Auth: ${maskToken(credential.token)}`);
509
- console.error(`> x-dashscope-source-config: ${SOURCE_CONFIG}`);
510
- }
511
- }
512
- const requestSignal = createRequestSignal((opts.timeout ?? config.timeout) * 1e3, opts.signal);
513
- const res = await fetch(opts.url, {
514
- method: opts.method ?? "GET",
515
- headers,
516
- body: opts.body ? isFormData ? opts.body : JSON.stringify(opts.body) : void 0,
517
- signal: requestSignal.signal
518
- }).finally(requestSignal.cleanup);
519
- if (config.verbose) {
520
- console.error(`< ${res.status} ${res.statusText}`);
521
- const reqId = res.headers.get("x-request-id");
522
- if (reqId) console.error(`request_id: ${reqId}`);
523
- }
524
- if (!res.ok) {
525
- let body = {};
526
- try {
527
- body = await res.json();
528
- } catch {}
529
- throw mapApiError(res.status, body, opts.url);
530
- }
531
- return res;
532
- }
533
- function createRequestSignal(timeoutMs, parentSignal) {
534
- const controller = new AbortController();
535
- const timeout = setTimeout(() => controller.abort(), timeoutMs);
536
- const abortFromParent = () => controller.abort(parentSignal?.reason);
537
- const cleanup = () => {
538
- clearTimeout(timeout);
539
- parentSignal?.removeEventListener("abort", abortFromParent);
540
- };
541
- if (parentSignal?.aborted) abortFromParent();
542
- else parentSignal?.addEventListener("abort", abortFromParent, { once: true });
543
- controller.signal.addEventListener("abort", cleanup, { once: true });
544
- return {
545
- signal: controller.signal,
546
- cleanup
547
- };
548
- }
549
- async function requestJson(config, opts) {
550
- const res = await request(config, opts);
551
- let data;
552
- try {
553
- data = await res.json();
554
- } catch {
555
- throw new BailianError(`API returned non-JSON response (${res.headers.get("content-type") || "unknown type"}). Server may be experiencing issues.`, ExitCode.GENERAL);
556
- }
557
- if (data.code && typeof data.code === "string" && data.code !== "200" && data.code !== "Success") throw mapApiError(200, { error: {
558
- message: data.message,
559
- type: data.code
560
- } }, opts.url);
561
- return data;
562
- }
563
- //#endregion
564
- //#region src/client/mcp.ts
565
- /**
566
- * Compose the streamable-HTTP MCP endpoint for a Bailian MCP server.
567
- * The path is `/api/v1/mcps/<serverCode>/mcp`; the `serverCode` is taken
568
- * verbatim from `bl mcp list` (e.g. `WebSearch`, `market-cmapi00073529`).
569
- */
570
- function bailianMcpUrl(baseUrl, serverCode) {
571
- return `${baseUrl.replace(/\/$/, "")}/api/v1/mcps/${serverCode}/mcp`;
572
- }
573
- var McpClient = class {
574
- url;
575
- sessionId;
576
- nextId = 1;
577
- config;
578
- authToken;
579
- constructor(config, url) {
580
- this.config = config;
581
- this.url = url;
582
- }
583
- /** Initialize the MCP session. Must be called before any other method. */
584
- async initialize() {
585
- const credential = await resolveCredential(this.config);
586
- this.authToken = credential.token;
587
- const result = await this.rpc("initialize", {
588
- protocolVersion: "2025-03-26",
589
- capabilities: {},
590
- clientInfo: {
591
- name: this.config.clientName ?? "bailian-cli-core",
592
- version: this.config.clientVersion ?? "0.0.0-dev"
593
- }
594
- });
595
- if (this.config.verbose) {
596
- console.error(`[MCP] Session initialized: ${this.sessionId ?? "no session"}`);
597
- console.error(`[MCP] Server: ${JSON.stringify(result)}`);
598
- }
599
- await this.notify("notifications/initialized");
600
- }
601
- async listTools() {
602
- return (await this.rpc("tools/list")).tools || [];
603
- }
604
- async callTool(name, args) {
605
- return await this.rpc("tools/call", {
606
- name,
607
- arguments: args
608
- });
609
- }
610
- async rpc(method, params) {
611
- const body = {
612
- jsonrpc: "2.0",
613
- id: this.nextId++,
614
- method,
615
- ...params ? { params } : {}
616
- };
617
- const data = await (await this.send(body)).json();
618
- if (data.error) throw new BailianError(`MCP error (${data.error.code}): ${data.error.message}`, ExitCode.GENERAL);
619
- return data.result;
620
- }
621
- async notify(method, params) {
622
- const body = {
623
- jsonrpc: "2.0",
624
- method,
625
- ...params ? { params } : {}
626
- };
627
- await this.send(body);
628
- }
629
- async send(body) {
630
- const headers = {
631
- "Content-Type": "application/json",
632
- Accept: "application/json, text/event-stream",
633
- "User-Agent": `${this.config.clientName ?? "bailian-cli-core"}/${this.config.clientVersion ?? "0.0.0-dev"}`,
634
- ...trackingHeaders()
635
- };
636
- if (this.authToken) headers["Authorization"] = `Bearer ${this.authToken}`;
637
- if (this.sessionId) headers["Mcp-Session-Id"] = this.sessionId;
638
- if (this.config.verbose) {
639
- console.error(`> POST ${this.url}`);
640
- console.error(`> Method: ${body.method}`);
641
- }
642
- const timeoutMs = this.config.timeout * 1e3;
643
- const res = await fetch(this.url, {
644
- method: "POST",
645
- headers,
646
- body: JSON.stringify(body),
647
- signal: AbortSignal.timeout(timeoutMs)
648
- });
649
- if (this.config.verbose) console.error(`< ${res.status} ${res.statusText}`);
650
- const sid = res.headers.get("Mcp-Session-Id") || res.headers.get("mcp-session-id");
651
- if (sid) this.sessionId = sid;
652
- if (!res.ok) {
653
- let errMsg = `MCP request failed: ${res.status} ${res.statusText}`;
654
- try {
655
- const errBody = await res.text();
656
- if (errBody) errMsg += ` - ${errBody.slice(0, 500)}`;
657
- } catch {}
658
- throw new BailianError(errMsg, ExitCode.GENERAL);
659
- }
660
- return res;
661
- }
662
- };
663
- //#endregion
664
- //#region src/client/stream.ts
665
- async function* parseSSE(response) {
666
- const reader = response.body?.getReader();
667
- if (!reader) return;
668
- const decoder = new TextDecoder();
669
- let buffer = "";
670
- const MAX_SSE_BUFFER = 16 * 1024 * 1024;
671
- try {
672
- while (true) {
673
- const { done, value } = await reader.read();
674
- if (done) break;
675
- buffer += decoder.decode(value, { stream: true });
676
- if (buffer.length > MAX_SSE_BUFFER) throw new BailianError("SSE stream exceeded the maximum buffer size.", ExitCode.GENERAL);
677
- const lines = buffer.split("\n");
678
- buffer = lines.pop() || "";
679
- let event = {};
680
- for (const line of lines) {
681
- if (line === "") {
682
- if (event.data !== void 0) yield {
683
- data: event.data,
684
- event: event.event,
685
- id: event.id
686
- };
687
- event = {};
688
- continue;
689
- }
690
- if (line.startsWith(":")) continue;
691
- const colonIndex = line.indexOf(":");
692
- if (colonIndex === -1) continue;
693
- const field = line.slice(0, colonIndex);
694
- const value = line.slice(colonIndex + 1).trimStart();
695
- switch (field) {
696
- case "data":
697
- event.data = event.data !== void 0 ? `${event.data}\n${value}` : value;
698
- if (event.data.length > MAX_SSE_BUFFER) throw new BailianError("SSE event exceeded the maximum buffer size.", ExitCode.GENERAL);
699
- break;
700
- case "event":
701
- event.event = value;
702
- break;
703
- case "id":
704
- event.id = value;
705
- break;
706
- }
707
- }
708
- }
709
- if (buffer.trim() && buffer.includes("data:")) {
710
- const colonIndex = buffer.indexOf(":");
711
- if (colonIndex !== -1) yield { data: buffer.slice(colonIndex + 1).trimStart() };
712
- }
713
- } finally {
714
- reader.releaseLock();
715
- }
716
- }
717
- //#endregion
718
- //#region src/console/gateway.ts
719
- const GATEWAY_PRODUCT = "sfm_bailian";
720
- const REGION_GATEWAYS = {
721
- "cn-beijing": {
722
- domestic: {
723
- csGateway: "bailian-cs.console.aliyun.com",
724
- action: "BroadScopeAspnGateway"
725
- },
726
- international: {
727
- csGateway: "bailian-cs.console.alibabacloud.com",
728
- action: "BroadScopeAspnGateway"
729
- }
730
- },
731
- "ap-southeast-1": {
732
- domestic: {
733
- csGateway: "modelstudio-cs.console.aliyun.com",
734
- action: "IntlBroadScopeAspnGateway"
735
- },
736
- international: {
737
- csGateway: "bailian-singapore-cs.alibabacloud.com",
738
- action: "IntlBroadScopeAspnGateway"
739
- }
740
- }
741
- };
742
- function resolveGateway(region, site) {
743
- return REGION_GATEWAYS[region]?.[site] ?? REGION_GATEWAYS["cn-beijing"][site];
744
- }
745
- /** Resolved console gateway settings (same defaults as {@link callConsoleGateway}). */
746
- function effectiveConsoleGatewayConfig(config) {
747
- const consoleRegion = config.consoleRegion ?? "cn-beijing";
748
- const consoleSite = config.consoleSite ?? "domestic";
749
- const consoleSwitchAgent = config.consoleSwitchAgent;
750
- return consoleSwitchAgent != null ? {
751
- consoleRegion,
752
- consoleSite,
753
- consoleSwitchAgent
754
- } : {
755
- consoleRegion,
756
- consoleSite
757
- };
758
- }
759
- function buildGatewayParams(api, data, switchAgent) {
760
- return JSON.stringify({
761
- Api: api,
762
- V: "1.0",
763
- Data: {
764
- ...data,
765
- cornerstoneParam: {
766
- protocol: "V2",
767
- console: "ONE_CONSOLE",
768
- productCode: "p_efm",
769
- consoleSite: "BAILIAN_ALIYUN",
770
- ...switchAgent != null ? { switchAgent } : {},
771
- ...typeof data.cornerstoneParam === "object" && data.cornerstoneParam !== null ? data.cornerstoneParam : {}
772
- }
773
- }
774
- });
775
- }
776
- /**
777
- * Invoke a Bailian **console** OpenAPI via the CLI gateway (`/cli/api.json`).
778
- * `token` is the console `access_token` (from `bl auth login --console`); when
779
- * omitted the request is sent without an Authorization header, which works for
780
- * public console APIs that don't require a login session.
781
- *
782
- * Gateway URL and action are resolved from `region + site` via {@link REGION_GATEWAYS}.
783
- * Each parameter falls back to the corresponding config value, then to a hardcoded default.
784
- */
785
- async function callConsoleGateway(config, token, { api, data }) {
786
- const { consoleRegion: effectiveRegion, consoleSite: effectiveSite, consoleSwitchAgent: effectiveSwitchAgent } = effectiveConsoleGatewayConfig(config);
787
- const resolved = resolveGateway(effectiveRegion, effectiveSite);
788
- const gatewayBase = `https://${resolved.csGateway}`;
789
- const action = resolved.action;
790
- const params = buildGatewayParams(api, data, effectiveSwitchAgent);
791
- const body = new URLSearchParams({
792
- params,
793
- region: effectiveRegion
794
- });
795
- const timeoutMs = config.timeout * 1e3;
796
- const headers = {
797
- Accept: "*/*",
798
- "Content-Type": "application/x-www-form-urlencoded"
799
- };
800
- if (token) headers.Authorization = `Bearer ${token}`;
801
- const res = await fetch(`${gatewayBase}/cli/api.json?action=${action}&product=${GATEWAY_PRODUCT}&api=${encodeURIComponent(api)}`, {
802
- method: "POST",
803
- headers,
804
- body: body.toString(),
805
- signal: AbortSignal.timeout(timeoutMs)
806
- });
807
- if (!res.ok) {
808
- const t = await res.text().catch(() => "");
809
- throw new BailianError(`Console CLI gateway failed: HTTP ${res.status} ${res.statusText}`, ExitCode.GENERAL, t.slice(0, 500));
810
- }
811
- const json = await res.json();
812
- const innerData = json.data;
813
- if (innerData?.success === false && innerData.errorCode) {
814
- const errorCode = String(innerData.errorCode);
815
- const notLogined = errorCode.includes("NotLogined");
816
- const errorMsg = typeof innerData.errorMsg === "string" ? innerData.errorMsg : void 0;
817
- throw new BailianError(notLogined ? "Console session is not logged in or has expired." : `Console gateway error: ${errorCode}`, notLogined ? ExitCode.AUTH : ExitCode.GENERAL, notLogined ? "Run `bl auth login --console` to sign in or refresh your console session." : errorMsg && errorMsg !== errorCode ? errorMsg : void 0);
818
- }
819
- return json;
820
- }
821
- //#endregion
822
- //#region src/console/models.ts
823
- const MODEL_LIST_API = "zeldaHttp.dashscopeModel./zelda/api/v1/modelCenter/listFoundationModels";
824
- async function fetchModelList(config, token, params = {}) {
825
- const { pageNo = 1, pageSize = 50, name = "", providers = [], capabilities = [] } = params;
826
- const result = await callConsoleGateway(config, token, {
827
- api: MODEL_LIST_API,
828
- data: { input: {
829
- pageNo,
830
- pageSize,
831
- name,
832
- providers,
833
- inferenceProviders: [],
834
- features: [],
835
- group: true,
836
- capabilities,
837
- contextWindows: []
838
- } }
839
- });
840
- const responseData = result?.data?.DataV2?.data ?? result?.data ?? {};
841
- const total = responseData?.data?.total ?? responseData?.total ?? 0;
842
- const groups = responseData?.data?.list ?? responseData?.list ?? [];
843
- const models = [];
844
- for (const group of groups) if (group.items?.length) for (const item of group.items) models.push(item);
845
- else models.push(group);
846
- return {
847
- total,
848
- models
849
- };
850
- }
851
- //#endregion
852
- //#region src/files/upload.ts
853
- /**
854
- * Upload local files to DashScope temporary OSS storage.
855
- *
856
- * Returns an `oss://` prefixed URL valid for 48 hours.
857
- * When using this URL in API calls, the request MUST include:
858
- * X-DashScope-OssResourceResolve: enable
859
- */
860
- const UPLOAD_API = `${REGIONS.cn}/api/v1/uploads`;
861
- /**
862
- * Step 1: Fetch the upload policy (presigned credentials) from DashScope.
863
- */
864
- async function getUploadPolicy(apiKey, model, signal) {
865
- const url = `${UPLOAD_API}?action=getPolicy&model=${encodeURIComponent(model)}`;
866
- const policySignal = combineWithTimeout(15e3, signal);
867
- const res = await fetch(url, {
868
- headers: {
869
- Authorization: `Bearer ${apiKey}`,
870
- "Content-Type": "application/json",
871
- ...trackingHeaders()
872
- },
873
- signal: policySignal.signal
874
- }).finally(policySignal.cleanup);
875
- if (!res.ok) {
876
- const text = await res.text().catch(() => "");
877
- throw new BailianError(`Failed to get upload policy (HTTP ${res.status}): ${text}`, ExitCode.GENERAL);
878
- }
879
- return (await res.json()).data;
880
- }
881
- /**
882
- * Step 2: Upload the file to OSS using the policy.
883
- */
884
- async function uploadToOSS(policy, filePath, signal) {
885
- const fileName = basename(filePath);
886
- const key = `${policy.upload_dir}/${fileName}`;
887
- const fileData = readFileSync(filePath);
888
- const form = new FormData();
889
- form.append("OSSAccessKeyId", policy.oss_access_key_id);
890
- form.append("Signature", policy.signature);
891
- form.append("policy", policy.policy);
892
- form.append("x-oss-object-acl", policy.x_oss_object_acl);
893
- form.append("x-oss-forbid-overwrite", policy.x_oss_forbid_overwrite);
894
- form.append("key", key);
895
- form.append("success_action_status", "200");
896
- form.append("file", new Blob([fileData]), fileName);
897
- const uploadSignal = combineWithTimeout(12e4, signal);
898
- const res = await fetch(policy.upload_host, {
899
- method: "POST",
900
- headers: { ...trackingHeaders() },
901
- body: form,
902
- signal: uploadSignal.signal
903
- }).finally(uploadSignal.cleanup);
904
- if (!res.ok) {
905
- const text = await res.text().catch(() => "");
906
- throw new BailianError(`Failed to upload file to OSS (HTTP ${res.status}): ${text}`, ExitCode.GENERAL);
907
- }
908
- return `oss://${key}`;
909
- }
910
- /**
911
- * Upload a local file to DashScope temporary storage and return the oss:// URL.
912
- * The URL is valid for 48 hours.
913
- */
914
- async function uploadFile(opts) {
915
- const { apiKey, model, filePath, signal } = opts;
916
- if (!existsSync(filePath)) throw new BailianError(`File not found: ${filePath}`, ExitCode.USAGE);
917
- if (!statSync(filePath).isFile()) throw new BailianError(`Not a file: ${filePath}`, ExitCode.USAGE);
918
- return uploadToOSS(await getUploadPolicy(apiKey, model, signal), filePath, signal);
919
- }
920
- /**
921
- * Check if a string looks like a local file path (not a URL).
922
- */
923
- function isLocalFile(input) {
924
- if (input.startsWith("http://") || input.startsWith("https://")) return false;
925
- if (input.startsWith("oss://")) return false;
926
- if (input.startsWith("data:")) return false;
927
- return existsSync(input);
928
- }
929
- /**
930
- * Resolve a file argument: if it's a local path, upload it and return the oss:// URL.
931
- * If it's already a URL, return as-is.
932
- */
933
- async function resolveFileUrl(input, apiKey, model, opts = {}) {
934
- if (!isLocalFile(input)) return input;
935
- return uploadFile({
936
- apiKey,
937
- model,
938
- filePath: input,
939
- signal: opts.signal
940
- });
941
- }
942
- function combineWithTimeout(timeoutMs, parentSignal) {
943
- const controller = new AbortController();
944
- const timeout = setTimeout(() => controller.abort(), timeoutMs);
945
- const abortFromParent = () => controller.abort(parentSignal?.reason);
946
- const cleanup = () => {
947
- clearTimeout(timeout);
948
- parentSignal?.removeEventListener("abort", abortFromParent);
949
- };
950
- if (parentSignal?.aborted) abortFromParent();
951
- else parentSignal?.addEventListener("abort", abortFromParent, { once: true });
952
- controller.signal.addEventListener("abort", cleanup, { once: true });
953
- return {
954
- signal: controller.signal,
955
- cleanup
956
- };
957
- }
958
- //#endregion
959
- //#region src/types/command.ts
960
- function defineCommand(spec) {
961
- return {
962
- name: spec.name,
963
- description: spec.description,
964
- usage: spec.usage,
965
- options: spec.options,
966
- examples: spec.examples,
967
- skipDefaultApiKeySetup: spec.skipDefaultApiKeySetup,
968
- notes: spec.notes,
969
- execute: (config, flags) => spec.run(config, flags)
970
- };
971
- }
972
- /** Global flags shared by all commands — drives the parser's type resolution. */
973
- const GLOBAL_OPTIONS = [
974
- {
975
- flag: "--api-key <key>",
976
- description: "API key"
977
- },
978
- {
979
- flag: "--base-url <url>",
980
- description: "API base URL"
981
- },
982
- {
983
- flag: "--output <format>",
984
- description: "Output format: text, json"
985
- },
986
- {
987
- flag: "--timeout <seconds>",
988
- description: "Request timeout",
989
- type: "number"
990
- },
991
- {
992
- flag: "--quiet",
993
- description: "Suppress non-essential output"
994
- },
995
- {
996
- flag: "--verbose",
997
- description: "Print HTTP request/response details"
998
- },
999
- {
1000
- flag: "--no-color",
1001
- description: "Disable ANSI colors"
1002
- },
1003
- {
1004
- flag: "--dry-run",
1005
- description: "Dry run mode"
1006
- },
1007
- {
1008
- flag: "--non-interactive",
1009
- description: "Disable interactive prompts"
1010
- },
1011
- {
1012
- flag: "--concurrent <n>",
1013
- description: "Run N parallel requests (default: 1)",
1014
- type: "number"
1015
- },
1016
- {
1017
- flag: "--console-region <region>",
1018
- description: "Console gateway region (e.g. cn-beijing, ap-southeast-1)"
1019
- },
1020
- {
1021
- flag: "--console-site <site>",
1022
- description: "Console site: domestic, international"
1023
- },
1024
- {
1025
- flag: "--console-switch-agent <uid>",
1026
- description: "Switch agent UID for delegated access",
1027
- type: "number"
1028
- },
1029
- {
1030
- flag: "--help",
1031
- description: "Show help"
1032
- },
1033
- {
1034
- flag: "--version",
1035
- description: "Print version"
1036
- }
1037
- ];
1038
- //#endregion
1039
- //#region src/utils/filename.ts
1040
- /**
1041
- * 生成文件名前缀
1042
- * @param prefix prompt的前10个字符
1043
- * @param suffix timestamp
1044
- * @returns
1045
- */
1046
- function sanitizeFilenamePart(input, fallback) {
1047
- return input.normalize("NFKC").replace(/[\\/:*?"<>|]/g, "_").replace(/\s+/g, "_").replace(/_+/g, "_").replace(/^_+|_+$/g, "") || fallback;
1048
- }
1049
- function generateFilename(prefix, prompt) {
1050
- return `${sanitizeFilenamePart(prefix || "image", "image")}_${sanitizeFilenamePart((prompt || "").substring(0, 20), "untitled")}_${Date.now()}`;
1051
- }
1052
- //#endregion
1053
- //#region src/utils/output-dir.ts
1054
- const DEFAULT_OUTPUT_DIR = () => join(homedir(), "bailian-output");
1055
- /**
1056
- * Resolve the output directory for generated files.
1057
- *
1058
- * Priority:
1059
- * 1. User-specified dir (e.g. --out-dir flag)
1060
- * 2. Config file output_dir
1061
- * 3. Default: ~/bailian-output/
1062
- *
1063
- * Optionally appends a subdirectory (e.g. 'images', 'videos', 'speech').
1064
- * Creates the directory if it doesn't exist.
1065
- */
1066
- function resolveOutputDir(config, options) {
1067
- const base = options?.flagDir || config.outputDir || DEFAULT_OUTPUT_DIR();
1068
- const dir = options?.subDir ? join(base, options.subDir) : base;
1069
- if (!existsSync(dir)) mkdirSync(dir, { recursive: true });
1070
- return dir;
1071
- }
1072
- //#endregion
1073
- //#region src/utils/schema.ts
1074
- /**
1075
- * Parse a CLI flag string (e.g. "--prompt <text>", "--stream") into
1076
- * a parameter name and inferred type.
1077
- */
1078
- function parseFlag(flag) {
1079
- const match = flag.match(/^--([a-zA-Z0-9-]+)/);
1080
- const kebabName = match ? match[1] : "";
1081
- const name = kebabName.replace(/-([a-zA-Z0-9])/g, (_, c) => c.toUpperCase());
1082
- let inferredType = "string";
1083
- let isArray = false;
1084
- if (!flag.includes("<") && !flag.includes("[")) inferredType = "boolean";
1085
- else if (flag.includes("<n>") || flag.includes("<hz>") || flag.includes("<bps>") || flag.includes("<count>")) inferredType = "number";
1086
- if (flag.toLowerCase().includes("repeatable")) isArray = true;
1087
- return {
1088
- name,
1089
- kebabName,
1090
- inferredType,
1091
- isArray
1092
- };
1093
- }
1094
- function generateToolSchema(cmd) {
1095
- const schema = {
1096
- name: `bailian_${cmd.name.replace(/ /g, "_")}`,
1097
- description: cmd.description,
1098
- input_schema: {
1099
- type: "object",
1100
- properties: {},
1101
- required: []
1102
- }
1103
- };
1104
- if (cmd.options) for (const opt of cmd.options) {
1105
- const { name, inferredType, isArray } = parseFlag(opt.flag);
1106
- if (!name) continue;
1107
- const explicitType = opt.type;
1108
- const effectiveType = isArray ? "array" : explicitType ?? inferredType;
1109
- const propSchema = { description: opt.description };
1110
- if (effectiveType === "array") {
1111
- propSchema.type = "array";
1112
- propSchema.items = { type: "string" };
1113
- } else propSchema.type = effectiveType;
1114
- const inputSchema = schema.input_schema;
1115
- inputSchema.properties[name] = propSchema;
1116
- if (opt.required) inputSchema.required.push(name);
1117
- }
1118
- return schema;
1119
- }
1120
- //#endregion
1121
- //#region src/utils/env.ts
1122
- /**
1123
- * Environment detection utilities for bailian-cli.
1124
- *
1125
- * Used to determine whether the CLI is running in an interactive terminal
1126
- * (human user) or in a non-interactive environment (CI, agent, pipe, etc.),
1127
- * so commands can adjust their behavior accordingly.
1128
- */
1129
- /**
1130
- * Detects whether the current environment is interactive.
1131
- *
1132
- * Returns false when:
1133
- * - stdout or stdin is not a TTY
1134
- * - The --non-interactive flag was explicitly set
1135
- * - The process is running in a known CI environment (CI env var present)
1136
- *
1137
- * Returns true when stdout and stdin are both TTYs and --non-interactive
1138
- * was not passed.
1139
- */
1140
- function isInteractive(options) {
1141
- if (options?.nonInteractive === true) return false;
1142
- if (process.env.CI) return false;
1143
- return process.stdout.isTTY === true && process.stdin.isTTY === true;
1144
- }
1145
- /**
1146
- * Detects whether the current process is running in a CI environment.
1147
- */
1148
- function isCI() {
1149
- return !!(process.env.CI || process.env.GITHUB_ACTIONS || process.env.GITLAB_CI || process.env.JENKINS_URL || process.env.TRAVIS || process.env.CIRCLECI);
1150
- }
1151
- //#endregion
1152
- //#region src/utils/object.ts
1153
- /**
1154
- * Generic object-cleaning utilities.
1155
- */
1156
- /**
1157
- * Remove all keys whose value is `undefined` from a plain object (in-place).
1158
- * Returns the same reference for chaining convenience.
1159
- *
1160
- * ```ts
1161
- * const params = { a: 1, b: undefined };
1162
- * stripUndefined(params); // { a: 1 }
1163
- * ```
1164
- */
1165
- function stripUndefined(obj) {
1166
- for (const key of Object.keys(obj)) if (obj[key] === void 0) delete obj[key];
1167
- return obj;
1168
- }
1169
- //#endregion
1170
- //#region src/utils/boolean-flag.ts
1171
- /** Parse true/false from CLI flags (e.g. `--watermark <bool>`). */
1172
- function parseBooleanValue(value, label = "boolean") {
1173
- if (typeof value === "boolean") return value;
1174
- if (typeof value === "string") {
1175
- const v = value.trim().toLowerCase();
1176
- if (v === "true") return true;
1177
- if (v === "false") return false;
1178
- }
1179
- throw new BailianError(`Invalid ${label} value "${String(value)}". Use true or false.`, ExitCode.USAGE);
1180
- }
1181
- function parseOptionalBooleanValue(value, label = "boolean") {
1182
- if (value === void 0 || value === null) return void 0;
1183
- return parseBooleanValue(value, label);
1184
- }
1185
- /**
1186
- * Resolve a tri-state boolean CLI flag (`--name <bool>`).
1187
- * Returns `defaultWhenUnset` when the flag is omitted.
1188
- */
1189
- function resolveBooleanFlag(flagValue, defaultWhenUnset, label = "boolean") {
1190
- const fromFlag = parseOptionalBooleanValue(flagValue, label);
1191
- if (fromFlag !== void 0) return fromFlag;
1192
- return defaultWhenUnset;
1193
- }
1194
- /** Resolve `--watermark` flag; default true when unset. */
1195
- function resolveWatermark(flagValue) {
1196
- return parseOptionalBooleanValue(flagValue, "watermark") ?? true;
1197
- }
1198
- //#endregion
1199
- //#region src/telemetry/event.ts
1200
- function createTrackingEvent(opts) {
1201
- const event = {
1202
- command: opts.command,
1203
- timestamp: (/* @__PURE__ */ new Date()).toISOString(),
1204
- durationMs: opts.durationMs,
1205
- success: opts.success,
1206
- cliVersion: opts.cliVersion,
1207
- nodeVersion: process.version,
1208
- os: process.platform
1209
- };
1210
- if (opts.authMethod) event.authMethod = opts.authMethod;
1211
- if (!opts.success && opts.error) {
1212
- if (opts.error.message) event.errorMessage = opts.error.message;
1213
- if (opts.error.httpStatus !== void 0) event.httpStatus = opts.error.httpStatus;
1214
- if (opts.error.requestId) event.requestId = opts.error.requestId;
1215
- }
1216
- if (opts.params && Object.keys(opts.params).length > 0) event.params = opts.params;
1217
- return event;
1218
- }
1219
- const AEM_TEXT_MAX = 500;
1220
- function aemText(value) {
1221
- if (value === void 0 || value === null) return void 0;
1222
- const s = typeof value === "string" ? value : JSON.stringify(value);
1223
- return s.length <= AEM_TEXT_MAX ? s : s.slice(0, AEM_TEXT_MAX);
1224
- }
1225
- function buildRemoteAemOptions(event) {
1226
- const { command: _command, params, ...extFields } = event;
1227
- const opts = {
1228
- et: "EXP",
1229
- ext: extFields,
1230
- c1: params,
1231
- c2: event.success ? "success" : "failure"
1232
- };
1233
- if (event.httpStatus !== void 0) opts.c3 = String(event.httpStatus);
1234
- if (event.errorMessage) opts.c4 = aemText(event.errorMessage);
1235
- if (event.requestId) opts.c5 = event.requestId;
1236
- return opts;
1237
- }
1238
- //#endregion
1239
- //#region src/telemetry/env.ts
1240
- /**
1241
- * 判断当前运行环境。任一条件为真即视为 dev,默认 prod。
1242
- *
1243
- * 1. NODE_ENV=development — Node 圈通用约定,测试同学/CI 可显式声明
1244
- * 2. 当前模块文件路径不在 node_modules 里 — 自动识别从源码运行(pnpm dev /
1245
- * npm link / 直接 node packages/cli/src/main.ts),避免开发者忘记设环境变量
1246
- * 时仍把数据打到 prod
1247
- *
1248
- * 缓存结果,模块加载期算一次就行。
1249
- */
1250
- let cachedEnv;
1251
- function detectEnv() {
1252
- if (cachedEnv) return cachedEnv;
1253
- if (process.env.NODE_ENV === "development") {
1254
- cachedEnv = "dev";
1255
- return cachedEnv;
1256
- }
1257
- cachedEnv = import.meta.url.includes("/node_modules/") ? "prod" : "dev";
1258
- return cachedEnv;
1259
- }
1260
- //#endregion
1261
- //#region lib/remote-telemetry/tracker.js
1262
- var require_tracker = /* @__PURE__ */ __commonJSMin(((exports, module) => {
1263
- module.exports = (function(e) {
1264
- var t = {};
1265
- function n(r) {
1266
- if (t[r]) return t[r].exports;
1267
- var o = t[r] = {
1268
- i: r,
1269
- l: !1,
1270
- exports: {}
1271
- };
1272
- return e[r].call(o.exports, o, o.exports, n), o.l = !0, o.exports;
1273
- }
1274
- return n.m = e, n.c = t, n.d = function(e, t, r) {
1275
- n.o(e, t) || Object.defineProperty(e, t, {
1276
- enumerable: !0,
1277
- get: r
1278
- });
1279
- }, n.r = function(e) {
1280
- "undefined" != typeof Symbol && Symbol.toStringTag && Object.defineProperty(e, Symbol.toStringTag, { value: "Module" }), Object.defineProperty(e, "__esModule", { value: !0 });
1281
- }, n.t = function(e, t) {
1282
- if (1 & t && (e = n(e)), 8 & t) return e;
1283
- if (4 & t && "object" == typeof e && e && e.__esModule) return e;
1284
- var r = Object.create(null);
1285
- if (n.r(r), Object.defineProperty(r, "default", {
1286
- enumerable: !0,
1287
- value: e
1288
- }), 2 & t && "string" != typeof e) for (var o in e) n.d(r, o, function(t) {
1289
- return e[t];
1290
- }.bind(null, o));
1291
- return r;
1292
- }, n.n = function(e) {
1293
- var t = e && e.__esModule ? function() {
1294
- return e.default;
1295
- } : function() {
1296
- return e;
1297
- };
1298
- return n.d(t, "a", t), t;
1299
- }, n.o = function(e, t) {
1300
- return Object.prototype.hasOwnProperty.call(e, t);
1301
- }, n.p = "", n(n.s = 8);
1302
- })([
1303
- function(e, t) {
1304
- e.exports = __require("os");
1305
- },
1306
- function(e, t) {
1307
- e.exports = globalThis.fetch;
1308
- },
1309
- function(e, t, n) {
1310
- "use strict";
1311
- e.exports = n(6);
1312
- },
1313
- function(e, t) {
1314
- e.exports = __require("dns");
1315
- },
1316
- function(e, t) {
1317
- e.exports = __require("util");
1318
- },
1319
- function(e, t) {
1320
- e.exports = __require("crypto");
1321
- },
1322
- function(e, t, n) {
1323
- Object.defineProperty(t, Symbol.toStringTag, { value: "Module" });
1324
- const r = n(7), o = (e, t) => {
1325
- t.appName = "BaiduSpider", t.appVersion = e.value, t.deviceBrand = "Baidu", t.deviceType = "bot", t.platform = "other";
1326
- }, i = (e, t) => {
1327
- t.appName = "360 Spider", t.appVersion = e.value, t.deviceBrand = "360", t.deviceType = "bot", t.platform = "other";
1328
- }, a = (e, t) => {
1329
- t.appName = "BingBot", t.appVersion = e.value, t.deviceBrand = "Microsoft", t.deviceType = "bot", t.platform = "other";
1330
- }, u = (e, t) => {
1331
- t.appName = "Googlebot", t.appVersion = e.value, t.deviceBrand = "Google", t.deviceType = "bot", t.platform = "other";
1332
- }, p = (e, t) => {
1333
- t.appName = "YandexBot", t.appVersion = e.value, t.deviceBrand = "Yandex", t.deviceType = "bot", t.platform = "other";
1334
- }, l = (e, t) => {
1335
- "Sogou web spider" === e.getPreviousNTokens(3) && (t.deviceBrand = "Sogou.com", t.appName = "SogouSpider"), t.appVersion = e.value, t.deviceType = "bot";
1336
- }, s = (e, t) => {
1337
- t.appName = "DataproviderBot", t.appVersion = e.value, t.deviceBrand = "Dataprovider.com", t.deviceType = "bot", t.platform = "other";
1338
- }, c = (e, t) => {
1339
- t.appName = "AhrefsBot", t.appVersion = e.value, t.deviceBrand = "Ahrefs", t.deviceType = "bot", t.platform = "other";
1340
- }, d = (e, t) => {
1341
- t.appName = "BitSightBot", t.appVersion = e.value, t.deviceBrand = "Bitsight", t.deviceType = "bot", t.platform = "other";
1342
- }, f = (e, t) => {
1343
- t.appName = "oBot", t.appVersion = e.value, t.deviceBrand = "IBM", t.deviceType = "bot", t.platform = "other";
1344
- }, v = (e, t) => {
1345
- t.appName = "Cincraw", t.appVersion = e.value, t.deviceBrand = "CINC", t.deviceType = "bot", t.platform = "other";
1346
- }, g = (e, t) => {
1347
- t.appName = "DingTalkBot", t.appVersion = e.value, t.deviceBrand = "Alibaba", t.deviceType = "bot", t.platform = "other";
1348
- }, h = (e, t) => {
1349
- t.appName = "YisouSpider", t.appVersion = e.value, t.deviceBrand = "Alibaba", t.deviceType = "bot", t.platform = "other";
1350
- }, m = (e, t) => {
1351
- t.appName = "ByteSpider", t.appVersion = e.value, t.deviceBrand = "ByteDance", t.deviceType = "bot", t.platform = "other";
1352
- }, b = (e, t) => {
1353
- t.appName = "HeadlineCrawler", t.appVersion = e.value, t.deviceBrand = "Headline.com", t.deviceType = "bot", t.platform = "other";
1354
- }, y = (e, t) => {
1355
- t.appName = "BitDiscoveryBot", t.appVersion = e.value, t.deviceBrand = "Tenable", t.deviceType = "bot", t.platform = "other";
1356
- }, _ = (e, t) => {
1357
- "Screaming Frog SEO Spider" === e.getPreviousNTokens(4) && (t.deviceBrand = "Screaming Frog", t.appName = "Screaming Frog"), t.appVersion = e.value, t.deviceType = "bot";
1358
- }, B = (e, t) => {
1359
- t.appName = "Ai2Bot", t.appVersion = e.value, t.deviceBrand = "Ai2", t.deviceType = "bot", t.platform = "other";
1360
- }, S = (e, t) => {
1361
- t.appName = "DianjingAdSpider", t.appVersion = e.value, t.deviceBrand = "Dianjing", t.deviceType = "bot", t.platform = "other";
1362
- }, T = (e, t) => {
1363
- t.appName = "BaiduSpider", t.appVersion = e.value, t.deviceBrand = "Baidu", t.deviceType = "bot", t.platform = "other";
1364
- }, j = (e, t) => {
1365
- t.appName = "360 Spider", t.appVersion = e.value, t.deviceBrand = "360", t.deviceType = "bot", t.platform = "other";
1366
- }, N = (e, t) => {
1367
- t.appName = "BingBot", t.appVersion = e.value, t.deviceBrand = "Microsoft", t.deviceType = "bot", t.platform = "other";
1368
- }, w = (e, t) => {
1369
- t.appName = "Googlebot", t.appVersion = e.value, t.deviceBrand = "Google", t.deviceType = "bot", t.platform = "other";
1370
- }, O = (e, t) => {
1371
- t.appName = "YandexBot", t.appVersion = e.value, t.deviceBrand = "Yandex", t.deviceType = "bot", t.platform = "other";
1372
- }, V = (e, t) => {
1373
- "Sogou web spider" === e.getPreviousNTokens(3) && (t.deviceBrand = "Sogou.com", t.appName = "SogouSpider"), t.appVersion = e.value, t.deviceType = "bot";
1374
- }, A = (e, t) => {
1375
- t.appName = "DataproviderBot", t.appVersion = e.value, t.deviceBrand = "Dataprovider.com", t.deviceType = "bot", t.platform = "other";
1376
- }, D = (e, t) => {
1377
- t.appName = "AhrefsBot", t.appVersion = e.value, t.deviceBrand = "Ahrefs", t.deviceType = "bot", t.platform = "other";
1378
- }, k = (e, t) => {
1379
- t.appName = "BitSightBot", t.appVersion = e.value, t.deviceBrand = "Bitsight", t.deviceType = "bot", t.platform = "other";
1380
- }, P = (e, t) => {
1381
- t.appName = "oBot", t.appVersion = e.value, t.deviceBrand = "IBM", t.deviceType = "bot", t.platform = "other";
1382
- }, C = (e, t) => {
1383
- t.appName = "Cincraw", t.appVersion = e.value, t.deviceBrand = "CINC", t.deviceType = "bot", t.platform = "other";
1384
- }, E = (e, t) => {
1385
- t.appName = "DingTalkBot", t.appVersion = e.value, t.deviceBrand = "Alibaba", t.deviceType = "bot", t.platform = "other";
1386
- }, x = (e, t) => {
1387
- t.appName = "YisouSpider", t.appVersion = e.value, t.deviceBrand = "Alibaba", t.deviceType = "bot", t.platform = "other";
1388
- }, M = (e, t) => {
1389
- t.appName = "ByteSpider", t.appVersion = e.value, t.deviceBrand = "ByteDance", t.deviceType = "bot", t.platform = "other";
1390
- }, q = (e, t) => {
1391
- t.appName = "HeadlineCrawler", t.appVersion = e.value, t.deviceBrand = "Headline.com", t.deviceType = "bot", t.platform = "other";
1392
- }, I = (e, t) => {
1393
- t.appName = "BitDiscoveryBot", t.appVersion = e.value, t.deviceBrand = "Tenable", t.deviceType = "bot", t.platform = "other";
1394
- }, H = (e, t) => {
1395
- "Screaming Frog SEO Spider" === e.getPreviousNTokens(4) && (t.deviceBrand = "Screaming Frog", t.appName = "Screaming Frog"), t.appVersion = e.value, t.deviceType = "bot";
1396
- }, U = (e, t) => {
1397
- t.appName = "Ai2Bot", t.appVersion = e.value, t.deviceBrand = "Ai2", t.deviceType = "bot", t.platform = "other";
1398
- }, L = (e, t) => {
1399
- t.appName = "DianjingAdSpider", t.appVersion = e.value, t.deviceBrand = "Dianjing", t.deviceType = "bot", t.platform = "other";
1400
- }, Q = /* @__PURE__ */ new Map(), R = /* @__PURE__ */ new Map();
1401
- Q.set("Baiduspider-render", o), Q.set("Baiduspider+", o), Q.set("Baiduspider-image+", o), Q.set("360Spider", i), Q.set("360Spider-Image", i), Q.set("bingbot", a), Q.set("Googlebot", u), Q.set("YandexRenderResourcesBot", p), Q.set("spider", l), Q.set("Dataprovider.com", s), Q.set("AhrefsBot", c), Q.set("BitSightBot", d), Q.set("oBot", f), Q.set("Cincraw", v), Q.set("DingTalkBot-LinkService", g), Q.set("YisouSpider", h), Q.set("Bytespider", m), Q.set("ev-crawler", b), Q.set("bitdiscovery", y), Q.set("Spider", _), Q.set("Ai2Bot-Dolma", B), Q.set("dianjing_ad_spider", S), R.set("Baiduspider-render", T), R.set("Baiduspider+", T), R.set("Baiduspider-image+", T), R.set("360Spider", j), R.set("360Spider-Image", j), R.set("bingbot", N), R.set("Googlebot", w), R.set("YandexRenderResourcesBot", O), R.set("spider", V), R.set("Dataprovider.com", A), R.set("AhrefsBot", D), R.set("BitSightBot", k), R.set("oBot", P), R.set("Cincraw", C), R.set("DingTalkBot-LinkService", E), R.set("YisouSpider", x), R.set("Bytespider", M), R.set("ev-crawler", q), R.set("bitdiscovery", I), R.set("Spider", H), R.set("Ai2Bot-Dolma", U), R.set("dianjing_ad_spider", L);
1402
- const F = {
1403
- productHandlerMap: Q,
1404
- commentHandlerMap: R,
1405
- getSpecialProductHandler: () => null,
1406
- getSpecialCommentHandler: () => null,
1407
- getDefaultModelHandler: () => null
1408
- };
1409
- t.isBot = function(e) {
1410
- const t = r.createUAInfo();
1411
- return r.runTask(e, t, F), "bot" === t.deviceType;
1412
- };
1413
- },
1414
- function(e, t) {
1415
- function n(e) {
1416
- const t = [], n = {
1417
- parent: e,
1418
- tokens: t,
1419
- get firstToken() {
1420
- return 0 === t.length ? null : t[0];
1421
- },
1422
- getNewToken(r) {
1423
- const o = (function() {
1424
- const e = [], t = [], n = [];
1425
- let r = null, o = null, i = null, a = !0, u = !0, p = !0, l = null;
1426
- const s = {
1427
- get key() {
1428
- return a && (r = e.join(""), a = !1), r;
1429
- },
1430
- get value() {
1431
- return u && (o = t.join(""), u = !1), o;
1432
- },
1433
- get originValue() {
1434
- return p && (i = n.join(""), p = !1), i;
1435
- },
1436
- previousToken: null,
1437
- properties: null,
1438
- appendKey(t) {
1439
- e.push(t), a = !0;
1440
- },
1441
- appendValue(e) {
1442
- t.push("_" === e ? "." : e), n.push(e), u = !0, p = !0, l = null;
1443
- },
1444
- getSplitValue(e) {
1445
- if (null === l) {
1446
- const e = s.value;
1447
- l = "" === e ? [] : e.split("/");
1448
- }
1449
- return e >= 0 && e < l.length ? l[e] : null;
1450
- },
1451
- getPreviousNTokens(e) {
1452
- const t = [];
1453
- let n = s;
1454
- for (let r = 0; r < e; r++) {
1455
- if (null == n) return null;
1456
- t.unshift(n.key), n = n.previousToken;
1457
- }
1458
- return t.join(" ");
1459
- }
1460
- };
1461
- return s;
1462
- })();
1463
- return t.push(o), o.previousToken = void 0 !== r ? r : t.length > 1 ? t[t.length - 2] : null, e && (e.properties = n), o;
1464
- },
1465
- getLastToken: () => 0 === t.length ? null : t[t.length - 1],
1466
- getFirstToken: () => 0 === t.length ? null : t[0],
1467
- isEmpty: () => 0 === t.length
1468
- };
1469
- return n;
1470
- }
1471
- function r() {
1472
- return {
1473
- appName: null,
1474
- appVersion: null,
1475
- browserName: null,
1476
- browserVersion: null,
1477
- engineName: null,
1478
- engineVersion: null,
1479
- deviceBrand: null,
1480
- deviceModel: null,
1481
- deviceType: "mobile",
1482
- osName: null,
1483
- osVersion: null,
1484
- platform: "web",
1485
- tokenGroup: n(null)
1486
- };
1487
- }
1488
- const o = new Set(" ;,\"'".split("")), i = new Set("/=:".split("")), a = new Set([
1489
- "Mozilla",
1490
- "AppleWebKit",
1491
- "Safari",
1492
- "Opera",
1493
- "Dalvik",
1494
- "com.ss.android.ugc.aweme"
1495
- ]);
1496
- function u(e) {
1497
- return 1 === e.length && o.has(e);
1498
- }
1499
- function p(e) {
1500
- return 1 === e.length && i.has(e);
1501
- }
1502
- function l(e, t, n, r) {
1503
- if (null == e) return;
1504
- const o = t.parent, i = e.key;
1505
- let u = null;
1506
- if (null != o) {
1507
- const e = o.key;
1508
- var p, l;
1509
- if (a.has(e)) u = null !== (p = r.commentHandlerMap.get(i)) && void 0 !== p ? p : null, u ??= r.getSpecialCommentHandler(i), null == u && i.endsWith(" Build") && (u = r.getDefaultModelHandler());
1510
- else u = null !== (l = r.productHandlerMap.get(i)) && void 0 !== l ? l : r.getSpecialProductHandler(i);
1511
- } else {
1512
- var s;
1513
- u = null !== (s = r.productHandlerMap.get(i)) && void 0 !== s ? s : r.getSpecialProductHandler(i);
1514
- }
1515
- if (null != u) try {
1516
- u(e, n);
1517
- } catch (e) {}
1518
- }
1519
- function s(e, t, r) {
1520
- if (null == e) throw new Error("input can not be null");
1521
- return (function e(t, r, o, i, a) {
1522
- let s, c = null, d = null, f = !1;
1523
- const v = t.length;
1524
- let g = r > 0 ? t[r - 1] : "\0";
1525
- for (s = r; s < v; s++) {
1526
- const h = t[s];
1527
- if (u(h)) {
1528
- const e = "\0" !== g && u(g);
1529
- if (!f && r > 0 && " " === h && !e) {
1530
- const e = s + 1;
1531
- if (e < v) {
1532
- const n = t[e];
1533
- /\d/.test(n) || "-" === n ? f = !0 : d?.appendKey(h);
1534
- } else d?.appendKey(h);
1535
- } else null != d && (c = d, d = null);
1536
- g = h;
1537
- } else if ("(" === h) {
1538
- if ("(" === g) {
1539
- g = h;
1540
- continue;
1541
- }
1542
- const r = s;
1543
- s = e(t, s + 1, n(o.getLastToken()), i, a), null != d && (c = d, d = null), g = t[r];
1544
- } else {
1545
- if (")" === h) {
1546
- if (0 === r) {
1547
- g = h;
1548
- continue;
1549
- }
1550
- break;
1551
- }
1552
- d ?? (l(o.getLastToken(), o, i, a), d = o.getNewToken(c), f = !1), p(h) ? (f && d.appendValue(h), f = !0) : f ? d.appendValue(h) : d.appendKey(h), g = h;
1553
- }
1554
- }
1555
- return l(o.getLastToken(), o, i, a), s;
1556
- })(e, 0, t.tokenGroup, t, r), t;
1557
- }
1558
- Object.defineProperty(t, "DEFAULT_MODEL_HANDLER_KEY", {
1559
- enumerable: !0,
1560
- get: function() {
1561
- return "DEFAULT_MODEL_HANDLER";
1562
- }
1563
- }), Object.defineProperty(t, "createUAInfo", {
1564
- enumerable: !0,
1565
- get: function() {
1566
- return r;
1567
- }
1568
- }), Object.defineProperty(t, "runTask", {
1569
- enumerable: !0,
1570
- get: function() {
1571
- return s;
1572
- }
1573
- });
1574
- },
1575
- function(e, t, n) {
1576
- "use strict";
1577
- n.r(t);
1578
- var r = n(0), o = n.n(r), i = n(1), a = n.n(i);
1579
- n(2);
1580
- function u() {
1581
- var e = arguments.length > 0 && void 0 !== arguments[0] ? arguments[0] : 20, t = arguments.length > 1 ? arguments[1] : void 0;
1582
- return t = t || "", e ? u(--e, "0123456789ABCDEFGHIJKLMNOPQRSTUVWXTZabcdefghiklmnopqrstuvwxyz".charAt(Math.floor(60 * Math.random())) + t) : t;
1583
- }
1584
- function p(e, t) {
1585
- for (var n in t) e[n] = t[n];
1586
- return e;
1587
- }
1588
- function l(e) {
1589
- return "[object Object]" === Object.prototype.toString.call(e);
1590
- }
1591
- function s(e) {
1592
- return "undefined" != typeof Promise && e instanceof Promise;
1593
- }
1594
- var c = Object.freeze({ __aesBeforeSkip: 1 }), d = function(e) {
1595
- var t = Object.prototype.toString.call(e);
1596
- if ("[object String]" === t && e || "[object Number]" === t || "[object Boolean]" === t) return e;
1597
- if ("[object Object]" === t || "[object Array]" === t) try {
1598
- return JSON.stringify(e);
1599
- } catch (e) {}
1600
- }, f = function(e) {
1601
- var t = {};
1602
- for (var n in e) {
1603
- var r = e[n];
1604
- void 0 !== r && (t[n] = d(r));
1605
- }
1606
- return t;
1607
- }, v = function(e) {
1608
- var t = [];
1609
- for (var n in e) {
1610
- var r = d(e[n]);
1611
- void 0 !== r && t.push("".concat(n, "=").concat(encodeURIComponent(r)));
1612
- }
1613
- return t.join("&");
1614
- };
1615
- function g(e) {
1616
- return (e.requiredFields || []).concat(["pid"]).some(function(t) {
1617
- return void 0 === e[t];
1618
- });
1619
- }
1620
- function h() {
1621
- var e = arguments.length > 0 && void 0 !== arguments[0] ? arguments[0] : "", t = arguments.length > 1 ? arguments[1] : void 0;
1622
- "undefined" != typeof console && console.warn("日志解析报错,埋点将被丢弃 => ".concat(e), t);
1623
- }
1624
- var m = "AEM_TRACKER_UNIQUE_PVID", b = "undefined" != typeof globalThis && globalThis ? globalThis : "undefined" != typeof window && window ? window : "undefined" != typeof global && global ? global : "undefined" != typeof self && self ? self : (console.error("Unable to locate global object in current environment"), {});
1625
- function y(e) {
1626
- this._queue = [], this._reqQueue = [], this._plugins = {}, this._subscribers = { onConfigUpdated: [] }, this._timeout = 0, this._config = {
1627
- sdk_version: "3.3.18",
1628
- set pv_id(e) {
1629
- b[m] = e;
1630
- },
1631
- get pv_id() {
1632
- return b[m] || (b[m] = u()), b[m];
1633
- },
1634
- timezone_offset: (/* @__PURE__ */ new Date()).getTimezoneOffset()
1635
- }, e && (this._config = p(this._config, e));
1636
- }
1637
- y.prototype = {
1638
- constructor: y,
1639
- _sendAll: function() {
1640
- if (this._timeout && (clearTimeout(this._timeout), this._timeout = 0), this._queue.length) {
1641
- var e, t = this._config.maxUrlLength || 3e4, n = this._getSendConfig();
1642
- try {
1643
- e = this._processData(this._queue, n);
1644
- } catch (e) {}
1645
- if (e && e.length < t) return this._queue = [], void this.send(e);
1646
- for (var r, o = []; this._queue.length;) {
1647
- o.push(this._queue.shift());
1648
- try {
1649
- r = this._processData(o, n);
1650
- } catch (e) {
1651
- var i = o.pop();
1652
- h(e.message, i);
1653
- continue;
1654
- }
1655
- if (r.length > t) {
1656
- o.length > 1 && (this._queue.unshift(o.pop()), r = this._processData(o, n));
1657
- break;
1658
- }
1659
- }
1660
- r && this.send(r), this._queue.length && this._sendAll();
1661
- }
1662
- },
1663
- _send: function(e, t) {
1664
- var n = this;
1665
- if (!1 === t) {
1666
- var r;
1667
- try {
1668
- r = this._processData([e]);
1669
- } catch (t) {
1670
- h(t.message, e);
1671
- }
1672
- r && this.send(r);
1673
- } else {
1674
- this._queue.push(e);
1675
- var o = this._config.mergeRequestInterval || 500;
1676
- this._timeout || (this._timeout = setTimeout(function() {
1677
- n._sendAll();
1678
- }, o));
1679
- }
1680
- },
1681
- _getSendConfig: function() {
1682
- var e = {}, t = this._config;
1683
- for (var n in t) "requiredFields" !== n && "maxUrlLength" !== n && "queueGlobalName" !== n && "debug" !== n && "excludeCrawlers" !== n && "collectClientHints" !== n && 0 !== n.indexOf("plugin") && "" !== t[n] && null !== t[n] && void 0 !== t[n] && (e[n] = d(t[n]));
1684
- return e;
1685
- },
1686
- _processData: function(e, t) {
1687
- t = t || this._getSendConfig();
1688
- var n = v(t);
1689
- return n += "&msg=" + encodeURIComponent(e.map(function(e) {
1690
- return v(e);
1691
- }).join("|"));
1692
- },
1693
- setConfig: function(e, t) {
1694
- var n = this, r = {};
1695
- void 0 !== t ? r[e] = t : r = e;
1696
- var o = !(function e(t, n) {
1697
- if (void 0 === t || void 0 === n) return !1;
1698
- if (!l(t) || !l(n)) return !1;
1699
- for (var r in t) if (l(t[r])) {
1700
- if (!e(t[r], n[r])) return !1;
1701
- } else if (t[r] !== n[r]) return !1;
1702
- return !0;
1703
- })(r, this._config), i = function() {
1704
- if (o) {
1705
- for (var e in r) l(r[e]) ? n._config[e] = p(n._config[e] || {}, r[e]) : n._config[e] = r[e];
1706
- n._execSubscribe("onConfigUpdated", [r, n._config]);
1707
- }
1708
- };
1709
- this._reqQueue.length ? (i(), g(this._config) || (this._reqQueue.forEach(function(e) {
1710
- n._send.apply(n, e);
1711
- }), this._reqQueue = [])) : (o && this._sendAll(), i());
1712
- },
1713
- getConfig: function(e) {
1714
- return e ? this._config[e] : this._config;
1715
- },
1716
- updatePVID: (function(e, t) {
1717
- if ("function" != typeof e) throw new TypeError("Expected a function");
1718
- t = "number" == typeof t && t >= 0 ? t : 100;
1719
- var n = null;
1720
- return function() {
1721
- if (null === n) {
1722
- var r = this, o = Array.prototype.slice.call(arguments);
1723
- n = setTimeout(function() {
1724
- n = null;
1725
- }, t), e.apply(r, o);
1726
- }
1727
- };
1728
- })(function() {
1729
- b[m] = u();
1730
- }, 200),
1731
- log: function(e) {
1732
- var t = arguments.length > 1 && void 0 !== arguments[1] ? arguments[1] : {}, n = arguments.length > 2 && void 0 !== arguments[2] ? arguments[2] : {};
1733
- e && (t.ts = t.ts || (/* @__PURE__ */ new Date()).getTime(), t.type = e, this._print("log", e, t), t = f(t), g(this._config) ? this._reqQueue.length < 1e3 && this._reqQueue.push([t, n.combo]) : this._send(t, n.combo));
1734
- },
1735
- before: function(e, t) {
1736
- var n = this;
1737
- return function() {
1738
- var r = arguments, o = t.apply(n, r);
1739
- o !== c && (s(o) ? o.then(function(t) {
1740
- t !== c && e.apply(n, t || r);
1741
- }) : e.apply(n, o || r));
1742
- };
1743
- },
1744
- after: function(e, t) {
1745
- var n = this;
1746
- return function() {
1747
- var r = arguments;
1748
- e.apply(n, r), t.apply(n, r);
1749
- };
1750
- },
1751
- use: function(e, t) {
1752
- var n = this;
1753
- return "[object Array]" === Object.prototype.toString.call(e) ? e.map(function(e) {
1754
- if ("[object Array]" === Object.prototype.toString.call(e)) {
1755
- var t = e[0], r = e[1];
1756
- return n._plugins[t] || (n._plugins[t] = new t(n, r));
1757
- }
1758
- return n._plugins[e] || (n._plugins[e] = new e(n));
1759
- }) : this._plugins[e] || (this._plugins[e] = new e(this, t));
1760
- },
1761
- _print: function() {
1762
- this._config.debug && "undefined" != typeof console && console.log.apply(console, arguments);
1763
- },
1764
- onConfigUpdated: function(e) {
1765
- this._subscribers.onConfigUpdated && this._subscribers.onConfigUpdated.push(e);
1766
- },
1767
- _execSubscribe: function(e, t) {
1768
- this._subscribers[e] && this._subscribers[e].forEach(function(e) {
1769
- e.apply(this, t);
1770
- });
1771
- }
1772
- };
1773
- var _ = y, B = n(3), S = n.n(B), T = n(4), j = n(5), N = n.n(j);
1774
- function w(e) {
1775
- return (w = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function(e) {
1776
- return typeof e;
1777
- } : function(e) {
1778
- return e && "function" == typeof Symbol && e.constructor === Symbol && e !== Symbol.prototype ? "symbol" : typeof e;
1779
- })(e);
1780
- }
1781
- function O(e, t) {
1782
- var n = Object.keys(e);
1783
- if (Object.getOwnPropertySymbols) {
1784
- var r = Object.getOwnPropertySymbols(e);
1785
- t && (r = r.filter(function(t) {
1786
- return Object.getOwnPropertyDescriptor(e, t).enumerable;
1787
- })), n.push.apply(n, r);
1788
- }
1789
- return n;
1790
- }
1791
- function V(e) {
1792
- for (var t = 1; t < arguments.length; t++) {
1793
- var n = null != arguments[t] ? arguments[t] : {};
1794
- t % 2 ? O(Object(n), !0).forEach(function(t) {
1795
- A(e, t, n[t]);
1796
- }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(n)) : O(Object(n)).forEach(function(t) {
1797
- Object.defineProperty(e, t, Object.getOwnPropertyDescriptor(n, t));
1798
- });
1799
- }
1800
- return e;
1801
- }
1802
- function A(e, t, n) {
1803
- return (t = (function(e) {
1804
- var t = (function(e, t) {
1805
- if ("object" != w(e) || !e) return e;
1806
- var n = e[Symbol.toPrimitive];
1807
- if (void 0 !== n) {
1808
- var r = n.call(e, t || "default");
1809
- if ("object" != w(r)) return r;
1810
- throw new TypeError("@@toPrimitive must return a primitive value.");
1811
- }
1812
- return ("string" === t ? String : Number)(e);
1813
- })(e, "string");
1814
- return "symbol" == w(t) ? t : t + "";
1815
- })(t)) in e ? Object.defineProperty(e, t, {
1816
- value: n,
1817
- enumerable: !0,
1818
- configurable: !0,
1819
- writable: !0
1820
- }) : e[t] = n, e;
1821
- }
1822
- function D(e, t) {
1823
- var n = "undefined" != typeof Symbol && e[Symbol.iterator] || e["@@iterator"];
1824
- if (!n) {
1825
- if (Array.isArray(e) || (n = P(e)) || t && e && "number" == typeof e.length) {
1826
- n && (e = n);
1827
- var r = 0, o = function() {};
1828
- return {
1829
- s: o,
1830
- n: function() {
1831
- return r >= e.length ? { done: !0 } : {
1832
- done: !1,
1833
- value: e[r++]
1834
- };
1835
- },
1836
- e: function(e) {
1837
- throw e;
1838
- },
1839
- f: o
1840
- };
1841
- }
1842
- throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.");
1843
- }
1844
- var i, a = !0, u = !1;
1845
- return {
1846
- s: function() {
1847
- n = n.call(e);
1848
- },
1849
- n: function() {
1850
- var e = n.next();
1851
- return a = e.done, e;
1852
- },
1853
- e: function(e) {
1854
- u = !0, i = e;
1855
- },
1856
- f: function() {
1857
- try {
1858
- a || null == n.return || n.return();
1859
- } finally {
1860
- if (u) throw i;
1861
- }
1862
- }
1863
- };
1864
- }
1865
- function k(e, t) {
1866
- return (function(e) {
1867
- if (Array.isArray(e)) return e;
1868
- })(e) || (function(e, t) {
1869
- var n = null == e ? null : "undefined" != typeof Symbol && e[Symbol.iterator] || e["@@iterator"];
1870
- if (null != n) {
1871
- var r, o, i, a, u = [], p = !0, l = !1;
1872
- try {
1873
- if (i = (n = n.call(e)).next, 0 === t) {
1874
- if (Object(n) !== n) return;
1875
- p = !1;
1876
- } else for (; !(p = (r = i.call(n)).done) && (u.push(r.value), u.length !== t); p = !0);
1877
- } catch (e) {
1878
- l = !0, o = e;
1879
- } finally {
1880
- try {
1881
- if (!p && null != n.return && (a = n.return(), Object(a) !== a)) return;
1882
- } finally {
1883
- if (l) throw o;
1884
- }
1885
- }
1886
- return u;
1887
- }
1888
- })(e, t) || P(e, t) || (function() {
1889
- throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.");
1890
- })();
1891
- }
1892
- function P(e, t) {
1893
- if (e) {
1894
- if ("string" == typeof e) return C(e, t);
1895
- var n = {}.toString.call(e).slice(8, -1);
1896
- return "Object" === n && e.constructor && (n = e.constructor.name), "Map" === n || "Set" === n ? Array.from(e) : "Arguments" === n || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n) ? C(e, t) : void 0;
1897
- }
1898
- }
1899
- function C(e, t) {
1900
- (null == t || t > e.length) && (t = e.length);
1901
- for (var n = 0, r = Array(t); n < t; n++) r[n] = e[n];
1902
- return r;
1903
- }
1904
- function E() {
1905
- for (var e = /(?:[0]{1,2}[:-]){5}[0]{1,2}/, t = o.a.networkInterfaces(), n = 0, r = Object.entries(t); n < r.length; n++) {
1906
- var i = k(r[n], 2), a = (i[0], i[1]);
1907
- if (a) {
1908
- var u, p = D(a);
1909
- try {
1910
- for (p.s(); !(u = p.n()).done;) {
1911
- var l = u.value;
1912
- if (!1 === e.test(l.mac)) return l.mac;
1913
- }
1914
- } catch (e) {
1915
- p.e(e);
1916
- } finally {
1917
- p.f();
1918
- }
1919
- }
1920
- }
1921
- return "00:00:00:00:00:00";
1922
- }
1923
- var x, M, q = (x = process.version, {
1924
- os: o.a.type(),
1925
- os_version: o.a.release(),
1926
- app_name: "node",
1927
- app_version: x,
1928
- device_id: N.a.createHash("md5").update(E()).digest("hex"),
1929
- platform: "node"
1930
- }), I = Object(T.promisify)(S.a.resolve);
1931
- function H(e) {
1932
- this._offlineQueue = [], e.endpoint = e.endpoint || "gm.mmstat.com", _.call(this, V(V({}, q), e)), this._config.endpoint_url = "https://".concat(this._config.endpoint).concat("/aes.1.1");
1933
- }
1934
- H.prototype = ((M = function() {}).prototype = _.prototype, new M()), H.prototype.constructor = H, H.prototype.send = function(e) {
1935
- var t, n = this;
1936
- return (t = this._config.endpoint, I(t)).then(function(t) {
1937
- return n._offlineQueue.forEach(function(e) {
1938
- n.send(e);
1939
- }), n._offlineQueue = [], n._print("send", e), a()(n._config.endpoint_url, {
1940
- method: "POST",
1941
- keepalive: true,
1942
- body: JSON.stringify({
1943
- gokey: encodeURIComponent(e),
1944
- gmkey: "EXP"
1945
- })
1946
- }).catch(function() {});
1947
- }).catch(function(t) {
1948
- n._offlineQueue.length > 500 && n._offlineQueue.shift(), n._offlineQueue.push(e);
1949
- });
1950
- };
1951
- t.default = H;
1952
- }
1953
- ]).default;
1954
- }));
1955
- //#endregion
1956
- //#region lib/remote-telemetry/event-plugin.js
1957
- var require_event_plugin = /* @__PURE__ */ __commonJSMin(((exports, module) => {
1958
- module.exports = (function(e) {
1959
- var t = {};
1960
- function n(r) {
1961
- if (t[r]) return t[r].exports;
1962
- var o = t[r] = {
1963
- i: r,
1964
- l: !1,
1965
- exports: {}
1966
- };
1967
- return e[r].call(o.exports, o, o.exports, n), o.l = !0, o.exports;
1968
- }
1969
- return n.m = e, n.c = t, n.d = function(e, t, r) {
1970
- n.o(e, t) || Object.defineProperty(e, t, {
1971
- enumerable: !0,
1972
- get: r
1973
- });
1974
- }, n.r = function(e) {
1975
- "undefined" != typeof Symbol && Symbol.toStringTag && Object.defineProperty(e, Symbol.toStringTag, { value: "Module" }), Object.defineProperty(e, "__esModule", { value: !0 });
1976
- }, n.t = function(e, t) {
1977
- if (1 & t && (e = n(e)), 8 & t) return e;
1978
- if (4 & t && "object" == typeof e && e && e.__esModule) return e;
1979
- var r = Object.create(null);
1980
- if (n.r(r), Object.defineProperty(r, "default", {
1981
- enumerable: !0,
1982
- value: e
1983
- }), 2 & t && "string" != typeof e) for (var o in e) n.d(r, o, function(t) {
1984
- return e[t];
1985
- }.bind(null, o));
1986
- return r;
1987
- }, n.n = function(e) {
1988
- var t = e && e.__esModule ? function() {
1989
- return e.default;
1990
- } : function() {
1991
- return e;
1992
- };
1993
- return n.d(t, "a", t), t;
1994
- }, n.o = function(e, t) {
1995
- return Object.prototype.hasOwnProperty.call(e, t);
1996
- }, n.p = "", n(n.s = 0);
1997
- })([function(e, t, n) {
1998
- "use strict";
1999
- n.r(t);
2000
- var r = [
2001
- "ec",
2002
- "ea",
2003
- "el",
2004
- "et"
2005
- ];
2006
- var o = function(e, t) {
2007
- var n = function(e) {
2008
- var n = e.ec, r = e.ea, o = e.el, l = e.et, u = void 0 === l ? "CLK" : l, a = e.xpath;
2009
- delete e.ec, delete e.ea, delete e.el, delete e.et, delete e.xpath, e.p1 = n, e.p2 = r, e.p3 = o, e.p4 = u, e.p5 = a;
2010
- try {
2011
- t.log("event", e);
2012
- } catch (e) {}
2013
- };
2014
- return function() {
2015
- var t = arguments, o = {};
2016
- if (0 !== t.length) {
2017
- for (var l = 0; l < t.length; l++) {
2018
- var u, a, i = t[l];
2019
- if (0 !== l && "object" == typeof i && l !== t.length - 1) return void (null == e || null === (u = e.console) || void 0 === u || null === (a = u.warn) || void 0 === a || a.call(u, "Only the last argument can be object type"));
2020
- if ("string" == typeof i || "number" == typeof i) o[r[l]] = i;
2021
- else if ("object" == typeof i && l === t.length - 1) for (var c in i) i.hasOwnProperty(c) && (o[c] = i[c]);
2022
- }
2023
- n(o);
2024
- } else {
2025
- var f, p;
2026
- null === (f = e.console) || void 0 === f || null === (p = f.warn) || void 0 === p || p.call(f, "At lease one augument");
2027
- }
2028
- };
2029
- };
2030
- t.default = function(e, t) {
2031
- return o(global, e);
2032
- };
2033
- }]).default;
2034
- }));
2035
- //#endregion
2036
- //#region src/telemetry/sink.ts
2037
- var import_tracker = /* @__PURE__ */ __toESM(require_tracker(), 1);
2038
- var import_event_plugin = /* @__PURE__ */ __toESM(require_event_plugin(), 1);
2039
- const TELEMETRY_FILE = () => join(getConfigDir(), "telemetry.jsonl");
2040
- const MAX_FILE_SIZE = 5 * 1024 * 1024;
2041
- let remoteSendEvent;
2042
- const inflightSends = /* @__PURE__ */ new Set();
2043
- let remoteClient = void 0;
2044
- try {
2045
- const client = new import_tracker.default({
2046
- pid: "bailian-cli-node",
2047
- env: detectEnv()
2048
- });
2049
- const originalSend = client.send.bind(client);
2050
- client.send = function(payload) {
2051
- const result = originalSend(payload);
2052
- if (result && typeof result.then === "function") {
2053
- const p = result;
2054
- inflightSends.add(p);
2055
- p.finally(() => inflightSends.delete(p));
2056
- }
2057
- return result;
2058
- };
2059
- remoteClient = client;
2060
- remoteSendEvent = client.use(import_event_plugin.default);
2061
- } catch {}
2062
- /**
2063
- * 尽力等待所有在途的埋点发送完成(best-effort)。
2064
- *
2065
- * 1. 先调用 `_sendAll` 排空 tracker 内部的去抖队列,把还卡在 500ms 合并窗口里
2066
- * 的事件立刻推上网络。
2067
- * 2. 然后用硬超时 race 所有已追踪的 fetch promise。
2068
- *
2069
- * 埋点永远不应阻塞 CLI:调用方应传入较短的超时(例如 1000ms),并始终与超时
2070
- * race。错误与超时一律静默吞掉。
2071
- */
2072
- async function flushTelemetry(timeoutMs = 1e3) {
2073
- try {
2074
- if (remoteClient) try {
2075
- if (typeof remoteClient._sendAll === "function") remoteClient._sendAll();
2076
- } catch {}
2077
- if (inflightSends.size === 0) return;
2078
- const pending = [...inflightSends].map((p) => p.catch(() => void 0));
2079
- await Promise.race([Promise.allSettled(pending), new Promise((resolve) => setTimeout(resolve, timeoutMs).unref?.())]);
2080
- } catch {}
2081
- }
2082
- async function localSink(event) {
2083
- try {
2084
- await ensureConfigDir();
2085
- const path = TELEMETRY_FILE();
2086
- try {
2087
- if (statSync(path).size > MAX_FILE_SIZE) unlinkSync(path);
2088
- } catch {}
2089
- appendFileSync(path, JSON.stringify(event) + "\n", { mode: 384 });
2090
- } catch {}
2091
- }
2092
- async function remoteSink(event) {
2093
- try {
2094
- if (!remoteSendEvent) return;
2095
- remoteSendEvent(event.command, buildRemoteAemOptions(event));
2096
- } catch {}
2097
- }
2098
- //#endregion
2099
- //#region src/telemetry/tracker.ts
2100
- const GLOBAL_FLAG_KEYS = new Set([
2101
- "apiKey",
2102
- "baseUrl",
2103
- "output",
2104
- "quiet",
2105
- "verbose",
2106
- "timeout",
2107
- "noColor",
2108
- "yes",
2109
- "dryRun",
2110
- "help",
2111
- "nonInteractive",
2112
- "async",
2113
- "console"
2114
- ]);
2115
- /**
2116
- * Allowlist of flag names safe to send to telemetry.
2117
- *
2118
- * Default is to NOT report. Only flags whose value space is enumerable / numeric / boolean
2119
- * (and therefore cannot leak user content, credentials, file paths, URLs, or customer IDs)
2120
- * belong here. When adding a new flag, ask: could this field carry PII, secrets, prompts,
2121
- * file paths, URLs, or tenant identifiers? If yes, do NOT add it.
2122
- */
2123
- const PARAM_ALLOWLIST = new Set([
2124
- "page",
2125
- "pageSize",
2126
- "n",
2127
- "count",
2128
- "model",
2129
- "voice",
2130
- "language",
2131
- "provider",
2132
- "capability",
2133
- "temperature",
2134
- "topP",
2135
- "topK",
2136
- "maxTokens",
2137
- "seed",
2138
- "stream",
2139
- "size",
2140
- "resolution",
2141
- "ratio",
2142
- "duration",
2143
- "format",
2144
- "audioFormat",
2145
- "sampleRate",
2146
- "pitch",
2147
- "rate",
2148
- "volume",
2149
- "api",
2150
- "mode",
2151
- "download",
2152
- "noWait",
2153
- "textOnly",
2154
- "promptExtend",
2155
- "enableSsml",
2156
- "watermark",
2157
- "hasThoughts",
2158
- "listTools",
2159
- "rerank",
2160
- "rerankTopN",
2161
- "diarization"
2162
- ]);
2163
- function extractParams(flags) {
2164
- const params = {};
2165
- for (const [key, value] of Object.entries(flags)) {
2166
- if (key.startsWith("_")) continue;
2167
- if (GLOBAL_FLAG_KEYS.has(key)) continue;
2168
- if (!PARAM_ALLOWLIST.has(key)) continue;
2169
- if (value === void 0 || value === false) continue;
2170
- params[key] = value;
2171
- }
2172
- return params;
2173
- }
2174
- async function trackCommandExecution(config, commandPath, flags, fn) {
2175
- if (!config.telemetry) {
2176
- await fn();
2177
- return;
2178
- }
2179
- const start = performance.now();
2180
- let success = true;
2181
- let errorMessage;
2182
- let httpStatus;
2183
- let requestId;
2184
- try {
2185
- await fn();
2186
- } catch (err) {
2187
- success = false;
2188
- if (err instanceof BailianError) {
2189
- errorMessage = err.message;
2190
- httpStatus = err.api?.httpStatus;
2191
- requestId = err.api?.requestId;
2192
- } else if (err instanceof Error) errorMessage = err.message;
2193
- throw err;
2194
- } finally {
2195
- const durationMs = Math.round(performance.now() - start);
2196
- let authMethod;
2197
- if (config.apiKey) authMethod = "api-key";
2198
- else if (config.fileApiKey) authMethod = "api-key";
2199
- else if (config.accessTokenEnv || config.fileAccessToken) authMethod = "access-token";
2200
- const event = createTrackingEvent({
2201
- command: commandPath.join(" "),
2202
- durationMs,
2203
- success,
2204
- error: success ? void 0 : {
2205
- message: errorMessage,
2206
- httpStatus,
2207
- requestId
2208
- },
2209
- cliVersion: config.clientVersion ?? "unknown",
2210
- authMethod,
2211
- params: extractParams(flags)
2212
- });
2213
- localSink(event).catch(() => {});
2214
- remoteSink(event).catch(() => {});
2215
- }
2216
- }
2217
- //#endregion
2218
- //#region src/advisor/sources/api.ts
2219
- const PAGE_SIZE = 50;
2220
- function toModelProfile(item) {
2221
- if (!item.model) return null;
2222
- const meta = item.inferenceMetadata;
2223
- return {
2224
- model: item.model,
2225
- name: item.name ?? item.model,
2226
- description: item.description ?? item.shortDescription ?? "",
2227
- shortDescription: item.shortDescription,
2228
- provider: item.provider ?? "",
2229
- capabilities: item.capabilities ?? [],
2230
- features: item.features ?? [],
2231
- category: item.category,
2232
- contextWindow: item.contextWindow ?? void 0,
2233
- maxOutputTokens: item.maxOutputTokens ?? void 0,
2234
- maxInputTokens: item.maxInputTokens ?? void 0,
2235
- docUrl: item.docUrl,
2236
- collectionTag: item.collectionTag,
2237
- inferenceMetadata: meta,
2238
- prices: item.prices,
2239
- qpmInfo: item.qpmInfo,
2240
- versionTag: item.versionTag,
2241
- openSource: item.openSource
2242
- };
2243
- }
2244
- var ApiSource = class {
2245
- name = "api";
2246
- constructor(config) {
2247
- this.config = config;
2248
- }
2249
- available() {
2250
- return true;
2251
- }
2252
- async load() {
2253
- const first = await fetchModelList(this.config, "", {
2254
- pageNo: 1,
2255
- pageSize: PAGE_SIZE
2256
- });
2257
- const allRaw = [...first.models];
2258
- const totalPages = Math.ceil(first.total / PAGE_SIZE);
2259
- for (let page = 2; page <= totalPages; page++) {
2260
- const result = await fetchModelList(this.config, "", {
2261
- pageNo: page,
2262
- pageSize: PAGE_SIZE
2263
- });
2264
- allRaw.push(...result.models);
2265
- }
2266
- return allRaw.map(toModelProfile).filter((profile) => profile !== null);
2267
- }
2268
- };
2269
- //#endregion
2270
- //#region src/advisor/sources/catalog.ts
2271
- const SKILL_DIR_NAME = "skills/doc-llm-wiki";
2272
- const MODELS_FILE = "models.jsonl";
2273
- function getCatalogDir() {
2274
- return join$1(getConfigDir(), SKILL_DIR_NAME);
2275
- }
2276
- function getCatalogPath() {
2277
- return join$1(getCatalogDir(), MODELS_FILE);
2278
- }
2279
- function getMonorepoModelsDir() {
2280
- return join$1(dirname(fileURLToPath(import.meta.url)), "../../../../../skills/doc-llm-wiki/models");
2281
- }
2282
- function fromJsonlRecord(raw) {
2283
- if (!raw.model || typeof raw.model !== "string") return null;
2284
- return {
2285
- model: raw.model,
2286
- name: raw.name ?? raw.model,
2287
- description: raw.description ?? "",
2288
- provider: raw.provider ?? "",
2289
- capabilities: raw.capabilities ?? [],
2290
- features: raw.features ?? [],
2291
- contextWindow: raw.contextWindow,
2292
- maxOutputTokens: raw.maxOutputTokens,
2293
- docUrl: raw.docUrl,
2294
- inferenceMetadata: raw.inferenceMetadata,
2295
- shortDescription: raw.shortDescription,
2296
- category: raw.category,
2297
- collectionTag: raw.collectionTag,
2298
- maxInputTokens: raw.maxInputTokens,
2299
- prices: raw.prices,
2300
- qpmInfo: raw.qpmInfo,
2301
- versionTag: raw.versionTag,
2302
- openSource: raw.openSource,
2303
- family: raw.family,
2304
- familyName: raw.familyName
2305
- };
2306
- }
2307
- function readJsonlModels(filePath) {
2308
- const lines = readFileSync$1(filePath, "utf-8").split("\n").filter(Boolean);
2309
- const models = [];
2310
- for (const line of lines) try {
2311
- const record = fromJsonlRecord(JSON.parse(line));
2312
- if (record) models.push(record);
2313
- } catch {}
2314
- return models;
2315
- }
2316
- function installFromMonorepo() {
2317
- const src = getMonorepoModelsDir();
2318
- if (!existsSync$1(join$1(src, MODELS_FILE))) return false;
2319
- const dest = getCatalogDir();
2320
- try {
2321
- mkdirSync$1(dest, { recursive: true });
2322
- cpSync(src, dest, { recursive: true });
2323
- return true;
2324
- } catch {
2325
- return false;
2326
- }
2327
- }
2328
- var CatalogSource = class {
2329
- name = "catalog";
2330
- options;
2331
- constructor(options) {
2332
- this.options = options ?? {};
2333
- }
2334
- available() {
2335
- return existsSync$1(getCatalogPath());
2336
- }
2337
- async load() {
2338
- if (!this.available()) {
2339
- this.options.onPrepareStart?.();
2340
- if (!installFromMonorepo()) return [];
2341
- }
2342
- return readJsonlModels(getCatalogPath());
2343
- }
2344
- };
2345
- //#endregion
2346
- //#region src/advisor/cache.ts
2347
- async function getModels(config, options) {
2348
- const sources = [new CatalogSource({ onPrepareStart: options?.onPrepareStart }), new ApiSource(config)];
2349
- for (const source of sources) if (source.available()) {
2350
- const models = await source.load();
2351
- if (models.length > 0) return models;
2352
- }
2353
- const models = await sources[0].load();
2354
- if (models.length > 0) return models;
2355
- throw new BailianError("No model data available.", ExitCode.GENERAL);
2356
- }
2357
- //#endregion
2358
- //#region src/advisor/types.ts
2359
- const Modalities = {
2360
- Text: "Text",
2361
- Image: "Image",
2362
- Video: "Video",
2363
- Audio: "Audio"
2364
- };
2365
- const Complexities = {
2366
- Single: "single",
2367
- Pipeline: "pipeline"
2368
- };
2369
- const Budgets = {
2370
- Low: "low",
2371
- Medium: "medium",
2372
- High: "high"
2373
- };
2374
- const ContextNeeds = {
2375
- Standard: "standard",
2376
- Large: "large",
2377
- ExtraLarge: "extra-large"
2378
- };
2379
- const QualityPreferences = {
2380
- Flagship: "flagship",
2381
- Balanced: "balanced",
2382
- CostOptimized: "cost-optimized"
2383
- };
2384
- const Capabilities = {
2385
- TG: "TG",
2386
- Reasoning: "Reasoning",
2387
- VU: "VU",
2388
- IG: "IG",
2389
- VG: "VG",
2390
- TTS: "TTS",
2391
- ASR: "ASR",
2392
- RealtimeASR: "Realtime-ASR",
2393
- RealtimeTTS: "Realtime-Text-to-Speech",
2394
- RealtimeAudioTranslate: "Realtime-Audio-Translate",
2395
- RealtimeOmni: "Realtime-Omni",
2396
- MultimodalOmni: "Multimodal-Omni",
2397
- ME: "ME",
2398
- TR: "TR",
2399
- ThreeDGeneration: "3D-generation"
2400
- };
2401
- const Features = {
2402
- FunctionCalling: "function-calling",
2403
- WebSearch: "web-search",
2404
- StructuredOutputs: "structured-outputs",
2405
- PrefixCompletion: "prefix-completion"
2406
- };
2407
- const ModelCategories = {
2408
- Flagship: "Flagship",
2409
- CostOptimized: "Cost-optimized"
2410
- };
2411
- //#endregion
2412
- //#region src/advisor/constants/prompts.ts
2413
- const INTENT_MODEL = "qwen-flash";
2414
- const RANKING_MODEL = "qwen3.6-flash";
2415
- const RANKING_MODEL_FAST = "qwen-flash";
2416
- const INTENT_SYSTEM_PROMPT = `You are an intent analyzer. Given the user's requirement, understand the scenario first, then extract structured information.
2417
-
2418
- CRITICAL: You MUST respond entirely in English. Do not use any Chinese characters anywhere in your response. All text fields (taskSummary, scenarioHints) must be in English.
2419
-
2420
- ## Analysis Steps
2421
- 1. Summarize the user's core need in one sentence (taskSummary) — be specific about the scenario, not generic
2422
- 2. Infer scenario hints (scenarioHints), e.g.: ["low-latency", "consumer-facing", "high-concurrency", "conversational", "offline-batch", "high-precision"]
2423
- 3. Infer budget and qualityPreference from scenario hints
2424
- - Only deviate from defaults when the user explicitly states or the scenario strongly implies
2425
- - User says "low cost", "cheap", "save money" → budget:"low"
2426
- - User says "best", "high precision", "cost no object" → qualityPreference:"flagship"
2427
- - Infer from scenario constraints only when strong: e.g. "1M requests/day customer service" → budget:"low" (high concurrency = cost-sensitive)
2428
- - Otherwise keep budget:"medium", qualityPreference:"balanced"
2429
- 4. Extract modalities, capabilities, features etc.
2430
-
2431
- ## Model preference detection
2432
- Analyze whether the user mentioned specific models, model families, or vendors:
2433
- - No models/families/vendors mentioned → mode:"unconstrained", no targets
2434
- - User scoped the range (e.g. "recommend from the deepseek family", "open-source reasoning models") → mode:"scoped", targets:["deepseek"]
2435
- - User wants to compare specific models (e.g. "compare wan2.6 and wan2.7", "is qwen-max good for legal analysis") → mode:"comparison", targets:["wan2.6","wan2.7"]
2436
- - Single model evaluation is also comparison with one target
2437
- - User wants alternatives to a reference model (e.g. "something like qwen-max but cheaper") → mode:"alternative", targets:["qwen-max"]
2438
- - User explicitly excludes certain models/families (e.g. "good models besides qwen") → excludes:["qwen"], mode determined by other signals
2439
- - targets should capture the model/family names as the user wrote them
2440
-
2441
- ## Output fields
2442
- - taskSummary: one-sentence scenario understanding (must be specific, never generic like "user wants AI")
2443
- - scenarioHints: array of inferred scenario features
2444
- - complexity: "single" or "pipeline"
2445
- - segments: only for pipeline, each with step/inputModality/outputModality/requiredCapabilities
2446
- - step must describe the specific problem this step solves in the user's task, no numbered or generic modal labels
2447
- - segments must form a modality chain: each step's inputModality should cover the previous step's outputModality
2448
- - inputModality: user input modalities ["Text","Image","Video","Audio"]
2449
- - outputModality: expected output modalities
2450
- - requiredCapabilities: capability codes (use strictly from the list, don't invent):
2451
- TG=Text Generation, Reasoning=Reasoning, VU=Vision Understanding, IG=Image Generation, VG=Video Generation,
2452
- TTS=Text-to-Speech, ASR=Speech-to-Text, Realtime-ASR=Realtime Speech-to-Text,
2453
- Realtime-Text-to-Speech=Realtime Text-to-Speech, Realtime-Audio-Translate=Realtime Audio Translation,
2454
- Realtime-Omni=Realtime Omni-modal, Multimodal-Omni=Multimodal Omni, ME=Multimodal Embedding,
2455
- TR=Translation, 3D-generation=3D Generation
2456
- - requiredFeatures: required features (function-calling, web-search, structured-outputs, prefix-completion)
2457
- - budget: "low"/"medium"/"high"
2458
- - contextNeed: "standard"/"large"/"extra-large"
2459
- - qualityPreference: "flagship"/"balanced"/"cost-optimized"
2460
- - modelPreference: { mode, targets?, excludes? }
2461
-
2462
- Output only JSON, no other text.`;
2463
- const SINGLE_SYSTEM_PROMPT = `You are a model recommendation advisor for Alibaba Cloud Model Studio. From the candidate models below, select the best recommendations.
1
+ import{createRequire as e}from"node:module";import{appendFileSync as t,createReadStream as n,existsSync as r,mkdirSync as i,readFileSync as a,renameSync as o,statSync as s,unlinkSync as c,writeFileSync as l}from"fs";import{homedir as u}from"os";import{basename as d,extname as f,join as p}from"path";import{stringify as m}from"yaml";import{createHash as h,createHmac as g,randomUUID as _}from"crypto";import{Readable as v}from"stream";import{createInterface as y}from"readline";import{cpSync as b,existsSync as x,mkdirSync as S,readFileSync as C,readdirSync as w,writeFileSync as ee}from"node:fs";import{dirname as T,join as E}from"node:path";import{fileURLToPath as D}from"node:url";var te=Object.create,ne=Object.defineProperty,re=Object.getOwnPropertyDescriptor,O=Object.getOwnPropertyNames,k=Object.getPrototypeOf,ie=Object.prototype.hasOwnProperty,A=(e,t)=>()=>(t||(e((t={exports:{}}).exports,t),e=null),t.exports),ae=(e,t,n,r)=>{if(t&&typeof t==`object`||typeof t==`function`)for(var i=O(t),a=0,o=i.length,s;a<o;a++)s=i[a],!ie.call(e,s)&&s!==n&&ne(e,s,{get:(e=>t[e]).bind(null,s),enumerable:!(r=re(t,s))||r.enumerable});return e},oe=(e,t,n)=>(n=e==null?{}:te(k(e)),ae(t||!e||!e.__esModule?ne(n,`default`,{value:e,enumerable:!0}):n,e)),j=e(import.meta.url);const M={SUCCESS:0,GENERAL:1,USAGE:2,AUTH:3,QUOTA:4,TIMEOUT:5,NETWORK:6,CONTENT_FILTER:10};var N=class extends Error{exitCode;hint;api;constructor(e,t=M.GENERAL,n,r){super(e,r?.cause===void 0?void 0:{cause:r.cause}),this.name=`BailianError`,this.exitCode=t,this.hint=n,this.api=r?.api}toJSON(){let e=se(this.cause);return{error:{code:this.exitCode,message:this.message,...this.hint?{hint:this.hint}:{},...this.api?.httpStatus===void 0?{}:{http_status:this.api.httpStatus},...this.api?.apiCode?{api_code:this.api.apiCode}:{},...this.api?.requestId?{request_id:this.api.requestId}:{},...e?{cause:e}:{}}}}};function se(e){if(e!=null){if(e instanceof Error){let t={message:e.message},n=e.code;return n&&(t.code=n),t}if(typeof e==`string`||typeof e==`number`||typeof e==`boolean`)return{message:String(e)};try{return{message:JSON.stringify(e)}}catch{return}}}function P(e,t,n){let r=t.error?.message||t.message||`HTTP ${e}`,i=t.error?.type??t.code,a=typeof i==`string`?i:typeof i==`number`?String(i):void 0;return new N(r,M.GENERAL,void 0,{api:{httpStatus:e,apiCode:a,requestId:t.request_id}})}const F={cn:`https://dashscope.aliyuncs.com`,us:`https://dashscope-us.aliyuncs.com`,intl:`https://dashscope-intl.aliyuncs.com`},ce={cn:`https://help.aliyun.com/zh/model-studio`,us:`https://help.aliyun.com/zh/model-studio`,intl:`https://help.aliyun.com/zh/model-studio`},le=`https://bailian.cn-beijing.aliyuncs.com`,ue=new Set([`text`,`json`]),de=new Set([`domestic`,`international`]);function fe(e){try{let t=new URL(e);return t.protocol===`http:`||t.protocol===`https:`}catch{return!1}}function pe(e){if(!e||typeof e!=`object`||Array.isArray(e))return{};let t=e,n={};return typeof t.api_key==`string`&&(n.api_key=t.api_key),typeof t.access_token==`string`&&t.access_token.length>0?n.access_token=t.access_token:typeof t.accessToken==`string`&&t.accessToken.length>0&&(n.access_token=t.accessToken),typeof t.base_url==`string`&&fe(t.base_url)&&(n.base_url=t.base_url),typeof t.output==`string`&&ue.has(t.output)&&(n.output=t.output),typeof t.output_dir==`string`&&t.output_dir.length>0&&(n.output_dir=t.output_dir),typeof t.timeout==`number`&&t.timeout>0&&(n.timeout=t.timeout),typeof t.default_text_model==`string`&&t.default_text_model.length>0&&(n.default_text_model=t.default_text_model),typeof t.default_video_model==`string`&&t.default_video_model.length>0&&(n.default_video_model=t.default_video_model),typeof t.default_image_model==`string`&&t.default_image_model.length>0&&(n.default_image_model=t.default_image_model),typeof t.default_speech_model==`string`&&t.default_speech_model.length>0&&(n.default_speech_model=t.default_speech_model),typeof t.default_omni_model==`string`&&t.default_omni_model.length>0&&(n.default_omni_model=t.default_omni_model),typeof t.access_key_id==`string`&&t.access_key_id.length>0&&(n.access_key_id=t.access_key_id),typeof t.access_key_secret==`string`&&t.access_key_secret.length>0&&(n.access_key_secret=t.access_key_secret),typeof t.workspace_id==`string`&&t.workspace_id.length>0&&(n.workspace_id=t.workspace_id),typeof t.console_site==`string`&&de.has(t.console_site)&&(n.console_site=t.console_site),typeof t.console_region==`string`&&t.console_region.length>0&&(n.console_region=t.console_region),typeof t.console_switch_agent==`number`&&t.console_switch_agent>0&&(n.console_switch_agent=t.console_switch_agent),typeof t.telemetry==`boolean`&&(n.telemetry=t.telemetry),n}function I(){return process.env.BAILIAN_CONFIG_DIR?process.env.BAILIAN_CONFIG_DIR:p(u(),`.bailian`)}function L(){return p(I(),`config.json`)}function me(){return p(I(),`credentials.json`)}async function he(){let e=I(),t=await import(`fs/promises`);await t.mkdir(e,{recursive:!0,mode:448});try{await t.chmod(e,448)}catch{}}function ge(e){return m(e).replace(/\n$/,``)}function _e(e){return JSON.stringify(e,null,2)}function ve(e,t,n){return JSON.stringify({error:{code:e,message:t,...n?{hint:n}:{}}},null,2)}function ye(e){return e===`json`||e===`text`?e:process.stdout.isTTY?`text`:`json`}function be(e,t){switch(t){case`json`:return _e(e);case`text`:return ge(e)}}function xe(){let e=L();if(!r(e))return{};try{return pe(JSON.parse(a(e,`utf-8`)))}catch(e){let t=e;return(t instanceof SyntaxError||t.message.includes(`JSON`))&&console.warn(`Warning: config file is corrupted; using defaults.`),{}}}async function Se(e){await he();let t=L(),n=t+`.tmp`;l(n,JSON.stringify(e,null,2)+`
2
+ `,{mode:384}),o(n,t)}function Ce(e){let t=xe(),n=e.apiKey||void 0,r=t.api_key,i=process.env.DASHSCOPE_ACCESS_TOKEN?.trim()||void 0,a=t.access_token?.trim()||void 0,o=e.baseUrl||t.base_url||process.env.DASHSCOPE_BASE_URL||F.cn,s=ye(e.output||process.env.DASHSCOPE_OUTPUT||t.output),c=process.env.DASHSCOPE_TIMEOUT?Number(process.env.DASHSCOPE_TIMEOUT):void 0,l=c!==void 0&&Number.isFinite(c)&&c>0?c:void 0,u=e.timeout??l??t.timeout??300;if(!Number.isFinite(u)||u<=0)throw new N(`Timeout must be a positive finite number.`,M.USAGE);return{apiKey:n,accessTokenEnv:i,fileAccessToken:a,fileApiKey:r,configPath:L(),baseUrl:o,output:s,outputDir:t.output_dir||void 0,timeout:u,defaultTextModel:t.default_text_model,defaultVideoModel:t.default_video_model,defaultImageModel:t.default_image_model,defaultSpeechModel:t.default_speech_model,defaultOmniModel:t.default_omni_model,accessKeyId:process.env.ALIBABA_CLOUD_ACCESS_KEY_ID||t.access_key_id||void 0,accessKeySecret:process.env.ALIBABA_CLOUD_ACCESS_KEY_SECRET||t.access_key_secret||void 0,workspaceId:process.env.BAILIAN_WORKSPACE_ID||t.workspace_id||void 0,consoleSite:e.consoleSite||t.console_site||void 0,consoleRegion:e.consoleRegion||t.console_region||void 0,consoleSwitchAgent:e.consoleSwitchAgent||t.console_switch_agent||void 0,verbose:e.verbose||process.env.DASHSCOPE_VERBOSE===`1`,quiet:e.quiet||!1,noColor:e.noColor||process.env.NO_COLOR!==void 0||!process.stdout.isTTY,yes:e.yes||!1,dryRun:e.dryRun||!1,nonInteractive:e.nonInteractive||!1,async:e.async||!1,telemetry:process.env.DO_NOT_TRACK===`1`?!1:t.telemetry??!0}}function we(){let e=L();if(!r(e))return null;try{let t=a(e,`utf-8`),n=JSON.parse(t);return typeof n.api_key==`string`&&n.api_key.length>0?n.api_key:null}catch{return null}}async function Te(e){await he();let t=L(),n={};try{n=JSON.parse(a(t,`utf-8`))}catch{}n.api_key=e;let r=t+`.tmp`;l(r,JSON.stringify(n,null,2)+`
3
+ `,{mode:384}),o(r,t)}async function Ee(){let e=L();if(r(e))try{let t=JSON.parse(a(e,`utf-8`));delete t.api_key,delete t.access_token;let n=e+`.tmp`;l(n,JSON.stringify(t,null,2)+`
4
+ `,{mode:384}),o(n,e)}catch{}}async function De(e){if(e.apiKey)return{token:e.apiKey,method:`api-key`,source:`flag`};if(e.fileApiKey)return{token:e.fileApiKey,method:`api-key`,source:`config.json`};if(e.accessTokenEnv)return{token:e.accessTokenEnv,method:`access-token`,source:`DASHSCOPE_ACCESS_TOKEN`};if(e.fileAccessToken)return{token:e.fileAccessToken,method:`access-token`,source:`config.json`};if(process.env.DASHSCOPE_API_KEY)return{token:process.env.DASHSCOPE_API_KEY,method:`api-key`,source:`DASHSCOPE_API_KEY`};throw new N(`No credentials found.`,M.AUTH,`Set DASHSCOPE_API_KEY environment variable, pass --api-key, or configure a key.`)}const Oe=`No console access token found.`;async function ke(e){if(e.accessTokenEnv)return{token:e.accessTokenEnv,method:`access-token`,source:`DASHSCOPE_ACCESS_TOKEN`};if(e.fileAccessToken)return{token:e.fileAccessToken,method:`access-token`,source:`config.json`};throw new N(Oe,M.AUTH,"Run `bl auth login --console` or set DASHSCOPE_ACCESS_TOKEN.")}function Ae(e){let t=e.method??`POST`,n=new Date().toISOString().replace(/\.\d{3}Z$/,`Z`),r=_(),i=je(e.body),a={host:e.host,"x-acs-action":e.action,"x-acs-version":e.version,"x-acs-date":n,"x-acs-signature-nonce":r,"x-acs-content-sha256":i,"content-type":`application/json`},o=Object.keys(a).filter(e=>e===`host`||e===`content-type`||e.startsWith(`x-acs-`)).sort(),s=o.map(e=>`${e}:${a[e]}`).join(`
5
+ `)+`
6
+ `,c=o.join(`;`),l=[t,e.pathname,``,s,c,i].join(`
7
+ `),u=`ACS3-HMAC-SHA256`,d=`${u}\n${je(l)}`,f=Me(e.accessKeySecret,d);return a.authorization=`${u} Credential=${e.accessKeyId},SignedHeaders=${c},Signature=${f}`,a}function je(e){return h(`sha256`).update(e,`utf8`).digest(`hex`)}function Me(e,t){return g(`sha256`,e).update(t,`utf8`).digest(`hex`)}function Ne(e){return`${e}/compatible-mode/v1/chat/completions`}function Pe(e){return`${e}/api/v1/services/aigc/image-generation/generation`}function Fe(e){return`${e}/api/v1/services/aigc/multimodal-generation/generation`}function Ie(e){return`${e}/api/v1/services/aigc/video-generation/video-synthesis`}function Le(e,t){return`${e}/api/v1/tasks/${encodeURIComponent(t)}`}function Re(e,t){return`${e}/api/v1/apps/${encodeURIComponent(t)}/completion`}function ze(e){return`${e}/api/v2/apps/memory/add`}function Be(e){return`${e}/api/v2/apps/memory/memory_nodes/search`}function Ve(e){return`${e}/api/v2/apps/memory/memory_nodes`}function He(e,t){return`${e}/api/v2/apps/memory/memory_nodes/${encodeURIComponent(t)}`}function Ue(e){return`${e}/api/v1/services/audio/tts/SpeechSynthesizer`}function We(e){return`${e}/api/v1/services/audio/asr/transcription`}function Ge(e){return`${e}/api/v2/apps/memory/profile_schemas`}function Ke(e,t){return`${e}/api/v2/apps/memory/profile_schemas/${encodeURIComponent(t)}/profiles`}function qe(e){return`${e}/api/v1/indices/rag/index/retrieve`}function Je(e){return`${e}/api/v1/mcps/WebSearch/mcp`}function Ye(e){return`${e}/compatible-mode/v1/files`}function Xe(e){return`${e}/api/v1/files`}function Ze(e,t){return`${e}/api/v1/files/${encodeURIComponent(t)}`}function Qe(e){return`${e}/api/v1/fine-tunes`}function $e(e,t){return`${e}/api/v1/fine-tunes/${encodeURIComponent(t)}`}function et(e,t){return`${e}/api/v1/fine-tunes/${encodeURIComponent(t)}/cancel`}function tt(e,t){return`${e}/api/v1/fine-tunes/${encodeURIComponent(t)}/logs`}function nt(e,t){return`${e}/api/v1/fine-tunes/${encodeURIComponent(t)}/checkpoints`}function rt(e,t,n){return`${e}/api/v1/fine-tunes/${encodeURIComponent(t)}/export/${encodeURIComponent(n)}`}function it(e){return`${e}/api/v1/deployments`}function at(e,t){return`${e}/api/v1/deployments/${encodeURIComponent(t)}`}function ot(e,t){return`${e}/api/v1/deployments/${encodeURIComponent(t)}/scale`}function st(e,t){return`${e}/api/v1/deployments/${encodeURIComponent(t)}/update`}function ct(e){return`${e}/api/v1/deployments/models`}const lt=`bailian-cli`,ut={t1:`public`,t2:``},dt=JSON.stringify({channel:lt,tags:ut});function R(){return{"x-dashscope-source-config":dt}}function ft(e){return e.length>8?`${e.slice(0,4)}...${e.slice(-4)}`:`***`}function pt(e){return typeof e!=`object`||!e||e instanceof FormData?!1:JSON.stringify(e).includes(`oss://`)}async function z(e,t){let n=typeof FormData<`u`&&t.body instanceof FormData,r={"User-Agent":`${e.clientName??`bailian-cli-core`}/${e.clientVersion??`0.0.0-dev`}`,...R(),...t.headers};if(!n&&!r[`Content-Type`]&&(r[`Content-Type`]=`application/json`),t.async&&(r[`X-DashScope-Async`]=`enable`),pt(t.body)&&(r[`X-DashScope-OssResourceResolve`]=`enable`),!t.noAuth){let n=await De(e);r.Authorization=`Bearer ${n.token}`,e.verbose&&(console.error(`> ${t.method??`GET`} ${t.url}`),console.error(`> Auth: ${ft(n.token)}`),console.error(`> x-dashscope-source-config: ${dt}`))}let i=mt((t.timeout??e.timeout)*1e3,t.signal),a=await fetch(t.url,{method:t.method??`GET`,headers:r,body:t.body?n?t.body:JSON.stringify(t.body):void 0,signal:i.signal}).finally(i.cleanup);if(e.verbose){console.error(`< ${a.status} ${a.statusText}`);let e=a.headers.get(`x-request-id`);e&&console.error(`request_id: ${e}`)}if(!a.ok){let e={};try{e=await a.json()}catch{}throw P(a.status,e,t.url)}return a}function mt(e,t){let n=new AbortController,r=setTimeout(()=>n.abort(),e),i=()=>n.abort(t?.reason),a=()=>{clearTimeout(r),t?.removeEventListener(`abort`,i)};return t?.aborted?i():t?.addEventListener(`abort`,i,{once:!0}),n.signal.addEventListener(`abort`,a,{once:!0}),{signal:n.signal,cleanup:a}}async function B(e,t){let n=await z(e,t),r;try{r=await n.json()}catch{throw new N(`API returned non-JSON response (${n.headers.get(`content-type`)||`unknown type`}). Server may be experiencing issues.`,M.GENERAL)}if(r.code&&typeof r.code==`string`&&r.code!==`200`&&r.code!==`Success`)throw P(200,{error:{message:r.message,type:r.code}},t.url);return r}function ht(e,t){return`${e.replace(/\/$/,``)}/api/v1/mcps/${t}/mcp`}var gt=class{url;sessionId;nextId=1;config;authToken;constructor(e,t){this.config=e,this.url=t}async initialize(){let e=await De(this.config);this.authToken=e.token;let t=await this.rpc(`initialize`,{protocolVersion:`2025-03-26`,capabilities:{},clientInfo:{name:this.config.clientName??`bailian-cli-core`,version:this.config.clientVersion??`0.0.0-dev`}});this.config.verbose&&(console.error(`[MCP] Session initialized: ${this.sessionId??`no session`}`),console.error(`[MCP] Server: ${JSON.stringify(t)}`)),await this.notify(`notifications/initialized`)}async listTools(){return(await this.rpc(`tools/list`)).tools||[]}async callTool(e,t){return await this.rpc(`tools/call`,{name:e,arguments:t})}async rpc(e,t){let n={jsonrpc:`2.0`,id:this.nextId++,method:e,...t?{params:t}:{}},r=await(await this.send(n)).json();if(r.error)throw new N(`MCP error (${r.error.code}): ${r.error.message}`,M.GENERAL);return r.result}async notify(e,t){let n={jsonrpc:`2.0`,method:e,...t?{params:t}:{}};await this.send(n)}async send(e){let t={"Content-Type":`application/json`,Accept:`application/json, text/event-stream`,"User-Agent":`${this.config.clientName??`bailian-cli-core`}/${this.config.clientVersion??`0.0.0-dev`}`,...R()};this.authToken&&(t.Authorization=`Bearer ${this.authToken}`),this.sessionId&&(t[`Mcp-Session-Id`]=this.sessionId),this.config.verbose&&(console.error(`> POST ${this.url}`),console.error(`> Method: ${e.method}`));let n=this.config.timeout*1e3,r=await fetch(this.url,{method:`POST`,headers:t,body:JSON.stringify(e),signal:AbortSignal.timeout(n)});this.config.verbose&&console.error(`< ${r.status} ${r.statusText}`);let i=r.headers.get(`Mcp-Session-Id`)||r.headers.get(`mcp-session-id`);if(i&&(this.sessionId=i),!r.ok){let e=`MCP request failed: ${r.status} ${r.statusText}`;try{let t=await r.text();t&&(e+=` - ${t.slice(0,500)}`)}catch{}throw new N(e,M.GENERAL)}return r}};async function*_t(e){let t=e.body?.getReader();if(!t)return;let n=new TextDecoder,r=``,i=16*1024*1024;try{for(;;){let{done:e,value:a}=await t.read();if(e)break;if(r+=n.decode(a,{stream:!0}),r.length>i)throw new N(`SSE stream exceeded the maximum buffer size.`,M.GENERAL);let o=r.split(`
8
+ `);r=o.pop()||``;let s={};for(let e of o){if(e===``){s.data!==void 0&&(yield{data:s.data,event:s.event,id:s.id}),s={};continue}if(e.startsWith(`:`))continue;let t=e.indexOf(`:`);if(t===-1)continue;let n=e.slice(0,t),r=e.slice(t+1).trimStart();switch(n){case`data`:if(s.data=s.data===void 0?r:`${s.data}\n${r}`,s.data.length>i)throw new N(`SSE event exceeded the maximum buffer size.`,M.GENERAL);break;case`event`:s.event=r;break;case`id`:s.id=r;break}}}if(r.trim()&&r.includes(`data:`)){let e=r.indexOf(`:`);e!==-1&&(yield{data:r.slice(e+1).trimStart()})}}finally{t.releaseLock()}}const vt={"cn-beijing":{domestic:{csGateway:`bailian-cs.console.aliyun.com`,action:`BroadScopeAspnGateway`},international:{csGateway:`bailian-cs.console.alibabacloud.com`,action:`BroadScopeAspnGateway`}},"ap-southeast-1":{domestic:{csGateway:`modelstudio-cs.console.aliyun.com`,action:`IntlBroadScopeAspnGateway`},international:{csGateway:`bailian-singapore-cs.alibabacloud.com`,action:`IntlBroadScopeAspnGateway`}}};function yt(e,t){return vt[e]?.[t]??vt[`cn-beijing`][t]}function bt(e){let t=e.consoleRegion??`cn-beijing`,n=e.consoleSite??`domestic`,r=e.consoleSwitchAgent;return r==null?{consoleRegion:t,consoleSite:n}:{consoleRegion:t,consoleSite:n,consoleSwitchAgent:r}}function xt(e,t,n){return JSON.stringify({Api:e,V:`1.0`,Data:{...t,cornerstoneParam:{protocol:`V2`,console:`ONE_CONSOLE`,productCode:`p_efm`,consoleSite:`BAILIAN_ALIYUN`,...n==null?{}:{switchAgent:n},...typeof t.cornerstoneParam==`object`&&t.cornerstoneParam!==null?t.cornerstoneParam:{}}}})}async function St(e,t,{api:n,data:r}){let{consoleRegion:i,consoleSite:a,consoleSwitchAgent:o}=bt(e),s=yt(i,a),c=`https://${s.csGateway}`,l=s.action,u=xt(n,r,o),d=new URLSearchParams({params:u,region:i}),f=e.timeout*1e3,p={Accept:`*/*`,"Content-Type":`application/x-www-form-urlencoded`};t&&(p.Authorization=`Bearer ${t}`);let m=await fetch(`${c}/cli/api.json?action=${l}&product=sfm_bailian&api=${encodeURIComponent(n)}`,{method:`POST`,headers:p,body:d.toString(),signal:AbortSignal.timeout(f)});if(!m.ok){let e=await m.text().catch(()=>``);throw new N(`Console CLI gateway failed: HTTP ${m.status} ${m.statusText}`,M.GENERAL,e.slice(0,500))}let h=await m.json(),g=h.data;if(g?.success===!1&&g.errorCode){let e=g.errorCode,t=typeof e==`string`?e:JSON.stringify(e),n=t.includes(`NotLogined`),r=typeof g.errorMsg==`string`?g.errorMsg:void 0;throw new N(n?`Console session is not logged in or has expired.`:`Console gateway error: ${t}`,n?M.AUTH:M.GENERAL,n?"Run `bl auth login --console` to sign in or refresh your console session.":r&&r!==t?r:void 0)}return h}async function V(e,t,n={}){let{pageNo:r=1,pageSize:i=50,name:a=``,providers:o=[],capabilities:s=[]}=n,c=await St(e,t,{api:`zeldaHttp.dashscopeModel./zelda/api/v1/modelCenter/listFoundationModels`,data:{input:{pageNo:r,pageSize:i,name:a,providers:o,inferenceProviders:[],features:[],group:!0,capabilities:s,contextWindows:[]}}}),l=c?.data?.DataV2?.data??c?.data??{},u=l?.data?.total??l?.total??0,d=l?.data?.list??l?.list??[],f=[];for(let e of d)if(e.items?.length)for(let t of e.items)f.push(t);else f.push(e);return{total:u,models:f}}const Ct=`${F.cn}/api/v1/uploads`;async function wt(e,t,n){let r=`${Ct}?action=getPolicy&model=${encodeURIComponent(t)}`,i=kt(15e3,n),a=await fetch(r,{headers:{Authorization:`Bearer ${e}`,"Content-Type":`application/json`,...R()},signal:i.signal}).finally(i.cleanup);if(!a.ok){let e=await a.text().catch(()=>``);throw new N(`Failed to get upload policy (HTTP ${a.status}): ${e}`,M.GENERAL)}return(await a.json()).data}async function Tt(e,t,n){let r=d(t),i=`${e.upload_dir}/${r}`,o=a(t),s=new FormData;s.append(`OSSAccessKeyId`,e.oss_access_key_id),s.append(`Signature`,e.signature),s.append(`policy`,e.policy),s.append(`x-oss-object-acl`,e.x_oss_object_acl),s.append(`x-oss-forbid-overwrite`,e.x_oss_forbid_overwrite),s.append(`key`,i),s.append(`success_action_status`,`200`),s.append(`file`,new Blob([o]),r);let c=kt(12e4,n),l=await fetch(e.upload_host,{method:`POST`,headers:{...R()},body:s,signal:c.signal}).finally(c.cleanup);if(!l.ok){let e=await l.text().catch(()=>``);throw new N(`Failed to upload file to OSS (HTTP ${l.status}): ${e}`,M.GENERAL)}return`oss://${i}`}async function Et(e){let{apiKey:t,model:n,filePath:i,signal:a}=e;if(!r(i))throw new N(`File not found: ${i}`,M.USAGE);if(!s(i).isFile())throw new N(`Not a file: ${i}`,M.USAGE);return Tt(await wt(t,n,a),i,a)}function Dt(e){return e.startsWith(`http://`)||e.startsWith(`https://`)||e.startsWith(`oss://`)||e.startsWith(`data:`)?!1:r(e)}async function Ot(e,t,n,r={}){return Dt(e)?Et({apiKey:t,model:n,filePath:e,signal:r.signal}):e}function kt(e,t){let n=new AbortController,r=setTimeout(()=>n.abort(),e),i=()=>n.abort(t?.reason),a=()=>{clearTimeout(r),t?.removeEventListener(`abort`,i)};return t?.aborted?i():t?.addEventListener(`abort`,i,{once:!0}),n.signal.addEventListener(`abort`,a,{once:!0}),{signal:n.signal,cleanup:a}}async function At(e,t){let{filePath:r,purpose:i=`fine-tune`,signal:a}=t,o=s(r),c=d(r),l=v.toWeb(n(r)),u=await new Response(l).blob(),f=new FormData;f.append(`file`,u,c),f.append(`purpose`,i);let p=await B(e,{url:Ye(e.baseUrl),method:`POST`,body:f,signal:a});if(p.id)return{file_id:p.id,name:p.filename??c,size:p.bytes??o.size,purpose:p.purpose??i,gmt_create:p.created_at?new Date(p.created_at*1e3).toISOString():void 0};let m=p.data?.failed_uploads;if(Array.isArray(m)&&m.length>0){let e=m[0]??{};throw new N(`Dataset upload failed${e.code?` [${e.code}]`:``}: ${e.message??`no message returned`}`,M.GENERAL,`Server reported failure for ${c}. Re-run with --verbose to see the raw response.`)}throw new N(`Dataset upload of ${c} returned no file_id (HTTP 200 with empty payload).`,M.GENERAL,`The platform accepted the request but did not allocate a file_id. Retry the upload; if it recurs, contact platform support with the request id.`)}async function jt(e,t={}){let n=new URLSearchParams;t.pageNo!==void 0&&n.set(`page_no`,String(t.pageNo)),t.pageSize!==void 0&&n.set(`page_size`,String(t.pageSize)),t.purpose&&n.set(`purpose`,t.purpose);let r=Xe(e.baseUrl);return B(e,{url:n.toString()?`${r}?${n.toString()}`:r,method:`GET`,signal:t.signal})}async function Mt(e,t,n){return B(e,{url:Ze(e.baseUrl,t),method:`GET`,signal:n})}async function Nt(e,t,n){let r=await z(e,{url:Ze(e.baseUrl,t),method:`DELETE`,signal:n});try{return await r.json()}catch{return{data:{deleted:!0,file_id:t}}}}const Pt=300*1024*1024;function Ft(e,t=Pt){if(!r(e))throw new N(`File not found: ${e}`,M.USAGE);let n=s(e);if(!n.isFile())throw new N(`Not a regular file: ${e}`,M.USAGE);if(n.size===0)throw new N(`File is empty: ${e}`,M.USAGE);if(n.size>t)throw new N(`File too large: ${(n.size/(1024*1024)).toFixed(1)}MB exceeds the ${(t/(1024*1024)).toFixed(0)}MB dataset upload cap.`,M.USAGE);return{bytes:n.size,ext:f(e).toLowerCase()}}function H(e,t,n,r={}){return{severity:e,code:t,message:n,...r}}function It(e){if(e===void 0||e.trim()===``)return;let t=e.trim();if(t===`chatml`||t===`dpo`||t===`cpt`)return t;throw new N(`Unsupported --schema "${e}". Supported: chatml, dpo, cpt.`,M.USAGE,`Omit --schema to auto-detect per record (chosen/rejected → DPO, text → CPT, else ChatML).`)}function Lt(e,t=50,n=100,r=10){if(e<=0)return[];if(e<=t+r)return Array.from({length:e},(e,t)=>t+1);let i=new Set;for(let n=1;n<=Math.min(t,e);n++)i.add(n);for(let t=0;t<r;t++)i.add(e-t);let a=Math.max(1,Math.ceil(e/n));for(let n=t+1;n<=e-r;n+=a)i.add(n);return[...i].filter(t=>t>=1&&t<=e).sort((e,t)=>e-t)}const Rt=new Set([`system`,`user`,`assistant`]);function zt(e,t,n){let r=[];if(typeof e!=`object`||!e||Array.isArray(e))return r.push(H(`error`,`MESSAGE_NOT_OBJECT`,`Message must be an object.`,{line:t,path:n})),r;let i=e,a=i.role,o=i.content;return(typeof a!=`string`||!Rt.has(a))&&r.push(H(`error`,`INVALID_ROLE`,`Invalid role "${String(a)}". Expected one of: system, user, assistant.`,{line:t,path:`${n}.role`})),typeof o!=`string`&&r.push(H(`error`,`INVALID_CONTENT`,`"content" must be a string (got ${typeof o}).`,{line:t,path:`${n}.content`})),r}function Bt(e,t){let n=[],r=e.messages;if(!Array.isArray(r))return n.push(H(`error`,`MISSING_MESSAGES`,`Required field "messages" is missing or not an array.`,{line:t,path:`messages`})),n;if(r.length===0)return n.push(H(`error`,`EMPTY_MESSAGES`,`"messages" must contain at least one entry.`,{line:t,path:`messages`})),n;let i=!1,a;for(let e=0;e<r.length;e++){let o=r[e],s=`messages[${e}]`;n.push(...zt(o,t,s));let c=o?.role;c===`system`&&(e!==0&&n.push(H(`warning`,`SYSTEM_NOT_FIRST`,`"system" message should appear at index 0; found at index ${e}.`,{line:t,path:`${s}.role`})),i=!0),a===c&&(c===`user`||c===`assistant`)&&n.push(H(`warning`,`ROLE_NOT_ALTERNATING`,`Consecutive ${c} messages — user/assistant turns should typically alternate.`,{line:t,path:`${s}.role`})),typeof c==`string`&&(a=c)}return r.some(e=>e.role===`user`)||n.push(H(`warning`,`NO_USER_ROLE`,`No "user" message found in this sample.`,{line:t,path:`messages`})),i&&r.length===1&&n.push(H(`warning`,`SYSTEM_ONLY`,`Sample only contains a "system" message.`,{line:t,path:`messages`})),n}const Vt={name:`chatml`,detect:()=>!0,inspect:Bt};function Ht(e,t){let n=[];if(!(`text`in e))return n.push(H(`error`,`MISSING_TEXT`,`Required field "text" is missing.`,{line:t,path:`text`})),n;let r=e.text;return typeof r==`string`?(r.trim().length===0&&n.push(H(`error`,`EMPTY_TEXT`,`"text" must not be empty / whitespace-only.`,{line:t,path:`text`})),n):(n.push(H(`error`,`INVALID_TEXT`,`"text" must be a string (got ${typeof r}).`,{line:t,path:`text`})),n)}const Ut={name:`cpt`,detect:e=>`text`in e&&!(`messages`in e),inspect:Ht};function Wt(e,t){let n=Bt(e,t),r=e.messages;if(!Array.isArray(r)||r.length===0)return n;let i=`chosen`in e,a=`rejected`in e;if(i||n.push(H(`error`,`MISSING_CHOSEN`,`DPO record is missing the "chosen" preference.`,{line:t,path:`chosen`})),a||n.push(H(`error`,`MISSING_REJECTED`,`DPO record is missing the "rejected" preference.`,{line:t,path:`rejected`})),i){n.push(...zt(e.chosen,t,`chosen`));let r=e.chosen?.role;typeof r==`string`&&r!==`assistant`&&n.push(H(`warning`,`PREFERENCE_ROLE_NOT_ASSISTANT`,`"chosen" role should be "assistant" (got "${r}").`,{line:t,path:`chosen.role`}))}if(a){n.push(...zt(e.rejected,t,`rejected`));let r=e.rejected?.role;typeof r==`string`&&r!==`assistant`&&n.push(H(`warning`,`PREFERENCE_ROLE_NOT_ASSISTANT`,`"rejected" role should be "assistant" (got "${r}").`,{line:t,path:`rejected.role`}))}return n}const Gt=[{name:`dpo`,detect:e=>`chosen`in e||`rejected`in e,inspect:Wt},Ut,Vt];function Kt(e,t){return t===void 0?Gt.find(t=>t.detect(e))??Vt:Gt.find(e=>e.name===t)||Vt}async function qt(e,t){let r=y({input:n(e,{encoding:`utf8`}),crlfDelay:1/0}),i=[],a=0,o=0;for await(let e of r){if(t?.aborted)break;a++;let n=e.trim();if(n.length===0){o++;continue}i.length>=20||(n[0]!==`{`||n[n.length-1]!==`}`)&&i.push(H(`error`,`MALFORMED_LINE`,`Line does not start with '{' and end with '}'. JSONL requires one minified JSON object per line — pretty-printed JSON or arrays are not accepted here.`,{line:a}))}return{totalLines:a,blankLines:o,issues:i}}async function Jt(e,t,r,i,a){let o=r?null:new Set(Lt(t)),s=[],c=0,l=y({input:n(e,{encoding:`utf8`}),crlfDelay:1/0}),u=0;for await(let e of l){if(a?.aborted)break;if(u++,o&&!o.has(u))continue;let t=e.trim();if(t.length===0||(c++,s.length>=30))continue;let n;try{n=JSON.parse(t)}catch(e){s.push(H(`error`,`MALFORMED_JSON`,`JSON.parse failed: ${e.message}`,{line:u}));continue}s.push(...Yt(n,u,i))}return{sampled:c,issues:s}}function Yt(e,t,n){if(typeof e!=`object`||!e||Array.isArray(e))return[H(`error`,`RECORD_NOT_OBJECT`,`Each line must be a JSON object, got ${Array.isArray(e)?`array`:typeof e}.`,{line:t})];let r=e;return Kt(r,n).inspect(r,t)}const U=[{format:`jsonl`,extensions:[`.jsonl`],async validate(e,t){let n=Date.now(),r=await qt(e,t.signal);if(r.totalLines===0||r.totalLines===r.blankLines)return{valid:!1,format:`jsonl`,filePath:e,errors:[H(`error`,`EMPTY_FILE`,`File contains no non-blank lines.`)],warnings:[],stats:{totalRecords:0,sampledRecords:0,durationMs:Date.now()-n}};if(r.issues.length>0)return{valid:!1,format:`jsonl`,filePath:e,errors:r.issues,warnings:[],stats:{totalRecords:r.totalLines-r.blankLines,sampledRecords:0,durationMs:Date.now()-n}};let i=await Jt(e,r.totalLines,!!t.fullValidate,t.schema,t.signal),a=i.issues.filter(e=>e.severity===`error`),o=i.issues.filter(e=>e.severity===`warning`);return{valid:a.length===0,format:`jsonl`,filePath:e,errors:a,warnings:o,stats:{totalRecords:r.totalLines-r.blankLines,sampledRecords:i.sampled,durationMs:Date.now()-n}}}}];function Xt(e){let t=f(e).toLowerCase(),n=U.find(e=>e.extensions.includes(t));if(!n){let e=U.flatMap(e=>e.extensions).join(`, `);throw new N(`Unsupported dataset format "${t||`(none)`}". Supported: ${e}`,M.USAGE,`Convert your data to one of the supported formats and re-run.`)}return n}function Zt(e){U.some(t=>t.format===e.format)||U.push(e)}async function Qt(e,t={}){let{bytes:n}=Ft(e,t.maxBytes??314572800),r=await Xt(e).validate(e,t);return r.stats.bytes===void 0&&(r.stats.bytes=n),r}function $t(){return U.map(e=>({format:e.format,extensions:[...e.extensions]}))}function en(e){let t=[];e.line!==void 0&&t.push(`line ${e.line}`),e.path&&t.push(e.path);let n=t.length?` [${t.join(` · `)}]`:``;return` ${e.severity.toUpperCase()} ${e.code}${n}: ${e.message}`}async function tn(e,t,n){return B(e,{url:Qe(e.baseUrl),method:`POST`,body:t,signal:n})}async function nn(e,t={}){let n=new URLSearchParams;t.pageNo!==void 0&&n.set(`page_no`,String(t.pageNo)),t.pageSize!==void 0&&n.set(`page_size`,String(t.pageSize)),t.status&&n.set(`status`,t.status);let r=Qe(e.baseUrl);return B(e,{url:n.toString()?`${r}?${n.toString()}`:r,method:`GET`,signal:t.signal})}async function rn(e,t,n){return B(e,{url:$e(e.baseUrl,t),method:`GET`,signal:n})}async function an(e,t,n){return B(e,{url:et(e.baseUrl,t),method:`POST`,signal:n})}async function on(e,t,n){return B(e,{url:$e(e.baseUrl,t),method:`DELETE`,signal:n})}async function sn(e,t,n={}){let r=new URLSearchParams;n.pageNo!==void 0&&r.set(`page_no`,String(n.pageNo)),n.pageSize!==void 0&&r.set(`page_size`,String(n.pageSize));let i=tt(e.baseUrl,t);return B(e,{url:r.toString()?`${i}?${r.toString()}`:i,method:`GET`,signal:n.signal})}async function cn(e,t,n){return B(e,{url:nt(e.baseUrl,t),method:`GET`,signal:n})}async function ln(e,t,n,r,i){let a=new URLSearchParams;return a.set(`model_name`,r),B(e,{url:`${rt(e.baseUrl,t,n)}?${a.toString()}`,method:`GET`,signal:i})}const W={sft:{server:`sft`,method:`sft`,variant:`full`},"sft-lora":{server:`efficient_sft`,method:`sft`,variant:`lora`},dpo:{server:`dpo_full`,method:`dpo`,variant:`full`},"dpo-lora":{server:`dpo_lora`,method:`dpo`,variant:`lora`},cpt:{server:`cpt`,method:`cpt`,variant:`full`}},un=Object.keys(W),dn=`sft-lora`;function fn(e){return e in W}function pn(e){return W[e].server}function mn(e){let{method:t,variant:n}=W[e];return{method:t,variant:n}}function hn(e,t){if(!e)return!1;let{method:n,variant:r}=W[t];if(e.supports?.[n]!==!0)return!1;let i=e.trainingTypes?.[n];return Array.isArray(i)&&i.includes(r)}function gn(e){return e?un.filter(t=>hn(e,t)):[]}async function _n(e,t){return(await V(e,``,{name:t,pageSize:20})).models.find(e=>e.model===t)??null}const vn=`INSUFFICIENT_SAMPLES`;function yn(e){let{recordCount:t,batchSize:n}=e;return t>n?{ok:!0}:{ok:!1,issue:{severity:`error`,code:vn,message:`Training dataset has ${t} sample(s), which is not greater than batch_size (${n}).`},hint:[`The platform requires the number of training samples to exceed batch_size.`,`Options:`,` • add more data (recommended: comfortably more than batch_size, since the`,` platform also holds back a default 0.9 train split),`,` • lower --batch-size (server clamps to a minimum of 8).`].join(`
9
+ `)}}async function bn(e,t,n){return B(e,{url:it(e.baseUrl),method:`POST`,body:t,signal:n})}async function xn(e,t={}){let n=new URLSearchParams;t.pageNo!==void 0&&n.set(`page_no`,String(t.pageNo)),t.pageSize!==void 0&&n.set(`page_size`,String(t.pageSize)),t.status&&n.set(`status`,t.status);let r=it(e.baseUrl);return B(e,{url:n.toString()?`${r}?${n.toString()}`:r,method:`GET`,signal:t.signal})}async function Sn(e,t,n){return B(e,{url:at(e.baseUrl,t),method:`GET`,signal:n})}async function Cn(e,t,n){return B(e,{url:at(e.baseUrl,t),method:`DELETE`,signal:n})}async function wn(e,t={}){let n=new URLSearchParams;t.pageNo!==void 0&&n.set(`page_no`,String(t.pageNo)),t.pageSize!==void 0&&n.set(`page_size`,String(t.pageSize)),t.version&&n.set(`version`,t.version),t.modelSource&&n.set(`model_source`,t.modelSource);let r=ct(e.baseUrl);return B(e,{url:n.toString()?`${r}?${n.toString()}`:r,method:`GET`,signal:t.signal})}async function Tn(e,t,n,r){return B(e,{url:ot(e.baseUrl,t),method:`PUT`,body:n,signal:r})}async function En(e,t,n,r){return B(e,{url:st(e.baseUrl,t),method:`PUT`,body:n,signal:r})}function Dn(e){return{description:e.description,usageArgs:e.usageArgs,options:e.options,exampleArgs:e.exampleArgs,skipDefaultApiKeySetup:e.skipDefaultApiKeySetup,notes:e.notes,execute:(t,n)=>e.run(t,n)}}const On=[{flag:`--api-key <key>`,description:`API key`},{flag:`--base-url <url>`,description:`API base URL`},{flag:`--output <format>`,description:`Output format: text, json`},{flag:`--timeout <seconds>`,description:`Request timeout`,type:`number`},{flag:`--quiet`,description:`Suppress non-essential output`},{flag:`--verbose`,description:`Print HTTP request/response details`},{flag:`--no-color`,description:`Disable ANSI colors`},{flag:`--dry-run`,description:`Dry run mode`},{flag:`--non-interactive`,description:`Disable interactive prompts`},{flag:`--concurrent <n>`,description:`Run N parallel requests (default: 1)`,type:`number`},{flag:`--console-region <region>`,description:`Console gateway region (e.g. cn-beijing, ap-southeast-1)`},{flag:`--console-site <site>`,description:`Console site: domestic, international`},{flag:`--console-switch-agent <uid>`,description:`Switch agent UID for delegated access`,type:`number`},{flag:`--help`,description:`Show help`},{flag:`--version`,description:`Print version`}];function kn(e,t){return e.normalize(`NFKC`).replace(/[\\/:*?"<>|]/g,`_`).replace(/\s+/g,`_`).replace(/_+/g,`_`).replace(/^_+|_+$/g,``)||t}function An(e,t){return`${kn(e||`image`,`image`)}_${kn((t||``).substring(0,20),`untitled`)}_${Date.now()}`}const jn=()=>p(u(),`bailian-output`);function Mn(e,t){let n=t?.flagDir||e.outputDir||jn(),a=t?.subDir?p(n,t.subDir):n;return r(a)||i(a,{recursive:!0}),a}function Nn(e){return e?.nonInteractive===!0||process.env.CI?!1:process.stdout.isTTY===!0&&process.stdin.isTTY===!0}function Pn(){return!!(process.env.CI||process.env.GITHUB_ACTIONS||process.env.GITLAB_CI||process.env.JENKINS_URL||process.env.TRAVIS||process.env.CIRCLECI)}function Fn(e){for(let t of Object.keys(e))e[t]===void 0&&delete e[t];return e}function In(e,t=`boolean`){if(typeof e==`boolean`)return e;if(typeof e==`string`){let t=e.trim().toLowerCase();if(t===`true`)return!0;if(t===`false`)return!1}throw new N(`Invalid ${t} value "${String(e)}". Use true or false.`,M.USAGE)}function Ln(e,t=`boolean`){if(e!=null)return In(e,t)}function Rn(e,t,n=`boolean`){let r=Ln(e,n);return r===void 0?t:r}function zn(e){return Ln(e,`watermark`)??!0}function Bn(e){let t={command:e.command,timestamp:new Date().toISOString(),durationMs:e.durationMs,success:e.success,cliVersion:e.cliVersion,nodeVersion:process.version,os:process.platform};return e.authMethod&&(t.authMethod=e.authMethod),!e.success&&e.error&&(e.error.message&&(t.errorMessage=e.error.message),e.error.httpStatus!==void 0&&(t.httpStatus=e.error.httpStatus),e.error.requestId&&(t.requestId=e.error.requestId)),e.params&&Object.keys(e.params).length>0&&(t.params=e.params),t}function Vn(e){if(e==null)return;let t=typeof e==`string`?e:JSON.stringify(e);return t.length<=500?t:t.slice(0,500)}function Hn(e){let{command:t,params:n,...r}=e,i={et:`EXP`,ext:r,c1:n,c2:e.success?`success`:`failure`};return e.httpStatus!==void 0&&(i.c3=String(e.httpStatus)),e.errorMessage&&(i.c4=Vn(e.errorMessage)),e.requestId&&(i.c5=e.requestId),i}let G;function Un(){return G||(process.env.NODE_ENV===`development`?(G=`dev`,G):(G=import.meta.url.includes(`/node_modules/`)?`prod`:`dev`,G))}var Wn=A(((e,t)=>{t.exports=(function(e){var t={};function n(r){if(t[r])return t[r].exports;var i=t[r]={i:r,l:!1,exports:{}};return e[r].call(i.exports,i,i.exports,n),i.l=!0,i.exports}return n.m=e,n.c=t,n.d=function(e,t,r){n.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:r})},n.r=function(e){typeof Symbol<`u`&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:`Module`}),Object.defineProperty(e,`__esModule`,{value:!0})},n.t=function(e,t){if(1&t&&(e=n(e)),8&t||4&t&&typeof e==`object`&&e&&e.__esModule)return e;var r=Object.create(null);if(n.r(r),Object.defineProperty(r,`default`,{enumerable:!0,value:e}),2&t&&typeof e!=`string`)for(var i in e)n.d(r,i,function(t){return e[t]}.bind(null,i));return r},n.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return n.d(t,`a`,t),t},n.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},n.p=``,n(n.s=8)})([function(e,t){e.exports=j(`os`)},function(e,t){e.exports=globalThis.fetch},function(e,t,n){e.exports=n(6)},function(e,t){e.exports=j(`dns`)},function(e,t){e.exports=j(`util`)},function(e,t){e.exports=j(`crypto`)},function(e,t,n){Object.defineProperty(t,Symbol.toStringTag,{value:`Module`});let r=n(7),i=(e,t)=>{t.appName=`BaiduSpider`,t.appVersion=e.value,t.deviceBrand=`Baidu`,t.deviceType=`bot`,t.platform=`other`},a=(e,t)=>{t.appName=`360 Spider`,t.appVersion=e.value,t.deviceBrand=`360`,t.deviceType=`bot`,t.platform=`other`},o=(e,t)=>{t.appName=`BingBot`,t.appVersion=e.value,t.deviceBrand=`Microsoft`,t.deviceType=`bot`,t.platform=`other`},s=(e,t)=>{t.appName=`Googlebot`,t.appVersion=e.value,t.deviceBrand=`Google`,t.deviceType=`bot`,t.platform=`other`},c=(e,t)=>{t.appName=`YandexBot`,t.appVersion=e.value,t.deviceBrand=`Yandex`,t.deviceType=`bot`,t.platform=`other`},l=(e,t)=>{e.getPreviousNTokens(3)===`Sogou web spider`&&(t.deviceBrand=`Sogou.com`,t.appName=`SogouSpider`),t.appVersion=e.value,t.deviceType=`bot`},u=(e,t)=>{t.appName=`DataproviderBot`,t.appVersion=e.value,t.deviceBrand=`Dataprovider.com`,t.deviceType=`bot`,t.platform=`other`},d=(e,t)=>{t.appName=`AhrefsBot`,t.appVersion=e.value,t.deviceBrand=`Ahrefs`,t.deviceType=`bot`,t.platform=`other`},f=(e,t)=>{t.appName=`BitSightBot`,t.appVersion=e.value,t.deviceBrand=`Bitsight`,t.deviceType=`bot`,t.platform=`other`},p=(e,t)=>{t.appName=`oBot`,t.appVersion=e.value,t.deviceBrand=`IBM`,t.deviceType=`bot`,t.platform=`other`},m=(e,t)=>{t.appName=`Cincraw`,t.appVersion=e.value,t.deviceBrand=`CINC`,t.deviceType=`bot`,t.platform=`other`},h=(e,t)=>{t.appName=`DingTalkBot`,t.appVersion=e.value,t.deviceBrand=`Alibaba`,t.deviceType=`bot`,t.platform=`other`},g=(e,t)=>{t.appName=`YisouSpider`,t.appVersion=e.value,t.deviceBrand=`Alibaba`,t.deviceType=`bot`,t.platform=`other`},_=(e,t)=>{t.appName=`ByteSpider`,t.appVersion=e.value,t.deviceBrand=`ByteDance`,t.deviceType=`bot`,t.platform=`other`},v=(e,t)=>{t.appName=`HeadlineCrawler`,t.appVersion=e.value,t.deviceBrand=`Headline.com`,t.deviceType=`bot`,t.platform=`other`},y=(e,t)=>{t.appName=`BitDiscoveryBot`,t.appVersion=e.value,t.deviceBrand=`Tenable`,t.deviceType=`bot`,t.platform=`other`},b=(e,t)=>{e.getPreviousNTokens(4)===`Screaming Frog SEO Spider`&&(t.deviceBrand=`Screaming Frog`,t.appName=`Screaming Frog`),t.appVersion=e.value,t.deviceType=`bot`},x=(e,t)=>{t.appName=`Ai2Bot`,t.appVersion=e.value,t.deviceBrand=`Ai2`,t.deviceType=`bot`,t.platform=`other`},S=(e,t)=>{t.appName=`DianjingAdSpider`,t.appVersion=e.value,t.deviceBrand=`Dianjing`,t.deviceType=`bot`,t.platform=`other`},C=(e,t)=>{t.appName=`BaiduSpider`,t.appVersion=e.value,t.deviceBrand=`Baidu`,t.deviceType=`bot`,t.platform=`other`},w=(e,t)=>{t.appName=`360 Spider`,t.appVersion=e.value,t.deviceBrand=`360`,t.deviceType=`bot`,t.platform=`other`},ee=(e,t)=>{t.appName=`BingBot`,t.appVersion=e.value,t.deviceBrand=`Microsoft`,t.deviceType=`bot`,t.platform=`other`},T=(e,t)=>{t.appName=`Googlebot`,t.appVersion=e.value,t.deviceBrand=`Google`,t.deviceType=`bot`,t.platform=`other`},E=(e,t)=>{t.appName=`YandexBot`,t.appVersion=e.value,t.deviceBrand=`Yandex`,t.deviceType=`bot`,t.platform=`other`},D=(e,t)=>{e.getPreviousNTokens(3)===`Sogou web spider`&&(t.deviceBrand=`Sogou.com`,t.appName=`SogouSpider`),t.appVersion=e.value,t.deviceType=`bot`},te=(e,t)=>{t.appName=`DataproviderBot`,t.appVersion=e.value,t.deviceBrand=`Dataprovider.com`,t.deviceType=`bot`,t.platform=`other`},ne=(e,t)=>{t.appName=`AhrefsBot`,t.appVersion=e.value,t.deviceBrand=`Ahrefs`,t.deviceType=`bot`,t.platform=`other`},re=(e,t)=>{t.appName=`BitSightBot`,t.appVersion=e.value,t.deviceBrand=`Bitsight`,t.deviceType=`bot`,t.platform=`other`},O=(e,t)=>{t.appName=`oBot`,t.appVersion=e.value,t.deviceBrand=`IBM`,t.deviceType=`bot`,t.platform=`other`},k=(e,t)=>{t.appName=`Cincraw`,t.appVersion=e.value,t.deviceBrand=`CINC`,t.deviceType=`bot`,t.platform=`other`},ie=(e,t)=>{t.appName=`DingTalkBot`,t.appVersion=e.value,t.deviceBrand=`Alibaba`,t.deviceType=`bot`,t.platform=`other`},A=(e,t)=>{t.appName=`YisouSpider`,t.appVersion=e.value,t.deviceBrand=`Alibaba`,t.deviceType=`bot`,t.platform=`other`},ae=(e,t)=>{t.appName=`ByteSpider`,t.appVersion=e.value,t.deviceBrand=`ByteDance`,t.deviceType=`bot`,t.platform=`other`},oe=(e,t)=>{t.appName=`HeadlineCrawler`,t.appVersion=e.value,t.deviceBrand=`Headline.com`,t.deviceType=`bot`,t.platform=`other`},j=(e,t)=>{t.appName=`BitDiscoveryBot`,t.appVersion=e.value,t.deviceBrand=`Tenable`,t.deviceType=`bot`,t.platform=`other`},M=(e,t)=>{e.getPreviousNTokens(4)===`Screaming Frog SEO Spider`&&(t.deviceBrand=`Screaming Frog`,t.appName=`Screaming Frog`),t.appVersion=e.value,t.deviceType=`bot`},N=(e,t)=>{t.appName=`Ai2Bot`,t.appVersion=e.value,t.deviceBrand=`Ai2`,t.deviceType=`bot`,t.platform=`other`},se=(e,t)=>{t.appName=`DianjingAdSpider`,t.appVersion=e.value,t.deviceBrand=`Dianjing`,t.deviceType=`bot`,t.platform=`other`},P=new Map,F=new Map;P.set(`Baiduspider-render`,i),P.set(`Baiduspider+`,i),P.set(`Baiduspider-image+`,i),P.set(`360Spider`,a),P.set(`360Spider-Image`,a),P.set(`bingbot`,o),P.set(`Googlebot`,s),P.set(`YandexRenderResourcesBot`,c),P.set(`spider`,l),P.set(`Dataprovider.com`,u),P.set(`AhrefsBot`,d),P.set(`BitSightBot`,f),P.set(`oBot`,p),P.set(`Cincraw`,m),P.set(`DingTalkBot-LinkService`,h),P.set(`YisouSpider`,g),P.set(`Bytespider`,_),P.set(`ev-crawler`,v),P.set(`bitdiscovery`,y),P.set(`Spider`,b),P.set(`Ai2Bot-Dolma`,x),P.set(`dianjing_ad_spider`,S),F.set(`Baiduspider-render`,C),F.set(`Baiduspider+`,C),F.set(`Baiduspider-image+`,C),F.set(`360Spider`,w),F.set(`360Spider-Image`,w),F.set(`bingbot`,ee),F.set(`Googlebot`,T),F.set(`YandexRenderResourcesBot`,E),F.set(`spider`,D),F.set(`Dataprovider.com`,te),F.set(`AhrefsBot`,ne),F.set(`BitSightBot`,re),F.set(`oBot`,O),F.set(`Cincraw`,k),F.set(`DingTalkBot-LinkService`,ie),F.set(`YisouSpider`,A),F.set(`Bytespider`,ae),F.set(`ev-crawler`,oe),F.set(`bitdiscovery`,j),F.set(`Spider`,M),F.set(`Ai2Bot-Dolma`,N),F.set(`dianjing_ad_spider`,se);let ce={productHandlerMap:P,commentHandlerMap:F,getSpecialProductHandler:()=>null,getSpecialCommentHandler:()=>null,getDefaultModelHandler:()=>null};t.isBot=function(e){let t=r.createUAInfo();return r.runTask(e,t,ce),t.deviceType===`bot`}},function(e,t){function n(e){let t=[],n={parent:e,tokens:t,get firstToken(){return t.length===0?null:t[0]},getNewToken(r){let i=(function(){let e=[],t=[],n=[],r=null,i=null,a=null,o=!0,s=!0,c=!0,l=null,u={get key(){return o&&=(r=e.join(``),!1),r},get value(){return s&&=(i=t.join(``),!1),i},get originValue(){return c&&=(a=n.join(``),!1),a},previousToken:null,properties:null,appendKey(t){e.push(t),o=!0},appendValue(e){t.push(e===`_`?`.`:e),n.push(e),s=!0,c=!0,l=null},getSplitValue(e){if(l===null){let e=u.value;l=e===``?[]:e.split(`/`)}return e>=0&&e<l.length?l[e]:null},getPreviousNTokens(e){let t=[],n=u;for(let r=0;r<e;r++){if(n==null)return null;t.unshift(n.key),n=n.previousToken}return t.join(` `)}};return u})();return t.push(i),i.previousToken=r===void 0?t.length>1?t[t.length-2]:null:r,e&&(e.properties=n),i},getLastToken:()=>t.length===0?null:t[t.length-1],getFirstToken:()=>t.length===0?null:t[0],isEmpty:()=>t.length===0};return n}function r(){return{appName:null,appVersion:null,browserName:null,browserVersion:null,engineName:null,engineVersion:null,deviceBrand:null,deviceModel:null,deviceType:`mobile`,osName:null,osVersion:null,platform:`web`,tokenGroup:n(null)}}let i=new Set(` ;,"'`.split(``)),a=new Set(`/=:`.split(``)),o=new Set([`Mozilla`,`AppleWebKit`,`Safari`,`Opera`,`Dalvik`,`com.ss.android.ugc.aweme`]);function s(e){return e.length===1&&i.has(e)}function c(e){return e.length===1&&a.has(e)}function l(e,t,n,r){if(e==null)return;let i=t.parent,a=e.key,s=null;if(i!=null){let e=i.key;o.has(e)?(s=r.commentHandlerMap.get(a)??null,s??=r.getSpecialCommentHandler(a),s==null&&a.endsWith(` Build`)&&(s=r.getDefaultModelHandler())):s=r.productHandlerMap.get(a)??r.getSpecialProductHandler(a)}else s=r.productHandlerMap.get(a)??r.getSpecialProductHandler(a);if(s!=null)try{s(e,n)}catch{}}function u(e,t,r){if(e==null)throw Error(`input can not be null`);return(function e(t,r,i,a,o){let u,d=null,f=null,p=!1,m=t.length,h=r>0?t[r-1]:`\0`;for(u=r;u<m;u++){let g=t[u];if(s(g)){let e=h!==`\0`&&s(h);if(!p&&r>0&&g===` `&&!e){let e=u+1;if(e<m){let n=t[e];/\d/.test(n)||n===`-`?p=!0:f?.appendKey(g)}else f?.appendKey(g)}else f!=null&&(d=f,f=null);h=g}else if(g===`(`){if(h===`(`){h=g;continue}let r=u;u=e(t,u+1,n(i.getLastToken()),a,o),f!=null&&(d=f,f=null),h=t[r]}else{if(g===`)`){if(r===0){h=g;continue}break}f??(l(i.getLastToken(),i,a,o),f=i.getNewToken(d),p=!1),c(g)?(p&&f.appendValue(g),p=!0):p?f.appendValue(g):f.appendKey(g),h=g}}return l(i.getLastToken(),i,a,o),u})(e,0,t.tokenGroup,t,r),t}Object.defineProperty(t,`DEFAULT_MODEL_HANDLER_KEY`,{enumerable:!0,get:function(){return`DEFAULT_MODEL_HANDLER`}}),Object.defineProperty(t,`createUAInfo`,{enumerable:!0,get:function(){return r}}),Object.defineProperty(t,`runTask`,{enumerable:!0,get:function(){return u}})},function(e,t,n){n.r(t);var r=n(0),i=n.n(r),a=n(1),o=n.n(a);n(2);function s(){var e=arguments.length>0&&arguments[0]!==void 0?arguments[0]:20,t=arguments.length>1?arguments[1]:void 0;return t||=``,e?s(--e,`0123456789ABCDEFGHIJKLMNOPQRSTUVWXTZabcdefghiklmnopqrstuvwxyz`.charAt(Math.floor(60*Math.random()))+t):t}function c(e,t){for(var n in t)e[n]=t[n];return e}function l(e){return Object.prototype.toString.call(e)===`[object Object]`}function u(e){return typeof Promise<`u`&&e instanceof Promise}var d=Object.freeze({__aesBeforeSkip:1}),f=function(e){var t=Object.prototype.toString.call(e);if(t===`[object String]`&&e||t===`[object Number]`||t===`[object Boolean]`)return e;if(t===`[object Object]`||t===`[object Array]`)try{return JSON.stringify(e)}catch{}},p=function(e){var t={};for(var n in e){var r=e[n];r!==void 0&&(t[n]=f(r))}return t},m=function(e){var t=[];for(var n in e){var r=f(e[n]);r!==void 0&&t.push(`${n}=${encodeURIComponent(r)}`)}return t.join(`&`)};function h(e){return(e.requiredFields||[]).concat([`pid`]).some(function(t){return e[t]===void 0})}function g(){var e=arguments.length>0&&arguments[0]!==void 0?arguments[0]:``,t=arguments.length>1?arguments[1]:void 0;typeof console<`u`&&console.warn(`日志解析报错,埋点将被丢弃 => ${e}`,t)}var _=`AEM_TRACKER_UNIQUE_PVID`,v=typeof globalThis<`u`&&globalThis?globalThis:typeof window<`u`&&window?window:typeof global<`u`&&global?global:typeof self<`u`&&self?self:(console.error(`Unable to locate global object in current environment`),{});function y(e){this._queue=[],this._reqQueue=[],this._plugins={},this._subscribers={onConfigUpdated:[]},this._timeout=0,this._config={sdk_version:`3.3.18`,set pv_id(e){v[_]=e},get pv_id(){return v[_]||(v[_]=s()),v[_]},timezone_offset:new Date().getTimezoneOffset()},e&&(this._config=c(this._config,e))}y.prototype={constructor:y,_sendAll:function(){if(this._timeout&&=(clearTimeout(this._timeout),0),this._queue.length){var e,t=this._config.maxUrlLength||3e4,n=this._getSendConfig();try{e=this._processData(this._queue,n)}catch{}if(e&&e.length<t)return this._queue=[],void this.send(e);for(var r,i=[];this._queue.length;){i.push(this._queue.shift());try{r=this._processData(i,n)}catch(e){var a=i.pop();g(e.message,a);continue}if(r.length>t){i.length>1&&(this._queue.unshift(i.pop()),r=this._processData(i,n));break}}r&&this.send(r),this._queue.length&&this._sendAll()}},_send:function(e,t){var n=this;if(!1===t){var r;try{r=this._processData([e])}catch(t){g(t.message,e)}r&&this.send(r)}else{this._queue.push(e);var i=this._config.mergeRequestInterval||500;this._timeout||=setTimeout(function(){n._sendAll()},i)}},_getSendConfig:function(){var e={},t=this._config;for(var n in t)n!==`requiredFields`&&n!==`maxUrlLength`&&n!==`queueGlobalName`&&n!==`debug`&&n!==`excludeCrawlers`&&n!==`collectClientHints`&&n.indexOf(`plugin`)!==0&&t[n]!==``&&t[n]!==null&&t[n]!==void 0&&(e[n]=f(t[n]));return e},_processData:function(e,t){t||=this._getSendConfig();var n=m(t);return n+=`&msg=`+encodeURIComponent(e.map(function(e){return m(e)}).join(`|`))},setConfig:function(e,t){var n=this,r={};t===void 0?r=e:r[e]=t;var i=!(function e(t,n){if(t===void 0||n===void 0||!l(t)||!l(n))return!1;for(var r in t)if(l(t[r])){if(!e(t[r],n[r]))return!1}else if(t[r]!==n[r])return!1;return!0})(r,this._config),a=function(){if(i){for(var e in r)l(r[e])?n._config[e]=c(n._config[e]||{},r[e]):n._config[e]=r[e];n._execSubscribe(`onConfigUpdated`,[r,n._config])}};this._reqQueue.length?(a(),h(this._config)||(this._reqQueue.forEach(function(e){n._send.apply(n,e)}),this._reqQueue=[])):(i&&this._sendAll(),a())},getConfig:function(e){return e?this._config[e]:this._config},updatePVID:(function(e,t){if(typeof e!=`function`)throw TypeError(`Expected a function`);t=typeof t==`number`&&t>=0?t:100;var n=null;return function(){if(n===null){var r=this,i=Array.prototype.slice.call(arguments);n=setTimeout(function(){n=null},t),e.apply(r,i)}}})(function(){v[_]=s()},200),log:function(e){var t=arguments.length>1&&arguments[1]!==void 0?arguments[1]:{},n=arguments.length>2&&arguments[2]!==void 0?arguments[2]:{};e&&(t.ts=t.ts||new Date().getTime(),t.type=e,this._print(`log`,e,t),t=p(t),h(this._config)?this._reqQueue.length<1e3&&this._reqQueue.push([t,n.combo]):this._send(t,n.combo))},before:function(e,t){var n=this;return function(){var r=arguments,i=t.apply(n,r);i!==d&&(u(i)?i.then(function(t){t!==d&&e.apply(n,t||r)}):e.apply(n,i||r))}},after:function(e,t){var n=this;return function(){var r=arguments;e.apply(n,r),t.apply(n,r)}},use:function(e,t){var n=this;return Object.prototype.toString.call(e)===`[object Array]`?e.map(function(e){if(Object.prototype.toString.call(e)===`[object Array]`){var t=e[0],r=e[1];return n._plugins[t]||(n._plugins[t]=new t(n,r))}return n._plugins[e]||(n._plugins[e]=new e(n))}):this._plugins[e]||(this._plugins[e]=new e(this,t))},_print:function(){this._config.debug&&typeof console<`u`&&console.log.apply(console,arguments)},onConfigUpdated:function(e){this._subscribers.onConfigUpdated&&this._subscribers.onConfigUpdated.push(e)},_execSubscribe:function(e,t){this._subscribers[e]&&this._subscribers[e].forEach(function(e){e.apply(this,t)})}};var b=y,x=n(3),S=n.n(x),C=n(4),w=n(5),ee=n.n(w);function T(e){return(T=typeof Symbol==`function`&&typeof Symbol.iterator==`symbol`?function(e){return typeof e}:function(e){return e&&typeof Symbol==`function`&&e.constructor===Symbol&&e!==Symbol.prototype?`symbol`:typeof e})(e)}function E(e,t){var n=Object.keys(e);if(Object.getOwnPropertySymbols){var r=Object.getOwnPropertySymbols(e);t&&(r=r.filter(function(t){return Object.getOwnPropertyDescriptor(e,t).enumerable})),n.push.apply(n,r)}return n}function D(e){for(var t=1;t<arguments.length;t++){var n=arguments[t]==null?{}:arguments[t];t%2?E(Object(n),!0).forEach(function(t){te(e,t,n[t])}):Object.getOwnPropertyDescriptors?Object.defineProperties(e,Object.getOwnPropertyDescriptors(n)):E(Object(n)).forEach(function(t){Object.defineProperty(e,t,Object.getOwnPropertyDescriptor(n,t))})}return e}function te(e,t,n){return(t=(function(e){var t=(function(e,t){if(T(e)!=`object`||!e)return e;var n=e[Symbol.toPrimitive];if(n!==void 0){var r=n.call(e,t||`default`);if(T(r)!=`object`)return r;throw TypeError(`@@toPrimitive must return a primitive value.`)}return(t===`string`?String:Number)(e)})(e,`string`);return T(t)==`symbol`?t:t+``})(t))in e?Object.defineProperty(e,t,{value:n,enumerable:!0,configurable:!0,writable:!0}):e[t]=n,e}function ne(e,t){var n=typeof Symbol<`u`&&e[Symbol.iterator]||e[`@@iterator`];if(!n){if(Array.isArray(e)||(n=O(e))||t&&e&&typeof e.length==`number`){n&&(e=n);var r=0,i=function(){};return{s:i,n:function(){return r>=e.length?{done:!0}:{done:!1,value:e[r++]}},e:function(e){throw e},f:i}}throw TypeError(`Invalid attempt to iterate non-iterable instance.
10
+ In order to be iterable, non-array objects must have a [Symbol.iterator]() method.`)}var a,o=!0,s=!1;return{s:function(){n=n.call(e)},n:function(){var e=n.next();return o=e.done,e},e:function(e){s=!0,a=e},f:function(){try{o||n.return==null||n.return()}finally{if(s)throw a}}}}function re(e,t){return(function(e){if(Array.isArray(e))return e})(e)||(function(e,t){var n=e==null?null:typeof Symbol<`u`&&e[Symbol.iterator]||e[`@@iterator`];if(n!=null){var r,i,a,o,s=[],c=!0,l=!1;try{if(a=(n=n.call(e)).next,t===0){if(Object(n)!==n)return;c=!1}else for(;!(c=(r=a.call(n)).done)&&(s.push(r.value),s.length!==t);c=!0);}catch(e){l=!0,i=e}finally{try{if(!c&&n.return!=null&&(o=n.return(),Object(o)!==o))return}finally{if(l)throw i}}return s}})(e,t)||O(e,t)||(function(){throw TypeError(`Invalid attempt to destructure non-iterable instance.
11
+ In order to be iterable, non-array objects must have a [Symbol.iterator]() method.`)})()}function O(e,t){if(e){if(typeof e==`string`)return k(e,t);var n={}.toString.call(e).slice(8,-1);return n===`Object`&&e.constructor&&(n=e.constructor.name),n===`Map`||n===`Set`?Array.from(e):n===`Arguments`||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)?k(e,t):void 0}}function k(e,t){(t==null||t>e.length)&&(t=e.length);for(var n=0,r=Array(t);n<t;n++)r[n]=e[n];return r}function ie(){for(var e=/(?:[0]{1,2}[:-]){5}[0]{1,2}/,t=i.a.networkInterfaces(),n=0,r=Object.entries(t);n<r.length;n++){var a=re(r[n],2),o=(a[0],a[1]);if(o){var s,c=ne(o);try{for(c.s();!(s=c.n()).done;){var l=s.value;if(!1===e.test(l.mac))return l.mac}}catch(e){c.e(e)}finally{c.f()}}}return`00:00:00:00:00:00`}var A,ae,oe=(A=process.version,{os:i.a.type(),os_version:i.a.release(),app_name:`node`,app_version:A,device_id:ee.a.createHash(`md5`).update(ie()).digest(`hex`),platform:`node`}),j=(0,C.promisify)(S.a.resolve);function M(e){this._offlineQueue=[],e.endpoint=e.endpoint||`gm.mmstat.com`,b.call(this,D(D({},oe),e)),this._config.endpoint_url=`https://${this._config.endpoint}/aes.1.1`}M.prototype=((ae=function(){}).prototype=b.prototype,new ae),M.prototype.constructor=M,M.prototype.send=function(e){var t,n=this;return(t=this._config.endpoint,j(t)).then(function(t){return n._offlineQueue.forEach(function(e){n.send(e)}),n._offlineQueue=[],n._print(`send`,e),o()(n._config.endpoint_url,{method:`POST`,keepalive:!0,body:JSON.stringify({gokey:encodeURIComponent(e),gmkey:`EXP`})}).catch(function(){})}).catch(function(t){n._offlineQueue.length>500&&n._offlineQueue.shift(),n._offlineQueue.push(e)})},t.default=M}]).default})),Gn=A(((e,t)=>{t.exports=(function(e){var t={};function n(r){if(t[r])return t[r].exports;var i=t[r]={i:r,l:!1,exports:{}};return e[r].call(i.exports,i,i.exports,n),i.l=!0,i.exports}return n.m=e,n.c=t,n.d=function(e,t,r){n.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:r})},n.r=function(e){typeof Symbol<`u`&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:`Module`}),Object.defineProperty(e,`__esModule`,{value:!0})},n.t=function(e,t){if(1&t&&(e=n(e)),8&t||4&t&&typeof e==`object`&&e&&e.__esModule)return e;var r=Object.create(null);if(n.r(r),Object.defineProperty(r,`default`,{enumerable:!0,value:e}),2&t&&typeof e!=`string`)for(var i in e)n.d(r,i,function(t){return e[t]}.bind(null,i));return r},n.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return n.d(t,`a`,t),t},n.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},n.p=``,n(n.s=0)})([function(e,t,n){n.r(t);var r=[`ec`,`ea`,`el`,`et`],i=function(e,t){var n=function(e){var n=e.ec,r=e.ea,i=e.el,a=e.et,o=a===void 0?`CLK`:a,s=e.xpath;delete e.ec,delete e.ea,delete e.el,delete e.et,delete e.xpath,e.p1=n,e.p2=r,e.p3=i,e.p4=o,e.p5=s;try{t.log(`event`,e)}catch{}};return function(){var t=arguments,i={};if(t.length!==0){for(var a=0;a<t.length;a++){var o,s,c=t[a];if(a!==0&&typeof c==`object`&&a!==t.length-1)return void(e==null||(o=e.console)==null||(s=o.warn)==null||s.call(o,`Only the last argument can be object type`));if(typeof c==`string`||typeof c==`number`)i[r[a]]=c;else if(typeof c==`object`&&a===t.length-1)for(var l in c)c.hasOwnProperty(l)&&(i[l]=c[l])}n(i)}else{var u,d;(u=e.console)==null||(d=u.warn)==null||d.call(u,`At lease one augument`)}}};t.default=function(e,t){return i(global,e)}}]).default})),Kn=oe(Wn(),1),qn=oe(Gn(),1);const Jn=()=>p(I(),`telemetry.jsonl`);let Yn;const K=new Set;let q;try{let e=new Kn.default({pid:`bailian-cli-node`,env:Un()}),t=e.send.bind(e);e.send=function(e){let n=t(e);if(n&&typeof n.then==`function`){let e=n;K.add(e),e.finally(()=>K.delete(e))}return n},q=e,Yn=e.use(qn.default)}catch{}async function Xn(e=1e3){try{if(q)try{typeof q._sendAll==`function`&&q._sendAll()}catch{}if(K.size===0)return;let t=[...K].map(e=>e.catch(()=>void 0));await Promise.race([Promise.allSettled(t),new Promise(t=>setTimeout(t,e).unref?.())])}catch{}}async function Zn(e){try{await he();let n=Jn();try{s(n).size>5242880&&c(n)}catch{}t(n,JSON.stringify(e)+`
12
+ `,{mode:384})}catch{}}async function Qn(e){try{if(!Yn)return;Yn(e.command,Hn(e))}catch{}}const $n=new Set([`apiKey`,`baseUrl`,`output`,`quiet`,`verbose`,`timeout`,`noColor`,`yes`,`dryRun`,`help`,`nonInteractive`,`async`,`console`]),er=new Set(`page.pageSize.n.count.model.voice.language.provider.capability.temperature.topP.topK.maxTokens.seed.stream.size.resolution.ratio.duration.format.audioFormat.sampleRate.pitch.rate.volume.api.mode.download.noWait.textOnly.promptExtend.enableSsml.watermark.hasThoughts.listTools.rerank.rerankTopN.diarization`.split(`.`));function tr(e){let t={};for(let[n,r]of Object.entries(e))n.startsWith(`_`)||$n.has(n)||er.has(n)&&(r===void 0||r===!1||(t[n]=r));return t}async function nr(e,t,n,r){if(!e.telemetry){await r();return}let i=performance.now(),a=!0,o,s,c;try{await r()}catch(e){throw a=!1,e instanceof N?(o=e.message,s=e.api?.httpStatus,c=e.api?.requestId):e instanceof Error&&(o=e.message),e}finally{let r=Math.round(performance.now()-i),l;e.apiKey||e.fileApiKey?l=`api-key`:(e.accessTokenEnv||e.fileAccessToken)&&(l=`access-token`);let u=Bn({command:t.join(` `),durationMs:r,success:a,error:a?void 0:{message:o,httpStatus:s,requestId:c},cliVersion:e.clientVersion??`unknown`,authMethod:l,params:tr(n)});Zn(u).catch(()=>{}),Qn(u).catch(()=>{})}}function rr(e){if(!e.model)return null;let t=e.inferenceMetadata;return{model:e.model,name:e.name??e.model,description:e.description??e.shortDescription??``,shortDescription:e.shortDescription,provider:e.provider??``,capabilities:e.capabilities??[],features:e.features??[],category:e.category,contextWindow:e.contextWindow??void 0,maxOutputTokens:e.maxOutputTokens??void 0,maxInputTokens:e.maxInputTokens??void 0,docUrl:e.docUrl,collectionTag:e.collectionTag,inferenceMetadata:t,prices:e.prices,qpmInfo:e.qpmInfo,versionTag:e.versionTag,openSource:e.openSource}}var ir=class{name=`api`;constructor(e){this.config=e}available(){return!0}async load(){let e=await V(this.config,``,{pageNo:1,pageSize:50}),t=[...e.models],n=Math.ceil(e.total/50);for(let e=2;e<=n;e++){let n=await V(this.config,``,{pageNo:e,pageSize:50});t.push(...n.models)}return t.map(rr).filter(e=>e!==null)}};const ar=`models.jsonl`;function or(){return E(I(),`skills/bailian-docs-llm-wiki`)}function sr(){return E(or(),ar)}function cr(){return E(T(D(import.meta.url)),`../../../../../skills/bailian-docs-llm-wiki/models`)}function lr(e){return!e.model||typeof e.model!=`string`?null:{model:e.model,name:e.name??e.model,description:e.description??``,provider:e.provider??``,capabilities:e.capabilities??[],features:e.features??[],contextWindow:e.contextWindow,maxOutputTokens:e.maxOutputTokens,docUrl:e.docUrl,inferenceMetadata:e.inferenceMetadata,shortDescription:e.shortDescription,category:e.category,collectionTag:e.collectionTag,maxInputTokens:e.maxInputTokens,prices:e.prices,qpmInfo:e.qpmInfo,versionTag:e.versionTag,openSource:e.openSource,family:e.family,familyName:e.familyName}}function ur(e){let t=C(e,`utf-8`).split(`
13
+ `).filter(Boolean),n=[];for(let e of t)try{let t=lr(JSON.parse(e));t&&n.push(t)}catch{}return n}function dr(){let e=cr();if(!x(E(e,ar)))return!1;let t=or();try{return S(t,{recursive:!0}),b(e,t,{recursive:!0}),!0}catch{return!1}}var fr=class{name=`catalog`;options;constructor(e){this.options=e??{}}available(){return x(sr())}async load(){return!this.available()&&(this.options.onPrepareStart?.(),!dr())?[]:ur(sr())}};async function pr(e,t){let n=[new fr({onPrepareStart:t?.onPrepareStart}),new ir(e)];for(let e of n)if(e.available()){let t=await e.load();if(t.length>0)return t}let r=await n[0].load();if(r.length>0)return r;throw new N(`No model data available.`,M.GENERAL)}const mr={Text:`Text`,Image:`Image`,Video:`Video`,Audio:`Audio`},J={Single:`single`,Pipeline:`pipeline`},hr={Low:`low`,Medium:`medium`,High:`high`},gr={Standard:`standard`,Large:`large`,ExtraLarge:`extra-large`},Y={Flagship:`flagship`,Balanced:`balanced`,CostOptimized:`cost-optimized`},X={TG:`TG`,Reasoning:`Reasoning`,VU:`VU`,IG:`IG`,VG:`VG`,TTS:`TTS`,ASR:`ASR`,RealtimeASR:`Realtime-ASR`,RealtimeTTS:`Realtime-Text-to-Speech`,RealtimeAudioTranslate:`Realtime-Audio-Translate`,RealtimeOmni:`Realtime-Omni`,MultimodalOmni:`Multimodal-Omni`,ME:`ME`,TR:`TR`,ThreeDGeneration:`3D-generation`},_r={FunctionCalling:`function-calling`,WebSearch:`web-search`,StructuredOutputs:`structured-outputs`,PrefixCompletion:`prefix-completion`},vr={Flagship:`Flagship`,CostOptimized:`Cost-optimized`},yr=`You are a model recommendation advisor for Alibaba Cloud Model Studio. From the candidate models below, select the best recommendations.
2464
14
 
2465
15
  CRITICAL: You MUST respond entirely in English. Do not use any Chinese characters anywhere in your response. Every field — reason, highlights, step, summary — must be written in English.
2466
16
 
@@ -2501,8 +51,7 @@ Single task:
2501
51
  {"type":"single","recommendations":[{"model":"model ID","reason":"recommendation reason","highlights":["key highlights"]}]}
2502
52
 
2503
53
  Pipeline (only when confident multi-model is needed):
2504
- {"type":"pipeline","summary":"one-line solution description","steps":[{"step":"step description","recommendations":[{"model":"model ID","reason":"reason for choosing","highlights":["highlights"]}]}]}`;
2505
- const PIPELINE_SYSTEM_PROMPT = `You are a model recommendation advisor for Alibaba Cloud Model Studio. The user's need has been decomposed into multi-step pipeline. Select the best model for each step.
54
+ {"type":"pipeline","summary":"one-line solution description","steps":[{"step":"step description","recommendations":[{"model":"model ID","reason":"reason for choosing","highlights":["highlights"]}]}]}`,br=`You are a model recommendation advisor for Alibaba Cloud Model Studio. The user's need has been decomposed into multi-step pipeline. Select the best model for each step.
2506
55
 
2507
56
  CRITICAL: You MUST respond entirely in English. Do not use any Chinese characters anywhere in your response. Every field — reason, highlights, step, summary — must be written in English.
2508
57
 
@@ -2541,8 +90,55 @@ Key principles:
2541
90
 
2542
91
  Or (if single model suffices):
2543
92
  {"type":"single","recommendations":[{"model":"model ID","reason":"recommendation reason","highlights":
2544
- ["key highlights"]}]}`;
2545
- const COMPARISON_SYSTEM_PROMPT = `You are a model comparison advisor for Alibaba Cloud Model Studio. The user wants to compare specific models — analyze them against the use case.
93
+ ["key highlights"]}]}`,Z={complexity:J.Single,taskSummary:``,scenarioHints:[],inputModality:[],outputModality:[],requiredCapabilities:[X.TG],requiredFeatures:[],budget:hr.Medium,contextNeed:gr.Standard,qualityPreference:Y.Balanced,confidence:0};async function xr(e,t){let n=Ne(e.baseUrl),r={model:`qwen-flash`,messages:[{role:`system`,content:`You are an intent analyzer. Given the user's requirement, understand the scenario first, then extract structured information.
94
+
95
+ CRITICAL: You MUST respond entirely in English. Do not use any Chinese characters anywhere in your response. All text fields (taskSummary, scenarioHints) must be in English.
96
+
97
+ ## Analysis Steps
98
+ 1. Summarize the user's core need in one sentence (taskSummary) — be specific about the scenario, not generic
99
+ 2. Infer scenario hints (scenarioHints), e.g.: ["low-latency", "consumer-facing", "high-concurrency", "conversational", "offline-batch", "high-precision"]
100
+ 3. Infer budget and qualityPreference from scenario hints
101
+ - Only deviate from defaults when the user explicitly states or the scenario strongly implies
102
+ - User says "low cost", "cheap", "save money" → budget:"low"
103
+ - User says "best", "high precision", "cost no object" → qualityPreference:"flagship"
104
+ - Infer from scenario constraints only when strong: e.g. "1M requests/day customer service" → budget:"low" (high concurrency = cost-sensitive)
105
+ - Otherwise keep budget:"medium", qualityPreference:"balanced"
106
+ 4. Extract modalities, capabilities, features etc.
107
+
108
+ ## Model preference detection
109
+ Analyze whether the user mentioned specific models, model families, or vendors:
110
+ - No models/families/vendors mentioned → mode:"unconstrained", no targets
111
+ - User scoped the range (e.g. "recommend from the deepseek family", "open-source reasoning models") → mode:"scoped", targets:["deepseek"]
112
+ - User wants to compare specific models (e.g. "compare wan2.6 and wan2.7", "is qwen-max good for legal analysis") → mode:"comparison", targets:["wan2.6","wan2.7"]
113
+ - Single model evaluation is also comparison with one target
114
+ - User wants alternatives to a reference model (e.g. "something like qwen-max but cheaper") → mode:"alternative", targets:["qwen-max"]
115
+ - User explicitly excludes certain models/families (e.g. "good models besides qwen") → excludes:["qwen"], mode determined by other signals
116
+ - targets should capture the model/family names as the user wrote them
117
+
118
+ ## Output fields
119
+ - taskSummary: one-sentence scenario understanding (must be specific, never generic like "user wants AI")
120
+ - scenarioHints: array of inferred scenario features
121
+ - complexity: "single" or "pipeline"
122
+ - segments: only for pipeline, each with step/inputModality/outputModality/requiredCapabilities
123
+ - step must describe the specific problem this step solves in the user's task, no numbered or generic modal labels
124
+ - segments must form a modality chain: each step's inputModality should cover the previous step's outputModality
125
+ - inputModality: user input modalities ["Text","Image","Video","Audio"]
126
+ - outputModality: expected output modalities
127
+ - requiredCapabilities: capability codes (use strictly from the list, don't invent):
128
+ TG=Text Generation, Reasoning=Reasoning, VU=Vision Understanding, IG=Image Generation, VG=Video Generation,
129
+ TTS=Text-to-Speech, ASR=Speech-to-Text, Realtime-ASR=Realtime Speech-to-Text,
130
+ Realtime-Text-to-Speech=Realtime Text-to-Speech, Realtime-Audio-Translate=Realtime Audio Translation,
131
+ Realtime-Omni=Realtime Omni-modal, Multimodal-Omni=Multimodal Omni, ME=Multimodal Embedding,
132
+ TR=Translation, 3D-generation=3D Generation
133
+ - requiredFeatures: required features (function-calling, web-search, structured-outputs, prefix-completion)
134
+ - budget: "low"/"medium"/"high"
135
+ - contextNeed: "standard"/"large"/"extra-large"
136
+ - qualityPreference: "flagship"/"balanced"/"cost-optimized"
137
+ - modelPreference: { mode, targets?, excludes? }
138
+
139
+ Output only JSON, no other text.`},{role:`user`,content:t}],max_tokens:1024,temperature:0};try{let t=((await B(e,{url:n,method:`POST`,body:r,timeout:5e3})).choices?.[0]?.message?.content??``).match(/\{[\s\S]*\}/);if(!t)return Z;let i=JSON.parse(t[0]),a=[`scoped`,`comparison`,`alternative`],o=i.modelPreference,s=o&&typeof o==`object`?{mode:a.includes(o.mode)?o.mode:`unconstrained`,targets:Array.isArray(o.targets)?o.targets:void 0,excludes:Array.isArray(o.excludes)?o.excludes:void 0}:void 0;return{complexity:i.complexity===J.Pipeline?J.Pipeline:J.Single,taskSummary:typeof i.taskSummary==`string`?i.taskSummary:``,scenarioHints:Array.isArray(i.scenarioHints)?i.scenarioHints:[],segments:Array.isArray(i.segments)?i.segments.map(e=>({step:e.step??``,inputModality:Array.isArray(e.inputModality)?e.inputModality:[],outputModality:Array.isArray(e.outputModality)?e.outputModality:[],requiredCapabilities:Array.isArray(e.requiredCapabilities)?e.requiredCapabilities:[]})):void 0,inputModality:Array.isArray(i.inputModality)?i.inputModality:[],outputModality:Array.isArray(i.outputModality)?i.outputModality:[],requiredCapabilities:Array.isArray(i.requiredCapabilities)?i.requiredCapabilities:[],requiredFeatures:Array.isArray(i.requiredFeatures)?i.requiredFeatures:[],budget:i.budget??Z.budget,contextNeed:i.contextNeed??Z.contextNeed,qualityPreference:i.qualityPreference??Z.qualityPreference,confidence:1,modelPreference:s}}catch{return Z}}const Sr=/-\d{4}-\d{2}-\d{2}$/,Cr=new Set([X.IG,X.VG,X.TTS,X.RealtimeTTS,X.ThreeDGeneration]),wr=new Set([X.TG,X.Reasoning,X.ASR,X.RealtimeASR,X.RealtimeAudioTranslate,X.TR,X.ME]),Tr={standard:0,large:32e3,"extra-large":128e3};function Er(e){let t=!1,n=!1;for(let r of e)Cr.has(r)&&(t=!0),wr.has(r)&&(n=!0);return t&&n}function Dr(e){let t=new Set(e.map(({model:e})=>e));return e.filter(({model:e})=>{let n=e.replace(Sr,``);return n===e?!0:!t.has(n)})}function Or(e,t,n){let r=e.inferenceMetadata?.request_modality??[],i=e.inferenceMetadata?.response_modality??[];return!(t.length>0&&!t.some(e=>r.includes(e))||n.length>0&&!n.some(e=>i.includes(e)))}function kr(e,t){if(t.length===0)return!0;let n=e.inferenceMetadata?.request_modality??[];return t.some(e=>n.includes(e))}function Ar(e,t){let{requiredCapabilities:n,requiredFeatures:r,contextNeed:i,qualityPreference:a}=t,{capabilities:o,features:s,contextWindow:c,category:l}=e,u=0;for(let e of n)o.includes(e)&&(u+=10);for(let e of r)s.includes(e)&&(u+=5);let d=Tr[i];return d>0&&(c??0)>=d&&(u+=8),a===Y.Flagship&&l===vr.Flagship||a===Y.CostOptimized&&l===vr.CostOptimized?u+=15:a===Y.Balanced&&l===vr.Flagship&&(u+=5),u}function Q(e,t,n){return e.map(e=>({model:e,score:Ar(e,t)})).sort((e,t)=>t.score-e.score).slice(0,n)}function jr(e){return new Set(e.map(({model:e})=>e.model))}function Mr(e,t){let n=new Map,r=[],i=[];for(let a of e){let e=a.model.family;if(!e){r.push(a);continue}let o=n.get(e)??0;o<t?(r.push(a),n.set(e,o+1)):i.push(a)}return r.length>=10?r:[...r,...i.slice(0,10-r.length)]}function Nr(e,t){let n=new Set(t);return e.filter(e=>n.has(e.model.model)?!1:(n.add(e.model.model),!0))}function Pr(e,t,n){return n.size>=10?[]:Q(e.filter(({model:e})=>!n.has(e)),t,10-n.size)}function Fr(e,t,n,r,i){let{inputModality:a,outputModality:o,requiredCapabilities:s}=t,c={complexity:J.Single,taskSummary:``,scenarioHints:[],inputModality:a,outputModality:o,requiredCapabilities:s,requiredFeatures:[],budget:r,contextNeed:gr.Standard,qualityPreference:i,confidence:1},l=e.filter(e=>Or(e,a,o)&&kr(e,n));return l.length<5&&(l=e.filter(e=>Or(e,a,o))),l.length<5&&(l=e),Q(l,c,5)}function Ir(e,t){e=Dr(e);let n;if(t.complexity===J.Pipeline&&t.segments?.length){let r=[];for(let[n,i]of t.segments.entries()){let a=n===0?[]:t.segments[n-1].outputModality,o=Nr(Fr(e,i,a,t.budget,t.qualityPreference),jr(r));r=[...r,...o]}let i=Pr(e,t,jr(r));n=[...r,...i]}else if(Er(t.requiredCapabilities))n=Lr(e,t);else{let r=e.filter(e=>Or(e,t.inputModality,t.outputModality));r.length<5&&(r=e),n=Q(r,t,50)}return Mr(n,3)}function Lr(e,t){let n=t.requiredCapabilities.filter(e=>Cr.has(e)),r=t.requiredCapabilities.filter(e=>wr.has(e)),i=[];if(n.length>0&&(i=Q(e.filter(e=>n.some(t=>e.capabilities.includes(t))),t,25)),r.length>0){let n=jr(i),a={...t,requiredCapabilities:r},o=e.filter(e=>!n.has(e.model)&&r.some(t=>e.capabilities.includes(t)));i=[...i,...Q(o,a,25)]}let a=Pr(e,t,jr(i));return[...i,...a]}const Rr=`text-embedding-v4`;function zr(){return E(I(),`skills/bailian-docs-llm-wiki`)}function Br(){return E(zr(),`models-embeddings.json`)}function Vr(){let e=Br();if(!x(e))return null;try{return JSON.parse(C(e,`utf-8`)).items}catch{return null}}async function Hr(e,t){return(await B(e,{url:`${e.baseUrl}/compatible-mode/v1/embeddings`,method:`POST`,body:{model:Rr,input:[t],dimensions:512,encoding_format:`float`},timeout:1e4})).data[0].embedding}async function Ur(e,t){return(await B(e,{url:`${e.baseUrl}/compatible-mode/v1/embeddings`,method:`POST`,body:{model:Rr,input:t,dimensions:512,encoding_format:`float`},timeout:3e4})).data.sort((e,t)=>e.index-t.index).map(e=>e.embedding)}const Wr={TG:`Text Generation`,Reasoning:`Reasoning`,VU:`Vision Understanding`,IG:`Image Generation`,VG:`Video Generation`,TTS:`Text-to-Speech`,ASR:`Speech-to-Text`},Gr={Text:`Text`,Image:`Image`,Video:`Video`,Audio:`Audio`};function Kr(){let e=E(zr(),`groups`),t=new Map;if(!x(e))return t;for(let n of w(e).filter(e=>e.endsWith(`.json`)))try{let r=JSON.parse(C(E(e,n),`utf-8`)),i=r.description??``;if(r.items)for(let e of r.items)t.set(e.model,e.description||i)}catch{}return t}function qr(e,t){let n=(e.capabilities??[]).map(e=>Wr[e]??e).join(`, `),r=t.get(e.model)||e.shortDescription||e.description||``,i=(e.inferenceMetadata?.request_modality??[]).map(e=>Gr[e]??e).join(`, `),a=(e.inferenceMetadata?.response_modality??[]).map(e=>Gr[e]??e).join(`, `);return[e.name,e.model,r,n?`Capabilities: ${n}`:``,i?`Input: ${i}`:``,a?`Output: ${a}`:``,e.features?.length?`Features: ${e.features.join(`, `)}`:``,e.familyName||``,e.category?`Category: ${e.category}`:``].filter(Boolean).join(` | `)}async function Jr(e,t){let n=Kr(),r=t.map(e=>qr(e,n)),i=[];for(let t=0;t<r.length;t+=10){let n=await Ur(e,r.slice(t,t+10));i.push(...n)}let a=t.map((e,t)=>({id:e.model,vector:i[t]})),o={model:Rr,dimensions:512,count:a.length,items:a},s=Br();return S(T(s),{recursive:!0}),ee(s,JSON.stringify(o)),a}function Yr(e,t){let n=0,r=0,i=0;for(let a=0;a<e.length;a++)n+=e[a]*t[a],r+=e[a]*e[a],i+=t[a]*t[a];let a=Math.sqrt(r)*Math.sqrt(i);return a===0?0:n/a}let Xr=null;function Zr(){return Xr===null&&(Xr=Vr()),Xr}function Qr(){return Zr()!==null}function $r(e,t){let n=t.toLowerCase();return[e.model,e.name,e.family,e.familyName,e.provider].some(e=>e?.toLowerCase().includes(n))}function ei(e,t){return t.some(t=>$r(e,t))}function ti(e,t){return t.length===0?e:e.filter(({model:e})=>!ei(e,t))}function ni(e,t){let n=e.inferenceMetadata?.request_modality??[],r=e.inferenceMetadata?.response_modality??[],i=t.inputModality.length===0||t.inputModality.some(e=>n.includes(e)),a=t.outputModality.length===0||t.outputModality.some(e=>r.includes(e));return!i||!a?!1:t.requiredCapabilities.length===0?!0:t.requiredCapabilities.some(t=>e.capabilities.includes(t))}function $(e,t,n,r){return e.filter(e=>n.has(e.id)).map(e=>({id:e.id,similarity:Yr(t,e.vector)})).sort((e,t)=>t.similarity-e.similarity).slice(0,r)}function ri(e,t,n,r,i){let a=r.targets??[],o=a.length>0?e.filter(e=>ei(e,a)):e,s=o.length>=5?o:e,c=$(t,n,new Set(s.map(e=>e.model)),i),l=new Map(e.map(e=>[e.model,e])),u=[];if(o.length<5&&a.length>0){for(let e of o)u.push({model:e,score:1});let e=new Set(u.map(({model:e})=>e.model));for(let{id:t,similarity:n}of c){if(e.has(t))continue;let r=l.get(t);if(r&&u.push({model:r,score:n}),u.length>=i)break}return u}for(let{id:e,similarity:t}of c){let n=l.get(e);n&&u.push({model:n,score:t})}return u}function ii(e,t,n,r,i){let a=r.targets??[],o=new Map(e.map(e=>[e.model,e])),s=[],c=new Set;for(let t of e)ei(t,a)&&!c.has(t.model)&&(s.push({model:t,score:1}),c.add(t.model));let l=i-s.length;if(l>0){let r=$(t,n,new Set(e.filter(e=>!c.has(e.model)).map(e=>e.model)),l);for(let{id:e,similarity:t}of r){let n=o.get(e);n&&s.push({model:n,score:t})}}return s}function ai(e,t,n,r,i){let a=r.targets??[],o=new Map(e.map(e=>[e.model,e])),s=e.filter(e=>ei(e,a)),c=new Set(s.map(e=>e.family).filter(Boolean)),l=[],u=new Set;for(let e of s)l.push({model:e,score:1}),u.add(e.model);let d=e.filter(e=>!u.has(e.model)&&(!e.family||!c.has(e.family))),f=$(t,n,new Set(d.map(e=>e.model)),i-l.length);for(let{id:e,similarity:t}of f){let n=o.get(e);n&&l.push({model:n,score:t})}return l}async function oi(e,t,n,r,i){let a=Zr();a||(a=await Jr(e,t),Xr=a);let o=await Hr(e,n),s=new Map(t.map(e=>[e.model,e])),c=i?.modelPreference,l=c?.excludes??[];if(c&&c.mode!==`unconstrained`){let e;switch(c.mode){case`scoped`:e=ri(t,a,o,c,r);break;case`comparison`:e=ii(t,a,o,c,r);break;case`alternative`:e=ai(t,a,o,c,r);break;default:e=[]}return ti(e,l)}if(i?.complexity===J.Pipeline&&i.segments?.length){let e=new Set,n=[],c=Math.max(5,Math.ceil(r/i.segments.length));for(let r of i.segments){let i=t.filter(e=>ni(e,r)),l=new Set(i.filter(t=>!e.has(t.model)).map(e=>e.model));if(l.size===0)continue;let u=$(a,o,l,c);for(let{id:t,similarity:r}of u){let i=s.get(t);i&&!e.has(t)&&(n.push({model:i,score:r}),e.add(t))}}return ti(n,l)}let u=new Set(t.map(e=>e.model)),d=$(a,o,u,r),f=[];for(let{id:e,similarity:t}of d){let n=s.get(e);n&&f.push({model:n,score:t})}return ti(f,l)}function si(e){if(e.prices?.length)return e.prices.map(e=>`${e.type}:${e.price}/${e.unit}`).join(`, `)}function ci(e){if(!e.qpmInfo)return;let t=Object.entries(e.qpmInfo);if(t.length!==0)return t.map(([e,t])=>`${e}:${t.count_limit}/${t.count_limit_period}s`).join(`, `)}function li(e){return e.map(({model:e})=>{let t=[`ID: ${e.model}`,`Name: ${e.name}`,`Description: ${e.shortDescription||e.description}`,`Capabilities: ${e.capabilities.join(`, `)}`,`Features: ${e.features.join(`, `)}`];e.contextWindow&&t.push(`Context Window: ${e.contextWindow}`),e.maxOutputTokens&&t.push(`Max Output: ${e.maxOutputTokens}`),e.category&&t.push(`Category: ${e.category}`);let n=e.inferenceMetadata;n?.request_modality?.length&&t.push(`Input Modality: ${n.request_modality.join(`, `)}`),n?.response_modality?.length&&t.push(`Output Modality: ${n.response_modality.join(`, `)}`);let r=si(e);r&&t.push(`Pricing: ${r}`);let i=ci(e);return i&&t.push(`QPM: ${i}`),e.versionTag&&t.push(`Version: ${e.versionTag}`),e.openSource!==void 0&&t.push(`Open Source: ${e.openSource?`Yes`:`No`}`),e.family&&t.push(`Family: ${e.family}`),t.join(` | `)}).join(`
140
+ `)}function ui(e){let{taskSummary:t,scenarioHints:n,inputModality:r,outputModality:i,requiredCapabilities:a,requiredFeatures:o,budget:s,qualityPreference:c,contextNeed:l,segments:u,modelPreference:d}=e,f=[];if(t&&f.push(`Task: ${t}`),n.length&&f.push(`Scenario: ${n.join(`, `)}`),r.length&&f.push(`Input: ${r.join(`, `)}`),i.length&&f.push(`Output: ${i.join(`, `)}`),a.length&&f.push(`Capabilities: ${a.join(`, `)}`),o.length&&f.push(`Features: ${o.join(`, `)}`),f.push(`Budget: ${s}`),f.push(`Quality: ${c}`),l!==gr.Standard&&f.push(`Context: ${l}`),d&&d.mode!==`unconstrained`&&(f.push(`Mode: ${d.mode}`),d.targets?.length&&f.push(`Targets: ${d.targets.join(`, `)}`),d.excludes?.length&&f.push(`Excludes: ${d.excludes.join(`, `)}`)),u?.length){f.push(`Pipeline Steps:`);for(let e of u){let t=e.inputModality.join(`,`)||`none`,n=e.outputModality.join(`,`)||`none`,r=e.requiredCapabilities.join(`,`)||`none`;f.push(` - ${e.step} (Input: ${t} → Output: ${n}, Capabilities: ${r})`)}}return f.join(`
141
+ `)}function di(e){if(!e)return;let t=e.match(/\/(\d+)\.html/);if(t)return`https://bailian.console.aliyun.com/cn-beijing?tab=doc#/doc/?type=model&url=${t[1]}`}function fi(e,t,n){let r=Array.isArray(e)?e:[],i=[],a=new Set;for(let e of r){let r=t.get(e.model);if(!r||r.family&&a.has(r.family))continue;r.family&&a.add(r.family);let{model:o,name:s,category:c,contextWindow:l,maxOutputTokens:u,docUrl:d}=r;if(i.push({model:o,name:s,reason:e.reason??``,highlights:e.highlights??[],category:c,contextWindow:l,maxOutputTokens:u,docUrl:d}),i.length>=n)break}return i}function pi(e,t){for(let n=1;n<e.length;n++){let r=e[n-1],i=e[n],a=new Set(r.recommendations.flatMap(e=>t.get(e.model)?.inferenceMetadata?.response_modality??[]));if(a.size===0)continue;let o=[];for(let e of i.recommendations){let n=t.get(e.model)?.inferenceMetadata?.request_modality??[];!n.some(e=>a.has(e))&&n.length>0&&o.push(`${e.name}'s input modalities [${n.join(`, `)}] may not be compatible with the previous step's output modalities [${[...a].join(`, `)}]`)}o.length>0&&(i.warnings=o)}}async function mi(e,t,n,r,i,a){let o=li(t),s=ui(n),c=n.modelPreference?.mode,l;if(c===`comparison`)l=`You are a model comparison advisor for Alibaba Cloud Model Studio. The user wants to compare specific models — analyze them against the use case.
2546
142
 
2547
143
  CRITICAL: You MUST respond entirely in English. Do not use any Chinese characters anywhere in your response. Every field — reason, highlights — must be written in English.
2548
144
 
@@ -2563,8 +159,7 @@ The intent's modelPreference.targets are the models to compare.
2563
159
  - Output strict JSON
2564
160
 
2565
161
  ## Output Format
2566
- {"type":"single","recommendations":[{"model":"model ID","reason":"comparative analysis","highlights":["differentiators"]}]}`;
2567
- const ALTERNATIVE_SYSTEM_PROMPT = `You are a model alternative advisor for Alibaba Cloud Model Studio. The user has a reference model and wants to find alternatives.
162
+ {"type":"single","recommendations":[{"model":"model ID","reason":"comparative analysis","highlights":["differentiators"]}]}`;else if(c===`alternative`)l=`You are a model alternative advisor for Alibaba Cloud Model Studio. The user has a reference model and wants to find alternatives.
2568
163
 
2569
164
  CRITICAL: You MUST respond entirely in English. Do not use any Chinese characters anywhere in your response. Every field — reason, highlights — must be written in English.
2570
165
 
@@ -2585,770 +180,4 @@ The intent's modelPreference.targets is the reference model.
2585
180
  - Output strict JSON
2586
181
 
2587
182
  ## Output Format
2588
- {"type":"single","recommendations":[{"model":"model ID","reason":"alternative analysis","highlights":["differentiators"]}]}`;
2589
- //#endregion
2590
- //#region src/advisor/constants/defaults.ts
2591
- const DEFAULT_INTENT = {
2592
- complexity: Complexities.Single,
2593
- taskSummary: "",
2594
- scenarioHints: [],
2595
- inputModality: [],
2596
- outputModality: [],
2597
- requiredCapabilities: [Capabilities.TG],
2598
- requiredFeatures: [],
2599
- budget: Budgets.Medium,
2600
- contextNeed: ContextNeeds.Standard,
2601
- qualityPreference: QualityPreferences.Balanced,
2602
- confidence: 0
2603
- };
2604
- //#endregion
2605
- //#region src/advisor/intent.ts
2606
- async function analyzeIntent(config, input) {
2607
- const url = chatEndpoint(config.baseUrl);
2608
- const body = {
2609
- model: INTENT_MODEL,
2610
- messages: [{
2611
- role: "system",
2612
- content: INTENT_SYSTEM_PROMPT
2613
- }, {
2614
- role: "user",
2615
- content: input
2616
- }],
2617
- max_tokens: 1024,
2618
- temperature: 0
2619
- };
2620
- try {
2621
- const jsonMatch = ((await requestJson(config, {
2622
- url,
2623
- method: "POST",
2624
- body,
2625
- timeout: 5e3
2626
- })).choices?.[0]?.message?.content ?? "").match(/\{[\s\S]*\}/);
2627
- if (!jsonMatch) return DEFAULT_INTENT;
2628
- const parsed = JSON.parse(jsonMatch[0]);
2629
- const VALID_MODES = [
2630
- "scoped",
2631
- "comparison",
2632
- "alternative"
2633
- ];
2634
- const rawPref = parsed.modelPreference;
2635
- const modelPreference = rawPref && typeof rawPref === "object" ? {
2636
- mode: VALID_MODES.includes(rawPref.mode) ? rawPref.mode : "unconstrained",
2637
- targets: Array.isArray(rawPref.targets) ? rawPref.targets : void 0,
2638
- excludes: Array.isArray(rawPref.excludes) ? rawPref.excludes : void 0
2639
- } : void 0;
2640
- return {
2641
- complexity: parsed.complexity === Complexities.Pipeline ? Complexities.Pipeline : Complexities.Single,
2642
- taskSummary: typeof parsed.taskSummary === "string" ? parsed.taskSummary : "",
2643
- scenarioHints: Array.isArray(parsed.scenarioHints) ? parsed.scenarioHints : [],
2644
- segments: Array.isArray(parsed.segments) ? parsed.segments.map((seg) => ({
2645
- step: seg.step ?? "",
2646
- inputModality: Array.isArray(seg.inputModality) ? seg.inputModality : [],
2647
- outputModality: Array.isArray(seg.outputModality) ? seg.outputModality : [],
2648
- requiredCapabilities: Array.isArray(seg.requiredCapabilities) ? seg.requiredCapabilities : []
2649
- })) : void 0,
2650
- inputModality: Array.isArray(parsed.inputModality) ? parsed.inputModality : [],
2651
- outputModality: Array.isArray(parsed.outputModality) ? parsed.outputModality : [],
2652
- requiredCapabilities: Array.isArray(parsed.requiredCapabilities) ? parsed.requiredCapabilities : [],
2653
- requiredFeatures: Array.isArray(parsed.requiredFeatures) ? parsed.requiredFeatures : [],
2654
- budget: parsed.budget ?? DEFAULT_INTENT.budget,
2655
- contextNeed: parsed.contextNeed ?? DEFAULT_INTENT.contextNeed,
2656
- qualityPreference: parsed.qualityPreference ?? DEFAULT_INTENT.qualityPreference,
2657
- confidence: 1,
2658
- modelPreference
2659
- };
2660
- } catch {
2661
- return DEFAULT_INTENT;
2662
- }
2663
- }
2664
- //#endregion
2665
- //#region src/advisor/constants/scoring.ts
2666
- const SNAPSHOT_DATE_RE = /-\d{4}-\d{2}-\d{2}$/;
2667
- const GENERATION_CAPS = new Set([
2668
- Capabilities.IG,
2669
- Capabilities.VG,
2670
- Capabilities.TTS,
2671
- Capabilities.RealtimeTTS,
2672
- Capabilities.ThreeDGeneration
2673
- ]);
2674
- const TEXT_CAPS = new Set([
2675
- Capabilities.TG,
2676
- Capabilities.Reasoning,
2677
- Capabilities.ASR,
2678
- Capabilities.RealtimeASR,
2679
- Capabilities.RealtimeAudioTranslate,
2680
- Capabilities.TR,
2681
- Capabilities.ME
2682
- ]);
2683
- const CONTEXT_THRESHOLDS = {
2684
- standard: 0,
2685
- large: 32e3,
2686
- "extra-large": 128e3
2687
- };
2688
- //#endregion
2689
- //#region src/advisor/recall.ts
2690
- function hasMultiDomainCapabilities(caps) {
2691
- let hasGen = false;
2692
- let hasText = false;
2693
- for (const cap of caps) {
2694
- if (GENERATION_CAPS.has(cap)) hasGen = true;
2695
- if (TEXT_CAPS.has(cap)) hasText = true;
2696
- }
2697
- return hasGen && hasText;
2698
- }
2699
- function deduplicateSnapshots(models) {
2700
- const mainModels = new Set(models.map(({ model }) => model));
2701
- return models.filter(({ model }) => {
2702
- const base = model.replace(SNAPSHOT_DATE_RE, "");
2703
- if (base === model) return true;
2704
- return !mainModels.has(base);
2705
- });
2706
- }
2707
- function matchesModality(model, inputModality, outputModality) {
2708
- const modelInput = model.inferenceMetadata?.request_modality ?? [];
2709
- const modelOutput = model.inferenceMetadata?.response_modality ?? [];
2710
- if (inputModality.length > 0) {
2711
- if (!inputModality.some((mod) => modelInput.includes(mod))) return false;
2712
- }
2713
- if (outputModality.length > 0) {
2714
- if (!outputModality.some((mod) => modelOutput.includes(mod))) return false;
2715
- }
2716
- return true;
2717
- }
2718
- function matchesUpstream(model, upstreamOutput) {
2719
- if (upstreamOutput.length === 0) return true;
2720
- const accepts = model.inferenceMetadata?.request_modality ?? [];
2721
- return upstreamOutput.some((mod) => accepts.includes(mod));
2722
- }
2723
- function scoreModel(model, intent) {
2724
- const { requiredCapabilities, requiredFeatures, contextNeed, qualityPreference } = intent;
2725
- const { capabilities, features, contextWindow, category } = model;
2726
- let score = 0;
2727
- for (const cap of requiredCapabilities) if (capabilities.includes(cap)) score += 10;
2728
- for (const feat of requiredFeatures) if (features.includes(feat)) score += 5;
2729
- const ctxThreshold = CONTEXT_THRESHOLDS[contextNeed];
2730
- if (ctxThreshold > 0 && (contextWindow ?? 0) >= ctxThreshold) score += 8;
2731
- if (qualityPreference === QualityPreferences.Flagship && category === ModelCategories.Flagship) score += 15;
2732
- else if (qualityPreference === QualityPreferences.CostOptimized && category === ModelCategories.CostOptimized) score += 15;
2733
- else if (qualityPreference === QualityPreferences.Balanced) {
2734
- if (category === ModelCategories.Flagship) score += 5;
2735
- }
2736
- return score;
2737
- }
2738
- function scoreAndRank(models, intent, limit) {
2739
- return models.map((model) => ({
2740
- model,
2741
- score: scoreModel(model, intent)
2742
- })).sort((left, right) => right.score - left.score).slice(0, limit);
2743
- }
2744
- function candidateIds(candidates) {
2745
- return new Set(candidates.map(({ model }) => model.model));
2746
- }
2747
- function capByFamily(candidates, cap) {
2748
- const counts = /* @__PURE__ */ new Map();
2749
- const kept = [];
2750
- const overflow = [];
2751
- for (const candidate of candidates) {
2752
- const family = candidate.model.family;
2753
- if (!family) {
2754
- kept.push(candidate);
2755
- continue;
2756
- }
2757
- const cur = counts.get(family) ?? 0;
2758
- if (cur < cap) {
2759
- kept.push(candidate);
2760
- counts.set(family, cur + 1);
2761
- } else overflow.push(candidate);
2762
- }
2763
- if (kept.length >= 10) return kept;
2764
- return [...kept, ...overflow.slice(0, 10 - kept.length)];
2765
- }
2766
- function deduplicateCandidates(candidates, excludeIds) {
2767
- const seen = new Set(excludeIds);
2768
- return candidates.filter((candidate) => {
2769
- if (seen.has(candidate.model.model)) return false;
2770
- seen.add(candidate.model.model);
2771
- return true;
2772
- });
2773
- }
2774
- function computeRemaining(models, intent, excludeIds) {
2775
- if (excludeIds.size >= 10) return [];
2776
- return scoreAndRank(models.filter(({ model }) => !excludeIds.has(model)), intent, 10 - excludeIds.size);
2777
- }
2778
- function recallForSegment(models, segment, upstreamOutput, budget, qualityPreference) {
2779
- const { inputModality, outputModality, requiredCapabilities } = segment;
2780
- const segmentIntent = {
2781
- complexity: Complexities.Single,
2782
- taskSummary: "",
2783
- scenarioHints: [],
2784
- inputModality,
2785
- outputModality,
2786
- requiredCapabilities,
2787
- requiredFeatures: [],
2788
- budget,
2789
- contextNeed: ContextNeeds.Standard,
2790
- qualityPreference,
2791
- confidence: 1
2792
- };
2793
- let candidates = models.filter((profile) => matchesModality(profile, inputModality, outputModality) && matchesUpstream(profile, upstreamOutput));
2794
- if (candidates.length < 5) candidates = models.filter((profile) => matchesModality(profile, inputModality, outputModality));
2795
- if (candidates.length < 5) candidates = models;
2796
- return scoreAndRank(candidates, segmentIntent, 5);
2797
- }
2798
- function recallCandidates(models, intent) {
2799
- models = deduplicateSnapshots(models);
2800
- let result;
2801
- if (intent.complexity === Complexities.Pipeline && intent.segments?.length) {
2802
- let results = [];
2803
- for (const [segIdx, segment] of intent.segments.entries()) {
2804
- const upstreamOutput = segIdx === 0 ? [] : intent.segments[segIdx - 1].outputModality;
2805
- const unique = deduplicateCandidates(recallForSegment(models, segment, upstreamOutput, intent.budget, intent.qualityPreference), candidateIds(results));
2806
- results = [...results, ...unique];
2807
- }
2808
- const remaining = computeRemaining(models, intent, candidateIds(results));
2809
- result = [...results, ...remaining];
2810
- } else if (hasMultiDomainCapabilities(intent.requiredCapabilities)) result = recallCrossDomain(models, intent);
2811
- else {
2812
- let hardFiltered = models.filter((profile) => matchesModality(profile, intent.inputModality, intent.outputModality));
2813
- if (hardFiltered.length < 5) hardFiltered = models;
2814
- result = scoreAndRank(hardFiltered, intent, 50);
2815
- }
2816
- return capByFamily(result, 3);
2817
- }
2818
- function recallCrossDomain(models, intent) {
2819
- const perDomain = Math.ceil(50 / 2);
2820
- const genCaps = intent.requiredCapabilities.filter((cap) => GENERATION_CAPS.has(cap));
2821
- const textCaps = intent.requiredCapabilities.filter((cap) => TEXT_CAPS.has(cap));
2822
- let results = [];
2823
- if (genCaps.length > 0) results = scoreAndRank(models.filter((profile) => genCaps.some((cap) => profile.capabilities.includes(cap))), intent, perDomain);
2824
- if (textCaps.length > 0) {
2825
- const excludeIds = candidateIds(results);
2826
- const textIntent = {
2827
- ...intent,
2828
- requiredCapabilities: textCaps
2829
- };
2830
- const textModels = models.filter((profile) => !excludeIds.has(profile.model) && textCaps.some((cap) => profile.capabilities.includes(cap)));
2831
- results = [...results, ...scoreAndRank(textModels, textIntent, perDomain)];
2832
- }
2833
- const remaining = computeRemaining(models, intent, candidateIds(results));
2834
- return [...results, ...remaining];
2835
- }
2836
- //#endregion
2837
- //#region src/advisor/embedding.ts
2838
- const EMBEDDING_MODEL = "text-embedding-v4";
2839
- const EMBEDDINGS_FILE = "models-embeddings.json";
2840
- const BATCH_SIZE = 10;
2841
- function skillDataDir() {
2842
- return join$1(getConfigDir(), "skills/doc-llm-wiki");
2843
- }
2844
- function embeddingsPath() {
2845
- return join$1(skillDataDir(), EMBEDDINGS_FILE);
2846
- }
2847
- function loadModelEmbeddings() {
2848
- const path = embeddingsPath();
2849
- if (!existsSync$1(path)) return null;
2850
- try {
2851
- return JSON.parse(readFileSync$1(path, "utf-8")).items;
2852
- } catch {
2853
- return null;
2854
- }
2855
- }
2856
- async function embedQuery(config, text) {
2857
- return (await requestJson(config, {
2858
- url: `${config.baseUrl}/compatible-mode/v1/embeddings`,
2859
- method: "POST",
2860
- body: {
2861
- model: EMBEDDING_MODEL,
2862
- input: [text],
2863
- dimensions: 512,
2864
- encoding_format: "float"
2865
- },
2866
- timeout: 1e4
2867
- })).data[0].embedding;
2868
- }
2869
- async function embedBatch(config, texts) {
2870
- return (await requestJson(config, {
2871
- url: `${config.baseUrl}/compatible-mode/v1/embeddings`,
2872
- method: "POST",
2873
- body: {
2874
- model: EMBEDDING_MODEL,
2875
- input: texts,
2876
- dimensions: 512,
2877
- encoding_format: "float"
2878
- },
2879
- timeout: 3e4
2880
- })).data.sort((left, right) => left.index - right.index).map((item) => item.embedding);
2881
- }
2882
- const CAPABILITY_LABELS = {
2883
- TG: "Text Generation",
2884
- Reasoning: "Reasoning",
2885
- VU: "Vision Understanding",
2886
- IG: "Image Generation",
2887
- VG: "Video Generation",
2888
- TTS: "Text-to-Speech",
2889
- ASR: "Speech-to-Text"
2890
- };
2891
- const MODALITY_LABELS = {
2892
- Text: "Text",
2893
- Image: "Image",
2894
- Video: "Video",
2895
- Audio: "Audio"
2896
- };
2897
- function loadGroupDescriptions() {
2898
- const groupsDir = join$1(skillDataDir(), "groups");
2899
- const map = /* @__PURE__ */ new Map();
2900
- if (!existsSync$1(groupsDir)) return map;
2901
- for (const file of readdirSync(groupsDir).filter((name) => name.endsWith(".json"))) try {
2902
- const data = JSON.parse(readFileSync$1(join$1(groupsDir, file), "utf-8"));
2903
- const groupDesc = data.description ?? "";
2904
- if (data.items) for (const item of data.items) map.set(item.model, item.description || groupDesc);
2905
- } catch {}
2906
- return map;
2907
- }
2908
- function buildModelText(model, descriptions) {
2909
- const caps = (model.capabilities ?? []).map((cap) => CAPABILITY_LABELS[cap] ?? cap).join(", ");
2910
- const description = descriptions.get(model.model) || model.shortDescription || model.description || "";
2911
- const inputMods = (model.inferenceMetadata?.request_modality ?? []).map((mod) => MODALITY_LABELS[mod] ?? mod).join(", ");
2912
- const outputMods = (model.inferenceMetadata?.response_modality ?? []).map((mod) => MODALITY_LABELS[mod] ?? mod).join(", ");
2913
- return [
2914
- model.name,
2915
- model.model,
2916
- description,
2917
- caps ? `Capabilities: ${caps}` : "",
2918
- inputMods ? `Input: ${inputMods}` : "",
2919
- outputMods ? `Output: ${outputMods}` : "",
2920
- model.features?.length ? `Features: ${model.features.join(", ")}` : "",
2921
- model.familyName || "",
2922
- model.category ? `Category: ${model.category}` : ""
2923
- ].filter(Boolean).join(" | ");
2924
- }
2925
- async function buildAndCacheEmbeddings(config, models) {
2926
- const descriptions = loadGroupDescriptions();
2927
- const texts = models.map((profile) => buildModelText(profile, descriptions));
2928
- const allVectors = [];
2929
- for (let batchStart = 0; batchStart < texts.length; batchStart += BATCH_SIZE) {
2930
- const vectors = await embedBatch(config, texts.slice(batchStart, batchStart + BATCH_SIZE));
2931
- allVectors.push(...vectors);
2932
- }
2933
- const items = models.map((profile, idx) => ({
2934
- id: profile.model,
2935
- vector: allVectors[idx]
2936
- }));
2937
- const output = {
2938
- model: EMBEDDING_MODEL,
2939
- dimensions: 512,
2940
- count: items.length,
2941
- items
2942
- };
2943
- const outPath = embeddingsPath();
2944
- mkdirSync$1(dirname(outPath), { recursive: true });
2945
- writeFileSync$1(outPath, JSON.stringify(output));
2946
- return items;
2947
- }
2948
- function cosineSimilarity(vecA, vecB) {
2949
- let dot = 0;
2950
- let normA = 0;
2951
- let normB = 0;
2952
- for (let idx = 0; idx < vecA.length; idx++) {
2953
- dot += vecA[idx] * vecB[idx];
2954
- normA += vecA[idx] * vecA[idx];
2955
- normB += vecB[idx] * vecB[idx];
2956
- }
2957
- const denom = Math.sqrt(normA) * Math.sqrt(normB);
2958
- return denom === 0 ? 0 : dot / denom;
2959
- }
2960
- //#endregion
2961
- //#region src/advisor/recall-semantic.ts
2962
- let cachedEmbeddings = null;
2963
- function getEmbeddings() {
2964
- if (cachedEmbeddings === null) cachedEmbeddings = loadModelEmbeddings();
2965
- return cachedEmbeddings;
2966
- }
2967
- function isSemanticAvailable() {
2968
- return getEmbeddings() !== null;
2969
- }
2970
- function matchesTarget(model, target) {
2971
- const needle = target.toLowerCase();
2972
- return [
2973
- model.model,
2974
- model.name,
2975
- model.family,
2976
- model.familyName,
2977
- model.provider
2978
- ].some((field) => field?.toLowerCase().includes(needle));
2979
- }
2980
- function matchesAnyTarget(model, targets) {
2981
- return targets.some((target) => matchesTarget(model, target));
2982
- }
2983
- function applyExcludes(candidates, excludes) {
2984
- if (excludes.length === 0) return candidates;
2985
- return candidates.filter(({ model }) => !matchesAnyTarget(model, excludes));
2986
- }
2987
- function matchesSegment(model, segment) {
2988
- const modelIn = model.inferenceMetadata?.request_modality ?? [];
2989
- const modelOut = model.inferenceMetadata?.response_modality ?? [];
2990
- const inOk = segment.inputModality.length === 0 || segment.inputModality.some((mod) => modelIn.includes(mod));
2991
- const outOk = segment.outputModality.length === 0 || segment.outputModality.some((mod) => modelOut.includes(mod));
2992
- if (!inOk || !outOk) return false;
2993
- if (segment.requiredCapabilities.length === 0) return true;
2994
- return segment.requiredCapabilities.some((cap) => model.capabilities.includes(cap));
2995
- }
2996
- function rankByEmbedding(embeddings, queryVector, allowedIds, topK) {
2997
- return embeddings.filter((item) => allowedIds.has(item.id)).map((item) => ({
2998
- id: item.id,
2999
- similarity: cosineSimilarity(queryVector, item.vector)
3000
- })).sort((left, right) => right.similarity - left.similarity).slice(0, topK);
3001
- }
3002
- function recallScoped(models, embeddings, queryVector, preference, topK) {
3003
- const targets = preference.targets ?? [];
3004
- const scopedModels = targets.length > 0 ? models.filter((profile) => matchesAnyTarget(profile, targets)) : models;
3005
- const MIN_SCOPED = 5;
3006
- const pool = scopedModels.length >= MIN_SCOPED ? scopedModels : models;
3007
- const scored = rankByEmbedding(embeddings, queryVector, new Set(pool.map((profile) => profile.model)), topK);
3008
- const modelMap = new Map(models.map((profile) => [profile.model, profile]));
3009
- const results = [];
3010
- if (scopedModels.length < MIN_SCOPED && targets.length > 0) {
3011
- for (const profile of scopedModels) results.push({
3012
- model: profile,
3013
- score: 1
3014
- });
3015
- const seen = new Set(results.map(({ model }) => model.model));
3016
- for (const { id, similarity } of scored) {
3017
- if (seen.has(id)) continue;
3018
- const model = modelMap.get(id);
3019
- if (model) results.push({
3020
- model,
3021
- score: similarity
3022
- });
3023
- if (results.length >= topK) break;
3024
- }
3025
- return results;
3026
- }
3027
- for (const { id, similarity } of scored) {
3028
- const model = modelMap.get(id);
3029
- if (model) results.push({
3030
- model,
3031
- score: similarity
3032
- });
3033
- }
3034
- return results;
3035
- }
3036
- function recallComparison(models, embeddings, queryVector, preference, topK) {
3037
- const targets = preference.targets ?? [];
3038
- const modelMap = new Map(models.map((profile) => [profile.model, profile]));
3039
- const forced = [];
3040
- const forcedIds = /* @__PURE__ */ new Set();
3041
- for (const profile of models) if (matchesAnyTarget(profile, targets) && !forcedIds.has(profile.model)) {
3042
- forced.push({
3043
- model: profile,
3044
- score: 1
3045
- });
3046
- forcedIds.add(profile.model);
3047
- }
3048
- const remaining = topK - forced.length;
3049
- if (remaining > 0) {
3050
- const extra = rankByEmbedding(embeddings, queryVector, new Set(models.filter((profile) => !forcedIds.has(profile.model)).map((profile) => profile.model)), remaining);
3051
- for (const { id, similarity } of extra) {
3052
- const model = modelMap.get(id);
3053
- if (model) forced.push({
3054
- model,
3055
- score: similarity
3056
- });
3057
- }
3058
- }
3059
- return forced;
3060
- }
3061
- function recallAlternative(models, embeddings, queryVector, preference, topK) {
3062
- const targets = preference.targets ?? [];
3063
- const modelMap = new Map(models.map((profile) => [profile.model, profile]));
3064
- const refModels = models.filter((profile) => matchesAnyTarget(profile, targets));
3065
- const refFamilies = new Set(refModels.map((profile) => profile.family).filter(Boolean));
3066
- const results = [];
3067
- const seen = /* @__PURE__ */ new Set();
3068
- for (const profile of refModels) {
3069
- results.push({
3070
- model: profile,
3071
- score: 1
3072
- });
3073
- seen.add(profile.model);
3074
- }
3075
- const altPool = models.filter((profile) => !seen.has(profile.model) && (!profile.family || !refFamilies.has(profile.family)));
3076
- const scored = rankByEmbedding(embeddings, queryVector, new Set(altPool.map((profile) => profile.model)), topK - results.length);
3077
- for (const { id, similarity } of scored) {
3078
- const model = modelMap.get(id);
3079
- if (model) results.push({
3080
- model,
3081
- score: similarity
3082
- });
3083
- }
3084
- return results;
3085
- }
3086
- async function recallSemantic(config, models, query, topK, intent) {
3087
- let embeddings = getEmbeddings();
3088
- if (!embeddings) {
3089
- embeddings = await buildAndCacheEmbeddings(config, models);
3090
- cachedEmbeddings = embeddings;
3091
- }
3092
- const queryVector = await embedQuery(config, query);
3093
- const modelMap = new Map(models.map((profile) => [profile.model, profile]));
3094
- const preference = intent?.modelPreference;
3095
- const excludes = preference?.excludes ?? [];
3096
- if (preference && preference.mode !== "unconstrained") {
3097
- let results;
3098
- switch (preference.mode) {
3099
- case "scoped":
3100
- results = recallScoped(models, embeddings, queryVector, preference, topK);
3101
- break;
3102
- case "comparison":
3103
- results = recallComparison(models, embeddings, queryVector, preference, topK);
3104
- break;
3105
- case "alternative":
3106
- results = recallAlternative(models, embeddings, queryVector, preference, topK);
3107
- break;
3108
- default: results = [];
3109
- }
3110
- return applyExcludes(results, excludes);
3111
- }
3112
- if (intent?.complexity === Complexities.Pipeline && intent.segments?.length) {
3113
- const seen = /* @__PURE__ */ new Set();
3114
- const results = [];
3115
- const perSegment = Math.max(5, Math.ceil(topK / intent.segments.length));
3116
- for (const segment of intent.segments) {
3117
- const matched = models.filter((profile) => matchesSegment(profile, segment));
3118
- const allowedIds = new Set(matched.filter((profile) => !seen.has(profile.model)).map((profile) => profile.model));
3119
- if (allowedIds.size === 0) continue;
3120
- const scored = rankByEmbedding(embeddings, queryVector, allowedIds, perSegment);
3121
- for (const { id, similarity } of scored) {
3122
- const model = modelMap.get(id);
3123
- if (model && !seen.has(id)) {
3124
- results.push({
3125
- model,
3126
- score: similarity
3127
- });
3128
- seen.add(id);
3129
- }
3130
- }
3131
- }
3132
- return applyExcludes(results, excludes);
3133
- }
3134
- const allIds = new Set(models.map((profile) => profile.model));
3135
- const scored = rankByEmbedding(embeddings, queryVector, allIds, topK);
3136
- const results = [];
3137
- for (const { id, similarity } of scored) {
3138
- const model = modelMap.get(id);
3139
- if (model) results.push({
3140
- model,
3141
- score: similarity
3142
- });
3143
- }
3144
- return applyExcludes(results, excludes);
3145
- }
3146
- //#endregion
3147
- //#region src/advisor/recommend.ts
3148
- function formatPrices(profile) {
3149
- if (!profile.prices?.length) return void 0;
3150
- return profile.prices.map((price) => `${price.type}:${price.price}/${price.unit}`).join(", ");
3151
- }
3152
- function formatQpm(profile) {
3153
- if (!profile.qpmInfo) return void 0;
3154
- const entries = Object.entries(profile.qpmInfo);
3155
- if (entries.length === 0) return void 0;
3156
- return entries.map(([key, limit]) => `${key}:${limit.count_limit}/${limit.count_limit_period}s`).join(", ");
3157
- }
3158
- function buildCandidatesContext(candidates) {
3159
- return candidates.map(({ model: profile }) => {
3160
- const parts = [
3161
- `ID: ${profile.model}`,
3162
- `Name: ${profile.name}`,
3163
- `Description: ${profile.shortDescription || profile.description}`,
3164
- `Capabilities: ${profile.capabilities.join(", ")}`,
3165
- `Features: ${profile.features.join(", ")}`
3166
- ];
3167
- if (profile.contextWindow) parts.push(`Context Window: ${profile.contextWindow}`);
3168
- if (profile.maxOutputTokens) parts.push(`Max Output: ${profile.maxOutputTokens}`);
3169
- if (profile.category) parts.push(`Category: ${profile.category}`);
3170
- const modality = profile.inferenceMetadata;
3171
- if (modality?.request_modality?.length) parts.push(`Input Modality: ${modality.request_modality.join(", ")}`);
3172
- if (modality?.response_modality?.length) parts.push(`Output Modality: ${modality.response_modality.join(", ")}`);
3173
- const prices = formatPrices(profile);
3174
- if (prices) parts.push(`Pricing: ${prices}`);
3175
- const qpm = formatQpm(profile);
3176
- if (qpm) parts.push(`QPM: ${qpm}`);
3177
- if (profile.versionTag) parts.push(`Version: ${profile.versionTag}`);
3178
- if (profile.openSource !== void 0) parts.push(`Open Source: ${profile.openSource ? "Yes" : "No"}`);
3179
- if (profile.family) parts.push(`Family: ${profile.family}`);
3180
- return parts.join(" | ");
3181
- }).join("\n");
3182
- }
3183
- function buildIntentContext(intent) {
3184
- const { taskSummary, scenarioHints, inputModality, outputModality, requiredCapabilities, requiredFeatures, budget, qualityPreference, contextNeed, segments, modelPreference } = intent;
3185
- const parts = [];
3186
- if (taskSummary) parts.push(`Task: ${taskSummary}`);
3187
- if (scenarioHints.length) parts.push(`Scenario: ${scenarioHints.join(", ")}`);
3188
- if (inputModality.length) parts.push(`Input: ${inputModality.join(", ")}`);
3189
- if (outputModality.length) parts.push(`Output: ${outputModality.join(", ")}`);
3190
- if (requiredCapabilities.length) parts.push(`Capabilities: ${requiredCapabilities.join(", ")}`);
3191
- if (requiredFeatures.length) parts.push(`Features: ${requiredFeatures.join(", ")}`);
3192
- parts.push(`Budget: ${budget}`);
3193
- parts.push(`Quality: ${qualityPreference}`);
3194
- if (contextNeed !== ContextNeeds.Standard) parts.push(`Context: ${contextNeed}`);
3195
- if (modelPreference && modelPreference.mode !== "unconstrained") {
3196
- parts.push(`Mode: ${modelPreference.mode}`);
3197
- if (modelPreference.targets?.length) parts.push(`Targets: ${modelPreference.targets.join(", ")}`);
3198
- if (modelPreference.excludes?.length) parts.push(`Excludes: ${modelPreference.excludes.join(", ")}`);
3199
- }
3200
- if (segments?.length) {
3201
- parts.push(`Pipeline Steps:`);
3202
- for (const seg of segments) {
3203
- const inMod = seg.inputModality.join(",") || "none";
3204
- const outMod = seg.outputModality.join(",") || "none";
3205
- const caps = seg.requiredCapabilities.join(",") || "none";
3206
- parts.push(` - ${seg.step} (Input: ${inMod} → Output: ${outMod}, Capabilities: ${caps})`);
3207
- }
3208
- }
3209
- return parts.join("\n");
3210
- }
3211
- function buildDocLink(docUrl) {
3212
- if (!docUrl) return void 0;
3213
- const match = docUrl.match(/\/(\d+)\.html/);
3214
- if (!match) return void 0;
3215
- return `https://bailian.console.aliyun.com/cn-beijing?tab=doc#/doc/?type=model&url=${match[1]}`;
3216
- }
3217
- function buildRecommendations(items, modelMap, limit) {
3218
- const list = Array.isArray(items) ? items : [];
3219
- const recommendations = [];
3220
- const seenFamilies = /* @__PURE__ */ new Set();
3221
- for (const item of list) {
3222
- const profile = modelMap.get(item.model);
3223
- if (!profile) continue;
3224
- if (profile.family && seenFamilies.has(profile.family)) continue;
3225
- if (profile.family) seenFamilies.add(profile.family);
3226
- const { model, name, category, contextWindow, maxOutputTokens, docUrl } = profile;
3227
- recommendations.push({
3228
- model,
3229
- name,
3230
- reason: item.reason ?? "",
3231
- highlights: item.highlights ?? [],
3232
- category,
3233
- contextWindow,
3234
- maxOutputTokens,
3235
- docUrl
3236
- });
3237
- if (recommendations.length >= limit) break;
3238
- }
3239
- return recommendations;
3240
- }
3241
- function validatePipelineCompatibility(steps, modelMap) {
3242
- for (let stepIdx = 1; stepIdx < steps.length; stepIdx++) {
3243
- const prevStep = steps[stepIdx - 1];
3244
- const currStep = steps[stepIdx];
3245
- const prevOutputs = new Set(prevStep.recommendations.flatMap((rec) => {
3246
- return modelMap.get(rec.model)?.inferenceMetadata?.response_modality ?? [];
3247
- }));
3248
- if (prevOutputs.size === 0) continue;
3249
- const warnings = [];
3250
- for (const rec of currStep.recommendations) {
3251
- const accepts = modelMap.get(rec.model)?.inferenceMetadata?.request_modality ?? [];
3252
- if (!accepts.some((mod) => prevOutputs.has(mod)) && accepts.length > 0) warnings.push(`${rec.name}'s input modalities [${accepts.join(", ")}] may not be compatible with the previous step's output modalities [${[...prevOutputs].join(", ")}]`);
3253
- }
3254
- if (warnings.length > 0) currStep.warnings = warnings;
3255
- }
3256
- }
3257
- async function rankModels(config, candidates, intent, userInput, top, options) {
3258
- const candidatesContext = buildCandidatesContext(candidates);
3259
- const intentContext = buildIntentContext(intent);
3260
- const preferenceMode = intent.modelPreference?.mode;
3261
- let systemPrompt;
3262
- if (preferenceMode === "comparison") systemPrompt = COMPARISON_SYSTEM_PROMPT;
3263
- else if (preferenceMode === "alternative") systemPrompt = ALTERNATIVE_SYSTEM_PROMPT;
3264
- else if (preferenceMode === "scoped") {
3265
- const scopeNote = intent.modelPreference?.targets?.length ? `\n\n## Scope Restriction\nThe user explicitly requested recommendations from: ${intent.modelPreference.targets.join(", ")}. Prioritize models within this scope.` : "";
3266
- systemPrompt = (intent.complexity === Complexities.Pipeline ? PIPELINE_SYSTEM_PROMPT : SINGLE_SYSTEM_PROMPT) + scopeNote;
3267
- } else systemPrompt = intent.complexity === Complexities.Pipeline ? PIPELINE_SYSTEM_PROMPT : SINGLE_SYSTEM_PROMPT;
3268
- const useThinkingModel = options?.enableThinking ?? false;
3269
- const userMessage = intent.complexity === Complexities.Pipeline ? `Intent Analysis:\n${intentContext}\n\nCandidate Models:\n${candidatesContext}\n\nUser Request: ${userInput}\n\nRecommend up to ${top} models for each pipeline step. Respond in English only.` : `Intent Analysis:\n${intentContext}\n\nCandidate Models:\n${candidatesContext}\n\nUser Request: ${userInput}\n\nRecommend up to ${top} models. Respond in English only.`;
3270
- const body = {
3271
- model: useThinkingModel ? RANKING_MODEL : RANKING_MODEL_FAST,
3272
- messages: [{
3273
- role: "system",
3274
- content: systemPrompt
3275
- }, {
3276
- role: "user",
3277
- content: userMessage
3278
- }],
3279
- max_tokens: 4096,
3280
- temperature: 0
3281
- };
3282
- if (useThinkingModel) {
3283
- body.stream = true;
3284
- body.enable_thinking = true;
3285
- }
3286
- const url = chatEndpoint(config.baseUrl);
3287
- let content;
3288
- if (useThinkingModel) {
3289
- const res = await request(config, {
3290
- url,
3291
- method: "POST",
3292
- body,
3293
- stream: true
3294
- });
3295
- let accumulated = "";
3296
- let contentStarted = false;
3297
- for await (const event of parseSSE(res)) {
3298
- if (event.data === "[DONE]") break;
3299
- try {
3300
- const parsed = JSON.parse(event.data);
3301
- for (const choice of parsed.choices) {
3302
- const delta = choice.delta;
3303
- if (delta.reasoning_content && options?.onThinking) options.onThinking(delta.reasoning_content);
3304
- if (delta.content) {
3305
- if (!contentStarted) {
3306
- contentStarted = true;
3307
- options?.onContentStart?.();
3308
- }
3309
- accumulated += delta.content;
3310
- }
3311
- }
3312
- } catch {}
3313
- }
3314
- content = accumulated || "{}";
3315
- } else content = (await requestJson(config, {
3316
- url,
3317
- method: "POST",
3318
- body
3319
- })).choices?.[0]?.message?.content ?? "{}";
3320
- let parsed;
3321
- try {
3322
- const jsonMatch = content.match(/\{[\s\S]*\}/);
3323
- parsed = JSON.parse(jsonMatch?.[0] ?? "{}");
3324
- } catch {
3325
- return {
3326
- type: Complexities.Single,
3327
- recommendations: []
3328
- };
3329
- }
3330
- const modelMap = new Map(candidates.map(({ model: profile }) => [profile.model, profile]));
3331
- if (parsed.type === Complexities.Pipeline && Array.isArray(parsed.steps)) {
3332
- const steps = [];
3333
- for (const rawStep of parsed.steps) {
3334
- const recs = buildRecommendations(rawStep.recommendations ?? (rawStep.model ? [rawStep] : []), modelMap, top);
3335
- if (recs.length > 0) steps.push({
3336
- step: rawStep.step ?? "",
3337
- recommendations: recs
3338
- });
3339
- }
3340
- validatePipelineCompatibility(steps, modelMap);
3341
- return {
3342
- type: Complexities.Pipeline,
3343
- summary: parsed.summary ?? "",
3344
- steps
3345
- };
3346
- }
3347
- const recommendations = buildRecommendations(parsed.recommendations ?? parsed ?? [], modelMap, top);
3348
- return {
3349
- type: Complexities.Single,
3350
- recommendations
3351
- };
3352
- }
3353
- //#endregion
3354
- export { BAILIAN_HOST, BailianError, Budgets, CHANNEL, CONSOLE_GATEWAY_NO_TOKEN_MESSAGE, Capabilities, Complexities, ContextNeeds, DOCS_HOSTS, ExitCode, Features, GLOBAL_OPTIONS, McpClient, Modalities, ModelCategories, QualityPreferences, REGIONS, SOURCE_CONFIG, TAGS, analyzeIntent, appCompletionEndpoint, bailianMcpUrl, buildDocLink, callConsoleGateway, chatEndpoint, clearApiKey, createTrackingEvent, defineCommand, detectOutputFormat, effectiveConsoleGatewayConfig, ensureConfigDir, fetchModelList, flushTelemetry, formatErrorJson, formatJson, formatOutput, formatText, generateFilename, generateToolSchema, getConfigDir, getConfigPath, getCredentialsPath, getModels, imageEndpoint, imageSyncEndpoint, isCI, isInteractive, isLocalFile, isSemanticAvailable, knowledgeRetrieveEndpoint, loadApiKeyFromConfig, loadConfig, localSink, mapApiError, maskToken, mcpWebSearchEndpoint, memoryAddEndpoint, memoryListEndpoint, memoryNodeEndpoint, memorySearchEndpoint, parseBooleanValue, parseConfigFile, parseOptionalBooleanValue, parseSSE, profileSchemaEndpoint, rankModels, readConfigFile, recallCandidates, recallSemantic, remoteSink, request, requestJson, resolveBooleanFlag, resolveConsoleGatewayCredential, resolveCredential, resolveFileUrl, resolveOutputDir, resolveWatermark, saveApiKeyToConfig, signRequest, speechRecognizeEndpoint, speechSynthesizeEndpoint, stripUndefined, taskEndpoint, trackCommandExecution, trackingHeaders, uploadFile, userProfileEndpoint, videoGenerateEndpoint, writeConfigFile };
183
+ {"type":"single","recommendations":[{"model":"model ID","reason":"alternative analysis","highlights":["differentiators"]}]}`;else if(c===`scoped`){let e=n.modelPreference?.targets?.length?`\n\n## Scope Restriction\nThe user explicitly requested recommendations from: ${n.modelPreference.targets.join(`, `)}. Prioritize models within this scope.`:``;l=(n.complexity===J.Pipeline?br:yr)+e}else l=n.complexity===J.Pipeline?br:yr;let u=a?.enableThinking??!1,d=n.complexity===J.Pipeline?`Intent Analysis:\n${s}\n\nCandidate Models:\n${o}\n\nUser Request: ${r}\n\nRecommend up to ${i} models for each pipeline step. Respond in English only.`:`Intent Analysis:\n${s}\n\nCandidate Models:\n${o}\n\nUser Request: ${r}\n\nRecommend up to ${i} models. Respond in English only.`,f={model:u?`qwen3.6-flash`:`qwen-flash`,messages:[{role:`system`,content:l},{role:`user`,content:d}],max_tokens:4096,temperature:0};u&&(f.stream=!0,f.enable_thinking=!0);let p=Ne(e.baseUrl),m;if(u){let t=await z(e,{url:p,method:`POST`,body:f,stream:!0}),n=``,r=!1;for await(let e of _t(t)){if(e.data===`[DONE]`)break;try{let t=JSON.parse(e.data);for(let e of t.choices){let t=e.delta;t.reasoning_content&&a?.onThinking&&a.onThinking(t.reasoning_content),t.content&&(r||(r=!0,a?.onContentStart?.()),n+=t.content)}}catch{}}m=n||`{}`}else m=(await B(e,{url:p,method:`POST`,body:f})).choices?.[0]?.message?.content??`{}`;let h;try{let e=m.match(/\{[\s\S]*\}/);h=JSON.parse(e?.[0]??`{}`)}catch{return{type:J.Single,recommendations:[]}}let g=new Map(t.map(({model:e})=>[e.model,e]));if(h.type===J.Pipeline&&Array.isArray(h.steps)){let e=[];for(let t of h.steps){let n=fi(t.recommendations??(t.model?[t]:[]),g,i);n.length>0&&e.push({step:t.step??``,recommendations:n})}return pi(e,g),{type:J.Pipeline,summary:h.summary??``,steps:e}}let _=fi(h.recommendations??h??[],g,i);return{type:J.Single,recommendations:_}}export{le as BAILIAN_HOST,N as BailianError,hr as Budgets,lt as CHANNEL,Oe as CONSOLE_GATEWAY_NO_TOKEN_MESSAGE,X as Capabilities,J as Complexities,gr as ContextNeeds,dn as DEFAULT_TRAINING_TYPE,ce as DOCS_HOSTS,M as ExitCode,_r as Features,On as GLOBAL_OPTIONS,vn as INSUFFICIENT_SAMPLES_CODE,Pt as MAX_DATASET_BYTES,gt as McpClient,mr as Modalities,vr as ModelCategories,Y as QualityPreferences,F as REGIONS,dt as SOURCE_CONFIG,ut as TAGS,un as TRAINING_TYPES_CLI,W as TRAINING_TYPE_MAP,xr as analyzeIntent,Re as appCompletionEndpoint,ht as bailianMcpUrl,di as buildDocLink,St as callConsoleGateway,an as cancelFineTune,Ne as chatEndpoint,Ee as clearApiKey,bn as createDeployment,tn as createFineTune,Bn as createTrackingEvent,Dn as defineCommand,Nt as deleteDataset,Cn as deleteDeployment,on as deleteFineTune,ye as detectOutputFormat,bt as effectiveConsoleGatewayConfig,he as ensureConfigDir,ln as exportCheckpoint,_n as fetchModelCapability,V as fetchModelList,Xn as flushTelemetry,ve as formatErrorJson,en as formatIssue,_e as formatJson,be as formatOutput,ge as formatText,An as generateFilename,I as getConfigDir,L as getConfigPath,me as getCredentialsPath,Mt as getDataset,Sn as getDeployment,rn as getFineTune,sn as getFineTuneLogs,pr as getModels,Pe as imageEndpoint,Fe as imageSyncEndpoint,Pn as isCI,Nn as isInteractive,Dt as isLocalFile,Qr as isSemanticAvailable,fn as isTrainingTypeCli,qe as knowledgeRetrieveEndpoint,cn as listCheckpoints,jt as listDatasets,wn as listDeployableModels,xn as listDeployments,nn as listFineTunes,$t as listSupportedFormats,gn as listSupportedTrainingTypes,we as loadApiKeyFromConfig,Ce as loadConfig,Zn as localSink,P as mapApiError,ft as maskToken,Je as mcpWebSearchEndpoint,ze as memoryAddEndpoint,Ve as memoryListEndpoint,He as memoryNodeEndpoint,Be as memorySearchEndpoint,hn as modelSupportsTrainingType,In as parseBooleanValue,pe as parseConfigFile,It as parseDatasetSchemaFlag,Ln as parseOptionalBooleanValue,_t as parseSSE,Xt as pickValidator,yn as preflightBatchSizeGate,Ge as profileSchemaEndpoint,mi as rankModels,xe as readConfigFile,Ir as recallCandidates,oi as recallSemantic,Zt as registerValidator,Qn as remoteSink,z as request,B as requestJson,Rn as resolveBooleanFlag,ke as resolveConsoleGatewayCredential,De as resolveCredential,Ot as resolveFileUrl,Mn as resolveOutputDir,zn as resolveWatermark,Te as saveApiKeyToConfig,Tn as scaleDeployment,Ae as signRequest,We as speechRecognizeEndpoint,Ue as speechSynthesizeEndpoint,Fn as stripUndefined,Le as taskEndpoint,pn as toServerTrainingType,nr as trackCommandExecution,R as trackingHeaders,mn as trainingTypeMethodVariant,En as updateDeployment,At as uploadDataset,Et as uploadFile,Ke as userProfileEndpoint,Qt as validateDataset,Ie as videoGenerateEndpoint,Se as writeConfigFile};