@done-coding/cli-cc-switch 0.2.0 → 0.3.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.
@@ -1,615 +0,0 @@
1
- #!/usr/bin/env node
2
- import { spawn as se } from "node:child_process";
3
- import b from "node:os";
4
- import P from "node:path";
5
- import { resolveHandlerContext as J, xPrompts as W } from "@done-coding/cli-utils";
6
- import m from "node:fs";
7
- import ne from "node:readline";
8
- const l = P.join(
9
- b.homedir(),
10
- ".done-coding",
11
- "cc-switch",
12
- "profile.json"
13
- ), p = P.join(
14
- b.homedir(),
15
- ".done-coding",
16
- "cc-switch",
17
- "provider.json"
18
- ), d = P.join(
19
- b.homedir(),
20
- ".done-coding",
21
- "cc-switch",
22
- "model.json"
23
- ), g = "--meta-profile=", j = "--meta-pick", A = "--meta-generate", v = "--meta-apiKey=", $ = "--meta-model-name=", h = "--meta-provider=", I = "--meta-provider-list", L = "--meta-model-list", N = "--meta-help", R = "--meta-version", F = {
24
- run: 0,
25
- profile: 1,
26
- pick: 2,
27
- setkey: 3,
28
- addmodel: 4,
29
- providerlist: 5,
30
- modellist: 6,
31
- generate: 7,
32
- version: 8,
33
- help: 9
34
- }, w = (e, r) => F[r] > F[e] ? r : e, ie = (e) => e.startsWith("--meta-") && e !== j && e !== A && e !== N && e !== R && e !== I && e !== L && !e.startsWith(g) && !e.startsWith(v) && !e.startsWith($) && !e.startsWith(h), ce = () => {
35
- process.stdout.write(
36
- [
37
- "dc-cc-switch(cc-router)— claude-code 模型路由透传",
38
- "",
39
- "用法:",
40
- " dc-cc-switch [meta 选项] <claude 参数...>",
41
- "",
42
- "meta 选项(cc-switch 自身命令面,不透传给 claude):",
43
- ` ${g}<name> 显式指定 profile 启动`,
44
- ` ${j} 终端交互选择 profile 启动`,
45
- ` ${A} 从 provider.json + model.json 重新生成 profile.json`,
46
- ` ${v}<key> 更新指定提供商 apiKey(自动重建)`,
47
- ` ${$}<name> 添加模型(自动重建)`,
48
- ` ${h}<id> 显式指定 provider(供 apiKey/model-name 跳过选择)`,
49
- ` ${I} 输出提供商列表(id + name)`,
50
- ` ${L} 输出模型列表(name + 所属 provider)`,
51
- ` ${N} 显示本帮助`,
52
- ` ${R} 显示版本`,
53
- "",
54
- "其余所有参数原样透传给 claude。",
55
- `配置: ${l}`,
56
- "源: provider.json / model.json(--meta-generate 消费)",
57
- ""
58
- ].join(`
59
- `)
60
- );
61
- }, ae = (e) => {
62
- process.stdout.write(`${e}
63
- `);
64
- }, le = async (e) => {
65
- const r = Object.keys(e.profiles);
66
- r.length === 0 && (process.stderr.write(
67
- `配置中没有可用 profile,请先编辑 ${l}。
68
- `
69
- ), process.exit(1)), J().interactive || (process.stderr.write(
70
- `--meta-pick 需要交互式终端,请改用 --meta-profile=<name> 显式指定。
71
- `
72
- ), process.exit(1));
73
- const { profile: t } = await W({
74
- type: "select",
75
- name: "profile",
76
- message: "选择以哪个配置启动 claude",
77
- choices: r.map((o) => ({ title: o, value: o }))
78
- });
79
- return t;
80
- }, de = async (e) => {
81
- const r = Object.keys(e.providers);
82
- r.length === 0 && (process.stderr.write(
83
- `provider.json 没有可用提供商,请先编辑 ${p}。
84
- `
85
- ), process.exit(1)), J().interactive || (process.stderr.write(
86
- `需要交互式终端选择提供商,请改用 ${h}<id> 显式指定。
87
- `
88
- ), process.exit(1));
89
- const { provider: t } = await W({
90
- type: "select",
91
- name: "provider",
92
- message: "选择提供商",
93
- choices: r.map((o) => ({
94
- title: `${o}(${e.providers[o].name})`,
95
- value: o
96
- }))
97
- });
98
- return t;
99
- }, pe = (e) => {
100
- let r, t, o, s, n = "run";
101
- const c = [];
102
- for (const i of e) {
103
- if (i.startsWith(g)) {
104
- r = i.slice(g.length), n = w(n, "profile");
105
- continue;
106
- }
107
- if (i.startsWith(v)) {
108
- if (t = i.slice(v.length), !t)
109
- throw new Error(`${v} 需提供 apiKey 值`);
110
- n = w(n, "setkey");
111
- continue;
112
- }
113
- if (i.startsWith($)) {
114
- if (o = i.slice($.length), !o)
115
- throw new Error(`${$} 需提供模型名`);
116
- n = w(n, "addmodel");
117
- continue;
118
- }
119
- if (i.startsWith(h)) {
120
- if (s = i.slice(h.length), !s)
121
- throw new Error(`${h} 需提供 provider id`);
122
- continue;
123
- }
124
- if (i === j) {
125
- n = w(n, "pick");
126
- continue;
127
- }
128
- if (i === A) {
129
- n = w(n, "generate");
130
- continue;
131
- }
132
- if (i === I) {
133
- n = w(n, "providerlist");
134
- continue;
135
- }
136
- if (i === L) {
137
- n = w(n, "modellist");
138
- continue;
139
- }
140
- if (i === N) {
141
- n = w(n, "help");
142
- continue;
143
- }
144
- if (i === R) {
145
- n = w(n, "version");
146
- continue;
147
- }
148
- if (ie(i))
149
- throw new Error(
150
- `未知 meta 选项:${i}。可用选项:${g}<name>、${j}、${A}、${v}<key>、${$}<name>、${h}<id>、${I}、${L}、${N}、${R}`
151
- );
152
- c.push(i);
153
- }
154
- return fe({ action: n, apiKey: t, modelName: o, providerId: s }), { action: n, profileName: r, apiKey: t, modelName: o, providerId: s, passthrough: c };
155
- }, fe = (e) => {
156
- const { action: r, apiKey: t, modelName: o, providerId: s } = e, n = [t, o].filter((c) => c !== void 0).length;
157
- if (n > 1)
158
- throw new Error(
159
- `不能同时指定 ${v} 与 ${$}`
160
- );
161
- if (r === "generate" && n > 0)
162
- throw new Error(
163
- `${A} 不能与 ${v} / ${$} 同时使用`
164
- );
165
- if (s !== void 0 && r !== "setkey" && r !== "addmodel" && r !== "help" && r !== "version")
166
- throw new Error(
167
- `${h} 仅用于 ${v} / ${$}`
168
- );
169
- }, me = (e, r) => {
170
- const t = r ?? e.defaultProfile, o = e.profiles[t];
171
- if (!o) {
172
- const s = Object.keys(e.profiles).join(", ") || "(无)";
173
- throw new Error(
174
- `profile "${t}" 不存在。可用 profile:${s}。配置文件:${l}。若需从 provider.json + model.json 重建,请运行 --meta-generate`
175
- );
176
- }
177
- return { name: t, profile: o };
178
- }, Ee = /^ANTHROPIC_/, ue = [
179
- "CLAUDE_CODE_SUBAGENT_MODEL",
180
- "CLAUDE_CODE_EFFORT_LEVEL"
181
- ], B = P.join(
182
- b.homedir(),
183
- ".claude",
184
- "settings.json"
185
- ), X = (e) => Ee.test(e) || ue.includes(e), we = (e, r) => {
186
- const t = {};
187
- for (const [o, s] of Object.entries(e))
188
- s !== void 0 && (X(o) || (t[o] = s));
189
- for (const [o, s] of Object.entries(r))
190
- t[o] = s;
191
- return t;
192
- }, ve = (e) => !e || typeof e != "object" ? [] : Object.keys(e).filter((r) => X(r)), $e = () => {
193
- let e;
194
- try {
195
- e = JSON.parse(m.readFileSync(B, "utf8"));
196
- } catch {
197
- return null;
198
- }
199
- if (typeof e != "object" || e === null)
200
- return null;
201
- const r = e.env;
202
- return typeof r != "object" || r === null || Array.isArray(r) ? null : r;
203
- }, G = {
204
- defaultProfile: "deepseek",
205
- profiles: {
206
- deepseek: {
207
- env: {
208
- ANTHROPIC_BASE_URL: "https://api.deepseek.com/anthropic",
209
- ANTHROPIC_AUTH_TOKEN: "",
210
- ANTHROPIC_MODEL: "deepseek-v4-pro[1m]",
211
- ANTHROPIC_DEFAULT_OPUS_MODEL: "deepseek-v4-pro[1m]",
212
- ANTHROPIC_DEFAULT_SONNET_MODEL: "deepseek-v4-pro[1m]",
213
- ANTHROPIC_DEFAULT_HAIKU_MODEL: "deepseek-v4-flash[1m]",
214
- CLAUDE_CODE_SUBAGENT_MODEL: "deepseek-v4-pro[1m]",
215
- CLAUDE_CODE_EFFORT_LEVEL: "max"
216
- }
217
- }
218
- }
219
- }, C = (e, r) => {
220
- m.mkdirSync(P.dirname(e), { recursive: !0 }), m.writeFileSync(e, JSON.stringify(r, null, 2)), m.chmodSync(e, 384);
221
- }, k = (e) => C(l, e), he = (e) => C(p, e), ye = (e) => C(d, e), Oe = () => {
222
- if (!m.existsSync(l)) {
223
- if (m.existsSync(p) || m.existsSync(d))
224
- throw new Error(
225
- `${l} 不存在,但已检测到 provider/model 源。请运行 --meta-generate 生成配置。`
226
- );
227
- return k(G), G;
228
- }
229
- const e = m.readFileSync(l, "utf8");
230
- let r;
231
- try {
232
- r = JSON.parse(e);
233
- } catch (o) {
234
- const s = o instanceof Error ? o.message : String(o);
235
- throw new Error(`配置文件非法 JSON:${l}(${s})`);
236
- }
237
- if (typeof r != "object" || r === null)
238
- throw new Error(`配置文件结构非法:${l}(应为 JSON 对象)`);
239
- const t = r;
240
- if (typeof t.defaultProfile != "string")
241
- throw new Error(`配置文件缺少字符串字段 defaultProfile:${l}`);
242
- if (typeof t.profiles != "object" || t.profiles === null || Array.isArray(t.profiles))
243
- throw new Error(`配置文件缺少对象字段 profiles:${l}`);
244
- return t;
245
- }, _ = (e) => typeof e == "object" && e !== null && !Array.isArray(e), Y = (e, r) => {
246
- if (e === void 0) return {};
247
- if (!_(e))
248
- throw new Error(`${r} [MUST] 为字符串键值对象`);
249
- const t = {};
250
- for (const [o, s] of Object.entries(e)) {
251
- if (typeof s != "string")
252
- throw new Error(`${r}.${o} [MUST] 为字符串`);
253
- t[o] = s;
254
- }
255
- return t;
256
- }, q = (e, r) => {
257
- if (!m.existsSync(e))
258
- throw new Error(`源配置文件不存在:${e}(请先创建 ${r})`);
259
- const t = m.readFileSync(e, "utf8");
260
- let o;
261
- try {
262
- o = JSON.parse(t);
263
- } catch (s) {
264
- const n = s instanceof Error ? s.message : String(s);
265
- throw new Error(`${r} 非法 JSON:${e}(${n})`);
266
- }
267
- if (!_(o))
268
- throw new Error(`${r} 结构非法:${e}(应为 JSON 对象)`);
269
- return o;
270
- }, T = () => {
271
- const r = q(p, "provider.json").providers;
272
- if (!_(r))
273
- throw new Error(`provider.json 缺少对象字段 providers:${p}`);
274
- const t = {};
275
- for (const [o, s] of Object.entries(r)) {
276
- if (!_(s))
277
- throw new Error(`provider「${o}」[MUST] 为对象:${p}`);
278
- const { name: n, url: c, apiKey: i } = s;
279
- if (typeof n != "string" || n.length === 0)
280
- throw new Error(`provider「${o}」缺字符串字段 name:${p}`);
281
- if (typeof c != "string" || c.length === 0)
282
- throw new Error(`provider「${o}」缺字符串字段 url:${p}`);
283
- if (typeof i != "string" || i.length === 0)
284
- throw new Error(`provider「${o}」缺字符串字段 apiKey:${p}`);
285
- const a = Y(
286
- s.envExtraParams,
287
- `provider「${o}」envExtraParams`
288
- );
289
- t[o] = {
290
- name: n,
291
- url: c,
292
- apiKey: i,
293
- ...Object.keys(a).length > 0 ? { envExtraParams: a } : {}
294
- };
295
- }
296
- return { providers: t };
297
- }, D = () => {
298
- const e = q(d, "model.json"), r = e.defaultProfile;
299
- if (typeof r != "string" || r.length === 0)
300
- throw new Error(`model.json 缺少字符串字段 defaultProfile:${d}`);
301
- const t = e.models;
302
- if (!Array.isArray(t))
303
- throw new Error(`model.json 缺少数组字段 models:${d}`);
304
- const o = [];
305
- for (const [s, n] of t.entries()) {
306
- if (!_(n))
307
- throw new Error(`model.json models[${s}] [MUST] 为对象:${d}`);
308
- const { provider: c, id: i, name: a } = n;
309
- if (typeof c != "string" || c.length === 0)
310
- throw new Error(
311
- `model.json models[${s}] 缺字符串字段 provider:${d}`
312
- );
313
- if (typeof i != "string" || i.length === 0)
314
- throw new Error(
315
- `model.json models[${s}] 缺字符串字段 id:${d}`
316
- );
317
- if (typeof a != "string" || a.length === 0)
318
- throw new Error(
319
- `model.json models[${s}] 缺字符串字段 name:${d}`
320
- );
321
- const f = Y(
322
- n.envExtraParams,
323
- `model.json models[${s}] envExtraParams`
324
- );
325
- o.push({
326
- provider: c,
327
- id: i,
328
- name: a,
329
- ...Object.keys(f).length > 0 ? { envExtraParams: f } : {}
330
- });
331
- }
332
- return { defaultProfile: r, models: o };
333
- }, ge = (e, r) => ({
334
- ANTHROPIC_BASE_URL: e.url,
335
- ANTHROPIC_AUTH_TOKEN: e.apiKey,
336
- ANTHROPIC_MODEL: r.name,
337
- ANTHROPIC_DEFAULT_OPUS_MODEL: r.name,
338
- ANTHROPIC_DEFAULT_SONNET_MODEL: r.name,
339
- ANTHROPIC_DEFAULT_HAIKU_MODEL: r.name,
340
- CLAUDE_CODE_SUBAGENT_MODEL: r.name,
341
- ...e.envExtraParams ?? {},
342
- ...r.envExtraParams ?? {}
343
- }), Ae = (e, r) => {
344
- const t = {}, o = /* @__PURE__ */ new Set();
345
- for (const s of r.models) {
346
- const n = e.providers[s.provider];
347
- if (!n)
348
- throw new Error(
349
- `model「${s.id}」引用了不存在的 provider「${s.provider}」:${d}`
350
- );
351
- const c = `${s.provider}-${s.id}`;
352
- if (o.has(c))
353
- throw new Error(
354
- `profile 名重复:${c}(provider+id 组合重复):${d}`
355
- );
356
- o.add(c), t[c] = { env: ge(n, s) };
357
- }
358
- if (Object.keys(t).length === 0)
359
- throw new Error(
360
- `model.json 的 models 为空,无可生成 profile:${d}`
361
- );
362
- if (!t[r.defaultProfile]) {
363
- const s = Object.keys(t).join(", ");
364
- throw new Error(
365
- `defaultProfile「${r.defaultProfile}」不在生成的 profile 中。可用:${s}。配置文件:${d}`
366
- );
367
- }
368
- return { defaultProfile: r.defaultProfile, profiles: t };
369
- }, x = () => {
370
- const e = Ae(T(), D());
371
- return k(e), e;
372
- }, z = (e) => {
373
- const r = e.trim();
374
- if (r.length === 0)
375
- throw new Error("模型名为空(--meta-model-name 值不可为空)");
376
- const t = r.replace(/\[1m\]$/, "");
377
- return { id: t, name: `${t}[1m]` };
378
- }, _e = (e, r) => {
379
- const t = T(), o = t.providers[e];
380
- if (!o)
381
- throw new Error(
382
- `provider「${e}」不存在。可用:${Object.keys(t.providers).join(", ")}。配置文件:${p}`
383
- );
384
- return o.apiKey = r, he(t), x();
385
- }, Te = (e, r) => {
386
- const { id: t, name: o } = z(r), s = T();
387
- if (!s.providers[e])
388
- throw new Error(
389
- `provider「${e}」不存在。可用:${Object.keys(s.providers).join(", ")}。配置文件:${p}`
390
- );
391
- const n = D(), c = n.models.find((i) => i.provider === e && i.id === t);
392
- if (c)
393
- throw new Error(
394
- `model「${e}/${t}」已存在(name=${c.name}):${d}`
395
- );
396
- return n.models.push({ provider: e, id: t, name: o }), ye(n), x();
397
- }, Pe = (e) => Object.entries(e.providers).map(([r, t]) => `${r}(${t.name})`), Se = (e) => e.models.map((r) => `${r.name}(${r.provider})`), je = /TOKEN|KEY|SECRET/i;
398
- class K extends Error {
399
- constructor() {
400
- super("用户中断输入"), this.name = "PromptAbortError";
401
- }
402
- }
403
- const Ie = (e) => je.test(e), We = (e) => e === "" ? "" : "******", Q = (e) => Object.keys(e).filter((r) => e[r] === "");
404
- let M = !1, O = null;
405
- const Le = (e) => new Promise((r, t) => {
406
- const o = ne.createInterface({
407
- input: process.stdin,
408
- output: process.stderr
409
- });
410
- O = o, o.on("close", () => {
411
- O === o && (O = null);
412
- }), o.question(e, (s) => {
413
- o.close(), r(s);
414
- }), o.on("SIGINT", () => {
415
- o.close(), t(new K());
416
- });
417
- }), Ne = 3, Re = 4, be = 127, Me = (e) => new Promise((r, t) => {
418
- process.stderr.write(e);
419
- const o = process.stdin;
420
- typeof o.setRawMode == "function" && (o.setRawMode(!0), M = !0), o.resume(), o.setEncoding("utf8");
421
- let s = "";
422
- const n = () => {
423
- o.removeListener("data", c);
424
- }, c = (i) => {
425
- for (const a of i) {
426
- const f = a.charCodeAt(0);
427
- if (a === "\r" || a === `
428
- `) {
429
- n(), process.stderr.write(`
430
- `), r(s);
431
- return;
432
- }
433
- if (f === Ne || f === Re) {
434
- n(), process.stderr.write(`
435
- `), t(new K());
436
- return;
437
- }
438
- if (f === be || a === "\b") {
439
- s = s.slice(0, -1);
440
- continue;
441
- }
442
- s += a;
443
- }
444
- };
445
- o.on("data", c);
446
- }), Ce = async (e) => {
447
- const r = Q(e.env);
448
- for (const t of r) {
449
- const o = Ie(t);
450
- let s = "";
451
- for (; s === ""; ) {
452
- const n = `请输入 ${t}: `;
453
- s = o ? await Me(n) : await Le(n);
454
- }
455
- e.env[t] = s;
456
- }
457
- }, ke = () => {
458
- O && (O.close(), O = null);
459
- const e = process.stdin;
460
- M && typeof e.setRawMode == "function" && (e.setRawMode(!1), M = !1), e.removeAllListeners("data"), e.removeAllListeners("keypress"), e.removeAllListeners("readable"), e.pause();
461
- }, Z = {
462
- version: "0.2.0",
463
- cliConfig: {
464
- moduleName: "cc-switch"
465
- }
466
- }, De = "claude", ee = async (e) => {
467
- const { action: r, profileName: t, apiKey: o, modelName: s, providerId: n, passthrough: c } = pe(e ?? process.argv.slice(2));
468
- if (r === "help" && (ce(), process.exit(0)), r === "version" && (ae(Z.version), process.exit(0)), r === "generate") {
469
- const E = x();
470
- process.stdout.write(
471
- `已生成 ${Object.keys(E.profiles).length} 个 profile → ${l}
472
- `
473
- ), process.exit(0);
474
- }
475
- if (r === "providerlist" || r === "modellist") {
476
- const E = r === "providerlist" ? Pe(T()) : Se(D());
477
- for (const u of E)
478
- process.stdout.write(`${u}
479
- `);
480
- process.exit(0);
481
- }
482
- if (r === "setkey" || r === "addmodel") {
483
- const E = T(), u = n ?? await de(E), y = r === "setkey" ? _e(u, o) : Te(u, s);
484
- process.stdout.write(
485
- r === "setkey" ? `已更新 provider「${u}」apiKey,重建 ${Object.keys(y.profiles).length} 个 profile → ${l}
486
- ` : `已添加 model「${u}/${z(s).id}」,重建 ${Object.keys(y.profiles).length} 个 profile → ${l}
487
- `
488
- ), process.exit(0);
489
- }
490
- const i = Oe(), a = r === "pick" ? await le(i) : t, { profile: f } = me(i, a);
491
- if (Q(f.env).length > 0) {
492
- try {
493
- await Ce(f);
494
- } catch (E) {
495
- if (E instanceof K)
496
- return process.stderr.write(`已取消,未写入配置。
497
- `), process.exit(1);
498
- throw E;
499
- }
500
- k(i), ke();
501
- }
502
- const re = $e(), U = ve(re);
503
- if (U.length > 0)
504
- return process.stderr.write(
505
- `检测到 ${B} 的 env 块含模型路由类 key:${U.join(", ")}。请手动清理这些 key 后重试。
506
- `
507
- ), process.exit(1);
508
- const oe = we(process.env, f.env), H = se(De, c, {
509
- stdio: "inherit",
510
- shell: !1,
511
- env: oe
512
- });
513
- return new Promise((E, u) => {
514
- H.on("error", (y) => {
515
- try {
516
- if (y.code === "ENOENT") {
517
- process.stderr.write(
518
- `未找到 claude 可执行文件,请确认 claude-code 已安装并在 PATH 中。
519
- `
520
- ), process.exit(127);
521
- return;
522
- }
523
- process.stderr.write(`启动 claude 失败:${y.message}
524
- `), process.exit(1);
525
- } catch (S) {
526
- u(S);
527
- }
528
- }), H.on("exit", (y, S) => {
529
- try {
530
- if (S) {
531
- process.exit(128 + xe(S));
532
- return;
533
- }
534
- process.exit(y ?? 1);
535
- } catch (te) {
536
- u(te);
537
- }
538
- });
539
- });
540
- }, xe = (e) => ({
541
- SIGHUP: 1,
542
- SIGINT: 2,
543
- SIGQUIT: 3,
544
- SIGILL: 4,
545
- SIGABRT: 6,
546
- SIGFPE: 8,
547
- SIGKILL: 9,
548
- SIGSEGV: 11,
549
- SIGPIPE: 13,
550
- SIGALRM: 14,
551
- SIGTERM: 15
552
- })[e] ?? 1, {
553
- cliConfig: { moduleName: V }
554
- } = Z, Be = async () => {
555
- try {
556
- await ee();
557
- } catch (e) {
558
- const r = e instanceof Error ? e.message : String(e);
559
- process.stderr.write(`${r}
560
- `), process.exit(1);
561
- }
562
- }, Xe = () => ({
563
- command: V,
564
- describe: "claude-code 模型路由透传(dc-cc-switch / cc-router)",
565
- builder(e) {
566
- return e.strict(!1).option("meta-profile", {
567
- type: "string",
568
- describe: "选择 profile(~/.done-coding/cc-switch/profile.json 中的 profile 名)"
569
- }).option("meta-pick", {
570
- type: "boolean",
571
- describe: "终端交互选择 profile 启动"
572
- }).option("meta-generate", {
573
- type: "boolean",
574
- describe: "从 provider.json + model.json 重建 profile.json"
575
- }).option("meta-apiKey", {
576
- type: "string",
577
- describe: "更新指定提供商 apiKey(自动重建)"
578
- }).option("meta-model-name", {
579
- type: "string",
580
- describe: "添加模型到指定提供商(自动重建)"
581
- }).option("meta-provider", {
582
- type: "string",
583
- describe: "显式指定 provider id(供 apiKey/model-name 跳过选择)"
584
- }).option("meta-provider-list", {
585
- type: "boolean",
586
- describe: "输出提供商列表(id + name)"
587
- }).option("meta-model-list", {
588
- type: "boolean",
589
- describe: "输出模型列表(name + 所属 provider)"
590
- }).option("meta-help", {
591
- type: "boolean",
592
- describe: "显示 cc-switch 自身帮助"
593
- }).option("meta-version", {
594
- type: "boolean",
595
- describe: "显示 cc-switch 自身版本"
596
- });
597
- },
598
- handler() {
599
- const e = process.argv.findIndex((t) => t === V), r = e >= 0 ? process.argv.slice(e + 1) : process.argv.slice(2);
600
- return ee(r);
601
- }
602
- });
603
- export {
604
- G as D,
605
- l as P,
606
- Be as a,
607
- we as b,
608
- Xe as c,
609
- Q as f,
610
- ve as h,
611
- Ie as i,
612
- We as m,
613
- pe as p,
614
- me as s
615
- };