anygate 0.5.10 → 0.6.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/{chunk-7QMN4CYN.js → chunk-CRK6YGKY.js} +5688 -4677
- package/dist/chunk-CRK6YGKY.js.map +1 -0
- package/dist/{chunk-FVNZB5RR.js → chunk-QLHVQYQN.js} +25 -3
- package/dist/chunk-QLHVQYQN.js.map +1 -0
- package/dist/{chunk-72WNE2IK.js → chunk-UT3JLF3M.js} +2 -13
- package/dist/{chunk-6AFYEDSU.js → chunk-VGM6EBG4.js} +10 -4
- package/dist/{chunk-6AFYEDSU.js.map → chunk-VGM6EBG4.js.map} +1 -1
- package/dist/cli.js +2219 -1221
- package/dist/cli.js.map +1 -1
- package/dist/{command-UYTXLN3H.js → command-PFFQI5YC.js} +186 -88
- package/dist/command-PFFQI5YC.js.map +1 -0
- package/dist/{constants-4XH536T3.js → constants-GW5BAY6G.js} +9 -3
- package/dist/{provider-templates-MNJZTG3Z.js → provider-templates-CRQJII3Z.js} +3 -3
- package/dist/registry/data/templates/agentrouter.json +19 -0
- package/dist/ui/dist/assets/{index-DWAOH_B3.css → index-D4hWZLit.css} +1 -1
- package/dist/ui/dist/assets/index-DyxtUjA-.js +7 -0
- package/dist/ui/dist/index.html +2 -2
- package/package.json +109 -93
- package/dist/chunk-7QMN4CYN.js.map +0 -1
- package/dist/chunk-FVNZB5RR.js.map +0 -1
- package/dist/command-UYTXLN3H.js.map +0 -1
- package/dist/ui/dist/assets/index-BSguLb1O.js +0 -6
- /package/dist/{chunk-72WNE2IK.js.map → chunk-UT3JLF3M.js.map} +0 -0
- /package/dist/{constants-4XH536T3.js.map → constants-GW5BAY6G.js.map} +0 -0
- /package/dist/{provider-templates-MNJZTG3Z.js.map → provider-templates-CRQJII3Z.js.map} +0 -0
|
@@ -29,8 +29,6 @@ import {
|
|
|
29
29
|
getServerMaskGatewayIds,
|
|
30
30
|
getUiDebugLogPath,
|
|
31
31
|
guiCallbackRedirectUri,
|
|
32
|
-
init_config,
|
|
33
|
-
init_paths,
|
|
34
32
|
loadPreferences,
|
|
35
33
|
loadRegistry,
|
|
36
34
|
loadServerModels,
|
|
@@ -66,23 +64,29 @@ import {
|
|
|
66
64
|
summarizeServerProviders,
|
|
67
65
|
validateCustomEndpointUrl,
|
|
68
66
|
writeSecureLogLine
|
|
69
|
-
} from "./chunk-
|
|
67
|
+
} from "./chunk-CRK6YGKY.js";
|
|
70
68
|
import {
|
|
71
69
|
BACKENDS,
|
|
72
70
|
MAX_MODEL_CATALOG
|
|
73
|
-
} from "./chunk-
|
|
71
|
+
} from "./chunk-QLHVQYQN.js";
|
|
74
72
|
import {
|
|
75
73
|
getTemplateById,
|
|
76
74
|
listSupportedTemplates,
|
|
77
75
|
listVisibleOAuthTemplates
|
|
78
|
-
} from "./chunk-
|
|
79
|
-
import "./chunk-
|
|
76
|
+
} from "./chunk-VGM6EBG4.js";
|
|
77
|
+
import "./chunk-UT3JLF3M.js";
|
|
80
78
|
|
|
81
79
|
// src/ui/command.ts
|
|
82
|
-
init_paths();
|
|
83
80
|
import { createServer } from "http";
|
|
84
81
|
import { execSync } from "child_process";
|
|
85
|
-
import {
|
|
82
|
+
import {
|
|
83
|
+
readFileSync,
|
|
84
|
+
readdirSync,
|
|
85
|
+
writeFileSync as writeFileSync2,
|
|
86
|
+
unlinkSync,
|
|
87
|
+
existsSync as existsSync3,
|
|
88
|
+
mkdirSync
|
|
89
|
+
} from "fs";
|
|
86
90
|
import { join as join2 } from "path";
|
|
87
91
|
import { fileURLToPath } from "url";
|
|
88
92
|
import { dirname } from "path";
|
|
@@ -90,7 +94,6 @@ import pc from "picocolors";
|
|
|
90
94
|
import * as p from "@clack/prompts";
|
|
91
95
|
|
|
92
96
|
// src/apps/shared/native-launcher.ts
|
|
93
|
-
init_config();
|
|
94
97
|
import { chmodSync, existsSync, mkdtempSync, writeFileSync } from "fs";
|
|
95
98
|
import { homedir } from "os";
|
|
96
99
|
import { tmpdir } from "os";
|
|
@@ -98,10 +101,38 @@ import { join } from "path";
|
|
|
98
101
|
var isWindows = process.platform === "win32";
|
|
99
102
|
var isMac = process.platform === "darwin";
|
|
100
103
|
var SUPPORTED_APPS = [
|
|
101
|
-
{
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
104
|
+
{
|
|
105
|
+
id: "claude",
|
|
106
|
+
name: "Claude Code CLI",
|
|
107
|
+
type: "cli",
|
|
108
|
+
detectId: "claude",
|
|
109
|
+
gatewayCommand: "claude",
|
|
110
|
+
installHint: "npm install -g @anthropic-ai/claude-code"
|
|
111
|
+
},
|
|
112
|
+
{
|
|
113
|
+
id: "codex",
|
|
114
|
+
name: "Codex CLI",
|
|
115
|
+
type: "cli",
|
|
116
|
+
detectId: "codex",
|
|
117
|
+
gatewayCommand: "codex",
|
|
118
|
+
installHint: "npm install -g @openai/codex"
|
|
119
|
+
},
|
|
120
|
+
{
|
|
121
|
+
id: "gemini",
|
|
122
|
+
name: "Gemini CLI",
|
|
123
|
+
type: "cli",
|
|
124
|
+
detectId: "gemini",
|
|
125
|
+
gatewayCommand: "gemini",
|
|
126
|
+
installHint: "npm install -g @google/gemini-cli"
|
|
127
|
+
},
|
|
128
|
+
{
|
|
129
|
+
id: "agy",
|
|
130
|
+
name: "Antigravity CLI",
|
|
131
|
+
type: "cli",
|
|
132
|
+
detectId: "agy",
|
|
133
|
+
gatewayCommand: "agy",
|
|
134
|
+
installHint: "npm install -g @google/antigravity-cli"
|
|
135
|
+
},
|
|
105
136
|
{
|
|
106
137
|
id: "antigravity",
|
|
107
138
|
name: "Antigravity (App)",
|
|
@@ -142,30 +173,21 @@ function fallbackPathsForApp(id, platform = process.platform) {
|
|
|
142
173
|
const localAppData = process.env["LOCALAPPDATA"] ?? join(homedir(), "AppData", "Local");
|
|
143
174
|
switch (id) {
|
|
144
175
|
case "claude":
|
|
145
|
-
return windows ? [
|
|
146
|
-
join(appData, "npm", "claude.cmd"),
|
|
147
|
-
join(appData, "npm", "claude")
|
|
148
|
-
] : [
|
|
176
|
+
return windows ? [join(appData, "npm", "claude.cmd"), join(appData, "npm", "claude")] : [
|
|
149
177
|
join(homedir(), ".local", "bin", "claude"),
|
|
150
178
|
join(homedir(), ".npm", "bin", "claude"),
|
|
151
179
|
"/usr/local/bin/claude",
|
|
152
180
|
"/opt/homebrew/bin/claude"
|
|
153
181
|
];
|
|
154
182
|
case "codex":
|
|
155
|
-
return windows ? [
|
|
156
|
-
join(appData, "npm", "codex.cmd"),
|
|
157
|
-
join(appData, "npm", "codex")
|
|
158
|
-
] : [
|
|
183
|
+
return windows ? [join(appData, "npm", "codex.cmd"), join(appData, "npm", "codex")] : [
|
|
159
184
|
join(homedir(), ".local", "bin", "codex"),
|
|
160
185
|
join(homedir(), ".npm", "bin", "codex"),
|
|
161
186
|
"/usr/local/bin/codex",
|
|
162
187
|
"/opt/homebrew/bin/codex"
|
|
163
188
|
];
|
|
164
189
|
case "gemini":
|
|
165
|
-
return windows ? [
|
|
166
|
-
join(appData, "npm", "gemini.cmd"),
|
|
167
|
-
join(appData, "npm", "gemini")
|
|
168
|
-
] : [
|
|
190
|
+
return windows ? [join(appData, "npm", "gemini.cmd"), join(appData, "npm", "gemini")] : [
|
|
169
191
|
join(homedir(), ".local", "bin", "gemini"),
|
|
170
192
|
join(homedir(), ".npm", "bin", "gemini"),
|
|
171
193
|
"/usr/local/bin/gemini",
|
|
@@ -186,7 +208,16 @@ function fallbackPathsForApp(id, platform = process.platform) {
|
|
|
186
208
|
if (mac) {
|
|
187
209
|
return [
|
|
188
210
|
"/Applications/Antigravity IDE.app/Contents/Resources/app/bin/antigravity-ide",
|
|
189
|
-
join(
|
|
211
|
+
join(
|
|
212
|
+
homedir(),
|
|
213
|
+
"Applications",
|
|
214
|
+
"Antigravity IDE.app",
|
|
215
|
+
"Contents",
|
|
216
|
+
"Resources",
|
|
217
|
+
"app",
|
|
218
|
+
"bin",
|
|
219
|
+
"antigravity-ide"
|
|
220
|
+
)
|
|
190
221
|
];
|
|
191
222
|
}
|
|
192
223
|
if (windows) {
|
|
@@ -205,15 +236,9 @@ function fallbackPathsForApp(id, platform = process.platform) {
|
|
|
205
236
|
];
|
|
206
237
|
}
|
|
207
238
|
if (windows) {
|
|
208
|
-
return [
|
|
209
|
-
join(localAppData, "Programs", "Antigravity", "Antigravity.exe")
|
|
210
|
-
];
|
|
239
|
+
return [join(localAppData, "Programs", "Antigravity", "Antigravity.exe")];
|
|
211
240
|
}
|
|
212
|
-
return [
|
|
213
|
-
"/opt/antigravity/antigravity",
|
|
214
|
-
"/usr/local/bin/antigravity",
|
|
215
|
-
"/usr/bin/antigravity"
|
|
216
|
-
];
|
|
241
|
+
return ["/opt/antigravity/antigravity", "/usr/local/bin/antigravity", "/usr/bin/antigravity"];
|
|
217
242
|
case "claude-app":
|
|
218
243
|
if (mac) {
|
|
219
244
|
return [
|
|
@@ -278,19 +303,23 @@ function getTerminalLaunchCommand(binPath, args, opts = {}) {
|
|
|
278
303
|
const dir2 = mkdtempSync(join(tmpdir(), "anygate-launch-"));
|
|
279
304
|
const scriptPath2 = join(dir2, "launch.command");
|
|
280
305
|
const displayCommand = opts.displayCommand ?? [binPath, ...args].join(" ");
|
|
281
|
-
writeFileSync(
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
306
|
+
writeFileSync(
|
|
307
|
+
scriptPath2,
|
|
308
|
+
[
|
|
309
|
+
"#!/bin/sh",
|
|
310
|
+
`trap 'rm -f "$0"; rmdir "$(dirname "$0")" 2>/dev/null' EXIT`,
|
|
311
|
+
"clear",
|
|
312
|
+
opts.cwd ? `cd ${quoteShellArg(opts.cwd)} || exit 1` : "",
|
|
313
|
+
`printf '%s\\n\\n' ${quoteShellArg(`$ ${displayCommand}`)}`,
|
|
314
|
+
fullCmd,
|
|
315
|
+
"status=$?",
|
|
316
|
+
'printf "\\nanygate session exited with code %s. Press Return to close this window. " "$status"',
|
|
317
|
+
"read _",
|
|
318
|
+
'exit "$status"',
|
|
319
|
+
""
|
|
320
|
+
].join("\n"),
|
|
321
|
+
{ encoding: "utf8", mode: 448 }
|
|
322
|
+
);
|
|
294
323
|
chmodSync(scriptPath2, 448);
|
|
295
324
|
return `open -a Terminal ${quoteShellArg(scriptPath2)}`;
|
|
296
325
|
}
|
|
@@ -300,12 +329,10 @@ function getTerminalLaunchCommand(binPath, args, opts = {}) {
|
|
|
300
329
|
}
|
|
301
330
|
const dir = mkdtempSync(join(tmpdir(), "anygate-launch-"));
|
|
302
331
|
const scriptPath = join(dir, "launch.sh");
|
|
303
|
-
writeFileSync(scriptPath, [
|
|
304
|
-
"
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
""
|
|
308
|
-
].join("\n"), { encoding: "utf8", mode: 448 });
|
|
332
|
+
writeFileSync(scriptPath, ["#!/bin/sh", runCmd, "exec sh", ""].join("\n"), {
|
|
333
|
+
encoding: "utf8",
|
|
334
|
+
mode: 448
|
|
335
|
+
});
|
|
309
336
|
chmodSync(scriptPath, 448);
|
|
310
337
|
const scriptArg = quoteShellArg(scriptPath);
|
|
311
338
|
return `x-terminal-emulator -e sh ${scriptArg} || gnome-terminal -- sh ${scriptArg} || xterm -e sh ${scriptArg}`;
|
|
@@ -355,21 +382,20 @@ function getSupportedApps() {
|
|
|
355
382
|
}
|
|
356
383
|
|
|
357
384
|
// src/ui/api.ts
|
|
358
|
-
init_config();
|
|
359
385
|
import { exec } from "child_process";
|
|
360
386
|
import { promisify } from "util";
|
|
361
387
|
import { existsSync as existsSync2, statSync } from "fs";
|
|
362
388
|
import { randomUUID } from "crypto";
|
|
363
389
|
|
|
364
390
|
// src/ui/server-control.ts
|
|
365
|
-
init_config();
|
|
366
391
|
var running = null;
|
|
367
392
|
var startInFlight = null;
|
|
368
393
|
var SAVED_PASSWORD_CACHE_TTL_MS = 3e4;
|
|
369
394
|
var hasSavedPasswordCache = null;
|
|
370
395
|
async function hasSavedPasswordCached() {
|
|
371
396
|
const now = Date.now();
|
|
372
|
-
if (hasSavedPasswordCache && hasSavedPasswordCache.expiresAt > now)
|
|
397
|
+
if (hasSavedPasswordCache && hasSavedPasswordCache.expiresAt > now)
|
|
398
|
+
return hasSavedPasswordCache.value;
|
|
373
399
|
const value = Boolean(await getSavedServerPassword());
|
|
374
400
|
hasSavedPasswordCache = { value, expiresAt: now + SAVED_PASSWORD_CACHE_TTL_MS };
|
|
375
401
|
return value;
|
|
@@ -384,9 +410,12 @@ function buildModelRows(models, gateway) {
|
|
|
384
410
|
}
|
|
385
411
|
const rows = [];
|
|
386
412
|
for (const [providerLabel, groupModels] of groups) {
|
|
387
|
-
for (const row of buildDedupedModelRows(groupModels, gateway))
|
|
413
|
+
for (const row of buildDedupedModelRows(groupModels, gateway))
|
|
414
|
+
rows.push({ providerLabel, ...row });
|
|
388
415
|
}
|
|
389
|
-
return rows.sort(
|
|
416
|
+
return rows.sort(
|
|
417
|
+
(a, b) => a.providerLabel.localeCompare(b.providerLabel) || a.name.localeCompare(b.name)
|
|
418
|
+
);
|
|
390
419
|
}
|
|
391
420
|
async function buildSavedConfig() {
|
|
392
421
|
return {
|
|
@@ -416,11 +445,13 @@ async function getServerStatus() {
|
|
|
416
445
|
models: modelRows
|
|
417
446
|
};
|
|
418
447
|
if (config.listenMode === "network") {
|
|
419
|
-
payload.networkUrls = getLocalIps().map(
|
|
420
|
-
name,
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
448
|
+
payload.networkUrls = getLocalIps().map(
|
|
449
|
+
({ name, address }) => ({
|
|
450
|
+
name,
|
|
451
|
+
anthropicUrl: `http://${address}:${handle.port}/anthropic`,
|
|
452
|
+
openaiUrl: `http://${address}:${handle.port}/openai/v1`
|
|
453
|
+
})
|
|
454
|
+
);
|
|
424
455
|
payload.apiKey = serverPassword ?? void 0;
|
|
425
456
|
} else {
|
|
426
457
|
payload.apiKey = "any non-empty value";
|
|
@@ -428,7 +459,8 @@ async function getServerStatus() {
|
|
|
428
459
|
return payload;
|
|
429
460
|
}
|
|
430
461
|
function startGatewayServer(req) {
|
|
431
|
-
if (running)
|
|
462
|
+
if (running)
|
|
463
|
+
return Promise.resolve({ ok: false, error: "Server is already running. Stop it first." });
|
|
432
464
|
if (startInFlight) return startInFlight;
|
|
433
465
|
startInFlight = doStartGatewayServer(req).finally(() => {
|
|
434
466
|
startInFlight = null;
|
|
@@ -441,7 +473,10 @@ async function doStartGatewayServer(req) {
|
|
|
441
473
|
}
|
|
442
474
|
const apiKey = await resolveServerUpstreamApiKey();
|
|
443
475
|
if (!apiKey) {
|
|
444
|
-
return {
|
|
476
|
+
return {
|
|
477
|
+
ok: false,
|
|
478
|
+
error: "No providers configured. Add a provider in Providers & Keys first."
|
|
479
|
+
};
|
|
445
480
|
}
|
|
446
481
|
let serverPassword = null;
|
|
447
482
|
if (req.listenMode === "network") {
|
|
@@ -463,13 +498,19 @@ async function doStartGatewayServer(req) {
|
|
|
463
498
|
try {
|
|
464
499
|
models = await loadServerModels();
|
|
465
500
|
} catch (err) {
|
|
466
|
-
return {
|
|
501
|
+
return {
|
|
502
|
+
ok: false,
|
|
503
|
+
error: `Failed to load models: ${err instanceof Error ? err.message : String(err)}`
|
|
504
|
+
};
|
|
467
505
|
}
|
|
468
506
|
if (req.exposedProviders) models = filterServerModelsByProviders(models, req.exposedProviders);
|
|
469
507
|
if (req.favoritesOnly) {
|
|
470
508
|
const favorites = loadPreferences().favoriteModels ?? [];
|
|
471
509
|
if (favorites.length === 0) {
|
|
472
|
-
return {
|
|
510
|
+
return {
|
|
511
|
+
ok: false,
|
|
512
|
+
error: "No favorite models configured. Add favorites in the Favorites tab first."
|
|
513
|
+
};
|
|
473
514
|
}
|
|
474
515
|
models = filterServerModelsByFavorites(models, favorites).slice(0, MAX_MODEL_CATALOG);
|
|
475
516
|
if (models.length === 0) {
|
|
@@ -483,7 +524,10 @@ async function doStartGatewayServer(req) {
|
|
|
483
524
|
}
|
|
484
525
|
}
|
|
485
526
|
if (models.length === 0) {
|
|
486
|
-
return {
|
|
527
|
+
return {
|
|
528
|
+
ok: false,
|
|
529
|
+
error: "No models to expose. Add providers or adjust the exposed-provider filter."
|
|
530
|
+
};
|
|
487
531
|
}
|
|
488
532
|
setServerFavoritesOnly(req.favoritesOnly);
|
|
489
533
|
setServerFreeModelsOnly(req.freeModelsOnly);
|
|
@@ -650,7 +694,8 @@ async function handlePostConfig(req, res) {
|
|
|
650
694
|
const body = JSON.parse(await readBody(req));
|
|
651
695
|
const update = {};
|
|
652
696
|
if (Array.isArray(body.favoriteModels)) update.favoriteModels = body.favoriteModels;
|
|
653
|
-
if (Array.isArray(body.antigravityCliFavoriteModels))
|
|
697
|
+
if (Array.isArray(body.antigravityCliFavoriteModels))
|
|
698
|
+
update.antigravityCliFavoriteModels = body.antigravityCliFavoriteModels;
|
|
654
699
|
if (Object.keys(update).length > 0) savePreferences(update);
|
|
655
700
|
sendJson(res, 200, { ok: true });
|
|
656
701
|
} catch (err) {
|
|
@@ -671,7 +716,9 @@ async function handleGetModels(res) {
|
|
|
671
716
|
try {
|
|
672
717
|
const catalog = await fetchModelsWithTimeout();
|
|
673
718
|
const registry = loadRegistry();
|
|
674
|
-
const rawCountById = new Map(
|
|
719
|
+
const rawCountById = new Map(
|
|
720
|
+
registry.providers.map((p2) => [p2.id, p2.modelsCache?.models.length ?? 0])
|
|
721
|
+
);
|
|
675
722
|
const providers = catalog.map((p2) => ({
|
|
676
723
|
id: p2.id,
|
|
677
724
|
name: p2.name,
|
|
@@ -692,6 +739,7 @@ async function handleGetModels(res) {
|
|
|
692
739
|
freeLabel: freeStatusLabel(m.freeStatus),
|
|
693
740
|
contextWindow: m.contextWindow,
|
|
694
741
|
cost: m.cost,
|
|
742
|
+
providerId: p2.id,
|
|
695
743
|
inputTypes: resolveInputTypes(m.family, p2.id, m.id)
|
|
696
744
|
}))
|
|
697
745
|
}));
|
|
@@ -703,7 +751,11 @@ async function handleGetModels(res) {
|
|
|
703
751
|
providers.push({
|
|
704
752
|
id: rp.id,
|
|
705
753
|
name: rp.name,
|
|
706
|
-
favoriteName: favoriteProviderDisplayName({
|
|
754
|
+
favoriteName: favoriteProviderDisplayName({
|
|
755
|
+
id: rp.id,
|
|
756
|
+
name: rp.name,
|
|
757
|
+
authType: rp.authType
|
|
758
|
+
}),
|
|
707
759
|
hasKey: true,
|
|
708
760
|
freeAccess: false,
|
|
709
761
|
authType: "oauth",
|
|
@@ -1029,8 +1081,20 @@ async function handlePostKeys(req, res) {
|
|
|
1029
1081
|
}
|
|
1030
1082
|
}
|
|
1031
1083
|
var CUSTOM_TEMPLATES = [
|
|
1032
|
-
{
|
|
1033
|
-
|
|
1084
|
+
{
|
|
1085
|
+
id: "__custom_openai__",
|
|
1086
|
+
name: "Custom OpenAI-compatible",
|
|
1087
|
+
signupUrl: null,
|
|
1088
|
+
authType: "api",
|
|
1089
|
+
custom: true
|
|
1090
|
+
},
|
|
1091
|
+
{
|
|
1092
|
+
id: "__custom_anthropic__",
|
|
1093
|
+
name: "Custom Anthropic-compatible",
|
|
1094
|
+
signupUrl: null,
|
|
1095
|
+
authType: "api",
|
|
1096
|
+
custom: true
|
|
1097
|
+
}
|
|
1034
1098
|
];
|
|
1035
1099
|
function handleGetTemplates(res) {
|
|
1036
1100
|
const registry = loadRegistry();
|
|
@@ -1039,6 +1103,7 @@ function handleGetTemplates(res) {
|
|
|
1039
1103
|
id: t.id,
|
|
1040
1104
|
name: t.name,
|
|
1041
1105
|
signupUrl: t.signupUrl ?? null,
|
|
1106
|
+
signupNote: t.signupNote ?? null,
|
|
1042
1107
|
authType: t.authType,
|
|
1043
1108
|
anonymousFreeModels: t.anonymousFreeModels ?? false,
|
|
1044
1109
|
urlPrompt: t.urlPrompt ?? null,
|
|
@@ -1097,7 +1162,7 @@ async function handleAddProvider(req, res) {
|
|
|
1097
1162
|
sendJson(res, 400, { error: "templateId required" });
|
|
1098
1163
|
return;
|
|
1099
1164
|
}
|
|
1100
|
-
const { listSupportedTemplates: listSupportedTemplates2 } = await import("./provider-templates-
|
|
1165
|
+
const { listSupportedTemplates: listSupportedTemplates2 } = await import("./provider-templates-CRQJII3Z.js");
|
|
1101
1166
|
const template = listSupportedTemplates2().find((t) => t.id === templateId);
|
|
1102
1167
|
if (!template) {
|
|
1103
1168
|
sendJson(res, 404, { error: `Template '${templateId}' not found` });
|
|
@@ -1117,13 +1182,17 @@ async function handleAddProvider(req, res) {
|
|
|
1117
1182
|
return;
|
|
1118
1183
|
}
|
|
1119
1184
|
const usesHttp = /^http:\/\//i.test(baseUrlOverride);
|
|
1120
|
-
const valid = await validateCustomEndpointUrl(baseUrlOverride, {
|
|
1185
|
+
const valid = await validateCustomEndpointUrl(baseUrlOverride, {
|
|
1186
|
+
allowInsecureLocal: usesHttp
|
|
1187
|
+
});
|
|
1121
1188
|
if (!valid.ok) {
|
|
1122
1189
|
sendJson(res, 400, { error: valid.error ?? "Invalid URL", hint: valid.hint });
|
|
1123
1190
|
return;
|
|
1124
1191
|
}
|
|
1125
1192
|
}
|
|
1126
|
-
const result = await addProviderFromTemplate(template, keyText, {
|
|
1193
|
+
const result = await addProviderFromTemplate(template, keyText, {
|
|
1194
|
+
baseUrl: baseUrlOverride
|
|
1195
|
+
});
|
|
1127
1196
|
if (result.added) {
|
|
1128
1197
|
sendJson(res, 200, { ok: true, name: template.name, count: result.modelCount ?? 0 });
|
|
1129
1198
|
} else {
|
|
@@ -1151,7 +1220,11 @@ async function handleRefreshAll(res) {
|
|
|
1151
1220
|
reason: r.reason
|
|
1152
1221
|
};
|
|
1153
1222
|
});
|
|
1154
|
-
sendJson(res, 200, {
|
|
1223
|
+
sendJson(res, 200, {
|
|
1224
|
+
ok: true,
|
|
1225
|
+
providers: summary,
|
|
1226
|
+
total: summary.reduce((n, p2) => n + p2.count, 0)
|
|
1227
|
+
});
|
|
1155
1228
|
} catch (err) {
|
|
1156
1229
|
sendJson(res, 500, { ok: false, error: String(err) });
|
|
1157
1230
|
}
|
|
@@ -1214,14 +1287,21 @@ async function handleOAuthStart(req, res) {
|
|
|
1214
1287
|
const body = JSON.parse(await readBody(req));
|
|
1215
1288
|
const { providerId } = body;
|
|
1216
1289
|
if (!providerId || !NATIVE_OAUTH_PROVIDER_IDS.has(providerId)) {
|
|
1217
|
-
sendJson(res, 400, {
|
|
1290
|
+
sendJson(res, 400, {
|
|
1291
|
+
error: `providerId must be one of: ${[...NATIVE_OAUTH_PROVIDER_IDS].join(", ")}`
|
|
1292
|
+
});
|
|
1218
1293
|
return;
|
|
1219
1294
|
}
|
|
1220
1295
|
const sessionId = randomUUID();
|
|
1221
1296
|
if (providerId === "xai-oauth") {
|
|
1222
1297
|
const device2 = await requestXaiDeviceCode();
|
|
1223
1298
|
const url2 = device2.verification_uri_complete ?? device2.verification_uri;
|
|
1224
|
-
const session2 = {
|
|
1299
|
+
const session2 = {
|
|
1300
|
+
status: "pending",
|
|
1301
|
+
url: url2,
|
|
1302
|
+
userCode: device2.user_code,
|
|
1303
|
+
providerId
|
|
1304
|
+
};
|
|
1225
1305
|
oauthSessions.set(sessionId, session2);
|
|
1226
1306
|
pollXaiDeviceCodeToken(device2).then(async (tokens) => {
|
|
1227
1307
|
await saveNativeOAuthCredential(providerId, tokens);
|
|
@@ -1236,7 +1316,12 @@ async function handleOAuthStart(req, res) {
|
|
|
1236
1316
|
if (providerId === "github-copilot") {
|
|
1237
1317
|
const device2 = await requestGithubDeviceCode();
|
|
1238
1318
|
const url2 = device2.verification_uri;
|
|
1239
|
-
const session2 = {
|
|
1319
|
+
const session2 = {
|
|
1320
|
+
status: "pending",
|
|
1321
|
+
url: url2,
|
|
1322
|
+
userCode: device2.user_code,
|
|
1323
|
+
providerId
|
|
1324
|
+
};
|
|
1240
1325
|
oauthSessions.set(sessionId, session2);
|
|
1241
1326
|
pollGithubDeviceCodeToken(device2).then(async (tokens) => {
|
|
1242
1327
|
await saveNativeOAuthCredential(providerId, tokens);
|
|
@@ -1404,7 +1489,9 @@ async function handleLaunchApp(req, res, opts) {
|
|
|
1404
1489
|
return;
|
|
1405
1490
|
}
|
|
1406
1491
|
if (!favorites && (providerId || modelId) && (!providerId || !modelId)) {
|
|
1407
|
-
sendJson(res, 400, {
|
|
1492
|
+
sendJson(res, 400, {
|
|
1493
|
+
error: "Both providerId and modelId are required to launch a specific anygate model."
|
|
1494
|
+
});
|
|
1408
1495
|
return;
|
|
1409
1496
|
}
|
|
1410
1497
|
const fullCatalog = Boolean(favoritesCatalog);
|
|
@@ -1463,7 +1550,9 @@ async function handleSetAppPath(req, res) {
|
|
|
1463
1550
|
return;
|
|
1464
1551
|
}
|
|
1465
1552
|
if (path !== null && (typeof path !== "string" || !path.trim())) {
|
|
1466
|
-
sendJson(res, 400, {
|
|
1553
|
+
sendJson(res, 400, {
|
|
1554
|
+
error: "path must be a non-empty string, or null to clear the override."
|
|
1555
|
+
});
|
|
1467
1556
|
return;
|
|
1468
1557
|
}
|
|
1469
1558
|
const trimmed = typeof path === "string" ? path.trim() : null;
|
|
@@ -1594,12 +1683,16 @@ async function handleBrowseFolder(res) {
|
|
|
1594
1683
|
const { stdout } = await execAsync(`powershell -NoProfile -Sta -EncodedCommand ${encoded}`);
|
|
1595
1684
|
resultPath = stdout.trim();
|
|
1596
1685
|
} catch (err) {
|
|
1597
|
-
sendJson(res, 500, {
|
|
1686
|
+
sendJson(res, 500, {
|
|
1687
|
+
error: `Failed to open folder picker: ${err instanceof Error ? err.message : String(err)}`
|
|
1688
|
+
});
|
|
1598
1689
|
return;
|
|
1599
1690
|
}
|
|
1600
1691
|
} else {
|
|
1601
1692
|
try {
|
|
1602
|
-
const { stdout } = await execAsync(
|
|
1693
|
+
const { stdout } = await execAsync(
|
|
1694
|
+
'zenity --file-selection --directory --title="Select launch folder"'
|
|
1695
|
+
);
|
|
1603
1696
|
resultPath = stdout.trim();
|
|
1604
1697
|
} catch {
|
|
1605
1698
|
try {
|
|
@@ -1678,7 +1771,10 @@ function checkExistingServer() {
|
|
|
1678
1771
|
let processExists = false;
|
|
1679
1772
|
if (isWindows2) {
|
|
1680
1773
|
try {
|
|
1681
|
-
const output = execSync(`tasklist /FI "PID eq ${pid}"`, {
|
|
1774
|
+
const output = execSync(`tasklist /FI "PID eq ${pid}"`, {
|
|
1775
|
+
encoding: "utf8",
|
|
1776
|
+
stdio: ["pipe", "pipe", "ignore"]
|
|
1777
|
+
});
|
|
1682
1778
|
processExists = output.includes(String(pid));
|
|
1683
1779
|
} catch {
|
|
1684
1780
|
processExists = false;
|
|
@@ -1795,10 +1891,12 @@ async function runUiCommand(opts = {}) {
|
|
|
1795
1891
|
process.on("SIGTERM", () => {
|
|
1796
1892
|
void handleSignal("SIGTERM");
|
|
1797
1893
|
});
|
|
1798
|
-
console.log(
|
|
1894
|
+
console.log(
|
|
1895
|
+
`
|
|
1799
1896
|
${pc.bold("anygate UI")} ${pc.cyan(url)}
|
|
1800
1897
|
${pc.dim("Press Ctrl+C to stop")}
|
|
1801
|
-
`
|
|
1898
|
+
`
|
|
1899
|
+
);
|
|
1802
1900
|
if (traceLogPath) {
|
|
1803
1901
|
console.log(` ${pc.dim(`Trace log: ${traceLogPath}`)}
|
|
1804
1902
|
`);
|
|
@@ -1821,4 +1919,4 @@ export {
|
|
|
1821
1919
|
resolveUiShutdownDecision,
|
|
1822
1920
|
runUiCommand
|
|
1823
1921
|
};
|
|
1824
|
-
//# sourceMappingURL=command-
|
|
1922
|
+
//# sourceMappingURL=command-PFFQI5YC.js.map
|