@vantaloom/runtime-win32-x64 0.3.0 → 0.4.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/VERSION +1 -1
- package/bin/easytier-cli.exe +0 -0
- package/bin/easytier-core.exe +0 -0
- package/bin/vantaloom-agent.exe +0 -0
- package/bin/vantaloom-api.exe +0 -0
- package/bin/vantaloom-tray.exe +0 -0
- package/bin/vantaloomctl.exe +0 -0
- package/bin/wintun.dll +0 -0
- package/cli/package.json +1 -1
- package/cli/src/cli.mjs +344 -23
- package/manifest.json +2 -2
- package/package.json +1 -1
- package/web/404.html +1 -1
- package/web/__next.__PAGE__.txt +2 -2
- package/web/__next._full.txt +3 -3
- package/web/__next._head.txt +1 -1
- package/web/__next._index.txt +2 -2
- package/web/__next._tree.txt +2 -2
- package/web/_next/static/chunks/73d2c788f1076e9a.css +2 -0
- package/web/_next/static/chunks/80b4a364458ec11d.js +52 -0
- package/web/_not-found/__next._full.txt +2 -2
- package/web/_not-found/__next._head.txt +1 -1
- package/web/_not-found/__next._index.txt +2 -2
- package/web/_not-found/__next._not-found/__PAGE__.txt +1 -1
- package/web/_not-found/__next._not-found.txt +1 -1
- package/web/_not-found/__next._tree.txt +2 -2
- package/web/_not-found.html +1 -1
- package/web/_not-found.txt +2 -2
- package/web/index.html +1 -1
- package/web/index.txt +3 -3
- package/web/_next/static/chunks/142a2ac944b17c0d.js +0 -52
- package/web/_next/static/chunks/afcc024bee6626a3.css +0 -2
- /package/web/_next/static/{NAZHZ_h1mU5v6lVYZ5tUw → E6VnJNHPIVhiQoKxBWUU2}/_buildManifest.js +0 -0
- /package/web/_next/static/{NAZHZ_h1mU5v6lVYZ5tUw → E6VnJNHPIVhiQoKxBWUU2}/_clientMiddlewareManifest.json +0 -0
- /package/web/_next/static/{NAZHZ_h1mU5v6lVYZ5tUw → E6VnJNHPIVhiQoKxBWUU2}/_ssgManifest.js +0 -0
package/VERSION
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
532507a
|
|
Binary file
|
|
Binary file
|
package/bin/vantaloom-agent.exe
CHANGED
|
Binary file
|
package/bin/vantaloom-api.exe
CHANGED
|
Binary file
|
package/bin/vantaloom-tray.exe
CHANGED
|
Binary file
|
package/bin/vantaloomctl.exe
CHANGED
|
Binary file
|
package/bin/wintun.dll
ADDED
|
Binary file
|
package/cli/package.json
CHANGED
package/cli/src/cli.mjs
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { execFileSync, spawnSync } from "node:child_process"
|
|
2
2
|
import {
|
|
3
|
+
appendFileSync,
|
|
3
4
|
chmodSync,
|
|
4
5
|
existsSync,
|
|
5
6
|
mkdirSync,
|
|
@@ -20,11 +21,45 @@ const installedConfigPath = path.join(cliRoot, "config.json")
|
|
|
20
21
|
const defaultReleaseTag = "runtime-latest"
|
|
21
22
|
const defaultRepo = "Timefiles404/Vantaloom-next"
|
|
22
23
|
const defaultNpmRegistry = "https://registry.npmjs.org"
|
|
24
|
+
const fallbackNpmRegistries = [
|
|
25
|
+
"https://registry.npmmirror.com",
|
|
26
|
+
]
|
|
27
|
+
|
|
28
|
+
// Inherit strict-ssl=false from npm/npx config, or respect NODE_TLS_REJECT_UNAUTHORIZED.
|
|
29
|
+
// When npm runs us via npx with strict-ssl disabled, it sets npm_config_strict_ssl="false".
|
|
30
|
+
// Also check user .npmrc for strict-ssl=false (common in China behind proxies).
|
|
31
|
+
function shouldDisableTLS() {
|
|
32
|
+
if (process.env.NODE_TLS_REJECT_UNAUTHORIZED === "0") return true
|
|
33
|
+
if (process.env.npm_config_strict_ssl === "false") return true
|
|
34
|
+
if (process.env.npm_config_strict_ssl === "") return true
|
|
35
|
+
try {
|
|
36
|
+
const npmrcPath = path.join(os.homedir(), ".npmrc")
|
|
37
|
+
if (existsSync(npmrcPath)) {
|
|
38
|
+
const content = readFileSync(npmrcPath, "utf8")
|
|
39
|
+
if (/^\s*strict-ssl\s*=\s*false/m.test(content)) return true
|
|
40
|
+
}
|
|
41
|
+
} catch {}
|
|
42
|
+
return false
|
|
43
|
+
}
|
|
44
|
+
if (shouldDisableTLS()) {
|
|
45
|
+
process.env.NODE_TLS_REJECT_UNAUTHORIZED = "0"
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
const cliVersion = readJSONIfExists(path.join(cliRoot, "package.json")).version ?? "unknown"
|
|
23
49
|
|
|
24
50
|
export async function main(argv) {
|
|
25
51
|
const command = argv[0] ?? "help"
|
|
26
52
|
const options = parseOptions(argv.slice(1))
|
|
27
53
|
|
|
54
|
+
// --no-strict-ssl flag disables TLS certificate verification for fetch calls
|
|
55
|
+
if (options.noStrictSsl) {
|
|
56
|
+
process.env.NODE_TLS_REJECT_UNAUTHORIZED = "0"
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
if (command === "install" || command === "update") {
|
|
60
|
+
console.log(`vantaloom-cli v${cliVersion} (${platformId()})`)
|
|
61
|
+
}
|
|
62
|
+
|
|
28
63
|
switch (command) {
|
|
29
64
|
case "install":
|
|
30
65
|
if (options.package) {
|
|
@@ -91,6 +126,7 @@ async function installFromSource(options) {
|
|
|
91
126
|
|
|
92
127
|
console.log(`${options.update ? "updated" : "installed"} Vantaloom: ${prefix}`)
|
|
93
128
|
console.log(`version: ${version}`)
|
|
129
|
+
ensureInPath(prefix)
|
|
94
130
|
console.log(`run: ${displayCommand(prefix)} status`)
|
|
95
131
|
}
|
|
96
132
|
|
|
@@ -104,6 +140,7 @@ async function installFromPackage(options) {
|
|
|
104
140
|
|
|
105
141
|
console.log(`${options.update ? "updated" : "installed"} Vantaloom: ${prefix}`)
|
|
106
142
|
console.log(`version: ${version}`)
|
|
143
|
+
ensureInPath(prefix)
|
|
107
144
|
console.log(`run: ${displayCommand(prefix)} status`)
|
|
108
145
|
}
|
|
109
146
|
|
|
@@ -159,6 +196,9 @@ async function buildRuntimePackage(sourceRoot, packageRoot, options) {
|
|
|
159
196
|
} catch { /* optional: skip if systray build fails */ }
|
|
160
197
|
}
|
|
161
198
|
|
|
199
|
+
// Bundle the EasyTier mesh binaries (P2P virtual network) for the target platform.
|
|
200
|
+
await copyEasyTier(sourceRoot, buildBin, platform)
|
|
201
|
+
|
|
162
202
|
if (options.buildWeb) {
|
|
163
203
|
runPnpm(["--filter", "vantaloom-app", "build"], { cwd: sourceRoot })
|
|
164
204
|
}
|
|
@@ -170,6 +210,41 @@ async function buildRuntimePackage(sourceRoot, packageRoot, options) {
|
|
|
170
210
|
return { platform, version }
|
|
171
211
|
}
|
|
172
212
|
|
|
213
|
+
// copyEasyTier bundles the vendored EasyTier binaries (easytier-core/easytier-cli,
|
|
214
|
+
// plus wintun.dll on Windows) for the target platform into the package bin/ dir.
|
|
215
|
+
async function copyEasyTier(sourceRoot, buildBin, platform) {
|
|
216
|
+
const vendorMap = {
|
|
217
|
+
"win32-x64": "windows-x86_64",
|
|
218
|
+
"darwin-arm64": "macos-aarch64",
|
|
219
|
+
"linux-x64": "linux-x86_64",
|
|
220
|
+
}
|
|
221
|
+
const vendorName = vendorMap[platform]
|
|
222
|
+
if (!vendorName) {
|
|
223
|
+
console.warn(` warning: no EasyTier mapping for ${platform}; mesh disabled for this platform`)
|
|
224
|
+
return
|
|
225
|
+
}
|
|
226
|
+
const srcDir = path.join(sourceRoot, "vendor", "easytier", vendorName, `easytier-${vendorName}`)
|
|
227
|
+
if (!existsSync(srcDir)) {
|
|
228
|
+
console.warn(` warning: EasyTier binaries not found at ${srcDir}; run vendor download first`)
|
|
229
|
+
return
|
|
230
|
+
}
|
|
231
|
+
const isWin = platform.startsWith("win32")
|
|
232
|
+
const files = isWin
|
|
233
|
+
? ["easytier-core.exe", "easytier-cli.exe", "wintun.dll"]
|
|
234
|
+
: ["easytier-core", "easytier-cli"]
|
|
235
|
+
let copied = 0
|
|
236
|
+
for (const f of files) {
|
|
237
|
+
const src = path.join(srcDir, f)
|
|
238
|
+
if (!existsSync(src)) {
|
|
239
|
+
console.warn(` warning: EasyTier file missing: ${f}`)
|
|
240
|
+
continue
|
|
241
|
+
}
|
|
242
|
+
await cp(src, path.join(buildBin, f), { force: true })
|
|
243
|
+
copied++
|
|
244
|
+
}
|
|
245
|
+
console.log(` bundled EasyTier ${vendorName} (${copied} files)`)
|
|
246
|
+
}
|
|
247
|
+
|
|
173
248
|
async function applyPackage(packageRoot, prefix, options) {
|
|
174
249
|
assertRuntimePackage(packageRoot)
|
|
175
250
|
|
|
@@ -186,15 +261,49 @@ async function applyPackage(packageRoot, prefix, options) {
|
|
|
186
261
|
spawnSync(existingCtl, ["stop", "--prefix", prefix], { stdio: "inherit" })
|
|
187
262
|
}
|
|
188
263
|
|
|
264
|
+
// Kill lingering tray process that may hold locks on bin/ (older versions
|
|
265
|
+
// don't write tray.pid, so vantaloomctl stop won't find them).
|
|
266
|
+
killTrayProcess(prefix)
|
|
267
|
+
|
|
268
|
+
// Copy package contents to install prefix
|
|
189
269
|
for (const name of ["bin", "web", "cli"]) {
|
|
190
|
-
|
|
191
|
-
|
|
270
|
+
const src = path.join(packageRoot, name)
|
|
271
|
+
const dst = path.join(prefix, name)
|
|
272
|
+
if (!existsSync(src)) {
|
|
273
|
+
console.error(` warning: package missing ${name}/ directory`)
|
|
274
|
+
continue
|
|
275
|
+
}
|
|
276
|
+
removeKnownPath(dst, prefix)
|
|
277
|
+
await cp(src, dst, {
|
|
192
278
|
recursive: true,
|
|
193
279
|
force: true,
|
|
194
280
|
dereference: false,
|
|
195
281
|
})
|
|
196
282
|
}
|
|
197
283
|
|
|
284
|
+
// Ensure binaries are executable on Unix (cross-compiled from Windows they lose +x)
|
|
285
|
+
const binDir = path.join(prefix, "bin")
|
|
286
|
+
if (process.platform !== "win32" && existsSync(binDir)) {
|
|
287
|
+
for (const entry of readdirSync(binDir)) {
|
|
288
|
+
const binPath = path.join(binDir, entry)
|
|
289
|
+
try { chmodSync(binPath, 0o755) } catch {}
|
|
290
|
+
}
|
|
291
|
+
}
|
|
292
|
+
|
|
293
|
+
// Verify vantaloomctl binary exists before trying to run it
|
|
294
|
+
const ctlBin = path.join(prefix, "bin", binaryName("vantaloomctl"))
|
|
295
|
+
if (!existsSync(ctlBin)) {
|
|
296
|
+
const binContents = existsSync(binDir) ? readdirSync(binDir) : []
|
|
297
|
+
const srcBinContents = existsSync(path.join(packageRoot, "bin")) ? readdirSync(path.join(packageRoot, "bin")) : []
|
|
298
|
+
throw new Error(
|
|
299
|
+
`vantaloomctl binary not found at ${ctlBin}\n` +
|
|
300
|
+
` installed bin/: [${binContents.join(", ")}]\n` +
|
|
301
|
+
` package bin/: [${srcBinContents.join(", ")}]\n` +
|
|
302
|
+
` platform: ${platformId()}\n` +
|
|
303
|
+
` This may indicate a corrupt download. Try again or install from source.`
|
|
304
|
+
)
|
|
305
|
+
}
|
|
306
|
+
|
|
198
307
|
await writeLauncher(prefix)
|
|
199
308
|
await writeText(path.join(prefix, "cli", "config.json"), `${JSON.stringify(mergedConfig, null, 2)}\n`)
|
|
200
309
|
await writeText(path.join(prefix, "VERSION"), `${version}\n`)
|
|
@@ -202,7 +311,7 @@ async function applyPackage(packageRoot, prefix, options) {
|
|
|
202
311
|
force: true,
|
|
203
312
|
})
|
|
204
313
|
|
|
205
|
-
run(
|
|
314
|
+
run(ctlBin, [
|
|
206
315
|
"install",
|
|
207
316
|
"--prefix",
|
|
208
317
|
prefix,
|
|
@@ -211,7 +320,7 @@ async function applyPackage(packageRoot, prefix, options) {
|
|
|
211
320
|
])
|
|
212
321
|
|
|
213
322
|
if (!options.noStart) {
|
|
214
|
-
run(
|
|
323
|
+
run(ctlBin, [
|
|
215
324
|
"start",
|
|
216
325
|
"--prefix",
|
|
217
326
|
prefix,
|
|
@@ -224,9 +333,13 @@ async function applyPackage(packageRoot, prefix, options) {
|
|
|
224
333
|
async function syncFromNpmRegistry(options, action) {
|
|
225
334
|
const prefix = safeDirectory(options.prefix ?? defaultPrefix())
|
|
226
335
|
const installedConfig = readInstalledConfig(prefix)
|
|
227
|
-
|
|
336
|
+
// Always derive runtimePackage from current platform — never trust stale config
|
|
337
|
+
// from a different platform (e.g. win32 config baked into a darwin package).
|
|
338
|
+
// Only explicit --runtime-package flag can override.
|
|
339
|
+
const runtimePackage = options.runtimePackage || runtimePackageName(platformId())
|
|
228
340
|
const runtimeVersion = options.runtimeVersion || installedConfig.runtimeVersion || "latest"
|
|
229
|
-
const
|
|
341
|
+
const explicitRegistry = options.npmRegistry || installedConfig.npmRegistry
|
|
342
|
+
const registry = normalizeRegistry(explicitRegistry || detectNpmRegistry() || defaultNpmRegistry)
|
|
230
343
|
const tempRoot = mkdtempSync(path.join(os.tmpdir(), "vantaloom-npm-"))
|
|
231
344
|
|
|
232
345
|
try {
|
|
@@ -234,7 +347,11 @@ async function syncFromNpmRegistry(options, action) {
|
|
|
234
347
|
const archive = path.join(tempRoot, `${packageBasename(runtimePackage)}-${runtimeVersion}.tgz`)
|
|
235
348
|
mkdirSync(extractRoot, { recursive: true })
|
|
236
349
|
|
|
237
|
-
const resolved = await
|
|
350
|
+
const resolved = await resolveNpmPackageWithFallback({
|
|
351
|
+
registries: explicitRegistry ? [registry] : [registry, ...fallbackNpmRegistries.map(normalizeRegistry)],
|
|
352
|
+
name: runtimePackage,
|
|
353
|
+
version: runtimeVersion,
|
|
354
|
+
})
|
|
238
355
|
await downloadNpmTarball({
|
|
239
356
|
tarballUrl: resolved.tarball,
|
|
240
357
|
target: archive,
|
|
@@ -248,13 +365,15 @@ async function syncFromNpmRegistry(options, action) {
|
|
|
248
365
|
noStart: options.noStart,
|
|
249
366
|
runtimePackage,
|
|
250
367
|
runtimeVersion: options.runtimeVersion ? resolved.version : "latest",
|
|
251
|
-
npmRegistry: registry,
|
|
368
|
+
npmRegistry: resolved.registry,
|
|
252
369
|
update: action === "update",
|
|
253
370
|
})
|
|
254
371
|
|
|
255
372
|
console.log(`${action === "update" ? "updated" : "installed"} Vantaloom: ${prefix}`)
|
|
256
373
|
console.log(`version: ${version}`)
|
|
257
374
|
console.log(`source: ${runtimePackage}@${resolved.version}`)
|
|
375
|
+
console.log(`registry: ${resolved.registry}`)
|
|
376
|
+
ensureInPath(prefix)
|
|
258
377
|
console.log(`run: ${displayCommand(prefix)} status`)
|
|
259
378
|
} finally {
|
|
260
379
|
removeKnownPath(tempRoot, os.tmpdir())
|
|
@@ -296,6 +415,7 @@ async function syncFromRelease(options, action) {
|
|
|
296
415
|
console.log(`${action === "update" ? "updated" : "installed"} Vantaloom: ${prefix}`)
|
|
297
416
|
console.log(`version: ${version}`)
|
|
298
417
|
console.log(`source: ${repo}@${releaseTag}`)
|
|
418
|
+
ensureInPath(prefix)
|
|
299
419
|
console.log(`run: ${displayCommand(prefix)} status`)
|
|
300
420
|
} finally {
|
|
301
421
|
removeKnownPath(tempRoot, os.tmpdir())
|
|
@@ -346,14 +466,114 @@ async function downloadReleaseAsset({ repo, releaseTag, assetName, target, token
|
|
|
346
466
|
await writeFile(target, buffer)
|
|
347
467
|
}
|
|
348
468
|
|
|
469
|
+
function detectNpmRegistry() {
|
|
470
|
+
// 1. NPM_CONFIG_REGISTRY env var (highest priority, set by npm/npx when running)
|
|
471
|
+
if (process.env.NPM_CONFIG_REGISTRY) {
|
|
472
|
+
return process.env.npm_config_registry || process.env.NPM_CONFIG_REGISTRY
|
|
473
|
+
}
|
|
474
|
+
// npm also sets the lowercase variant
|
|
475
|
+
if (process.env.npm_config_registry) {
|
|
476
|
+
return process.env.npm_config_registry
|
|
477
|
+
}
|
|
478
|
+
|
|
479
|
+
// 2. Read user .npmrc
|
|
480
|
+
try {
|
|
481
|
+
const npmrcPaths = [
|
|
482
|
+
path.join(os.homedir(), ".npmrc"),
|
|
483
|
+
]
|
|
484
|
+
// Also check project-level .npmrc
|
|
485
|
+
const localNpmrc = path.resolve(".npmrc")
|
|
486
|
+
if (localNpmrc !== npmrcPaths[0]) {
|
|
487
|
+
npmrcPaths.unshift(localNpmrc)
|
|
488
|
+
}
|
|
489
|
+
for (const npmrcPath of npmrcPaths) {
|
|
490
|
+
if (existsSync(npmrcPath)) {
|
|
491
|
+
const content = readFileSync(npmrcPath, "utf8")
|
|
492
|
+
const match = content.match(/^\s*registry\s*=\s*(.+)/m)
|
|
493
|
+
if (match) {
|
|
494
|
+
return match[1].trim()
|
|
495
|
+
}
|
|
496
|
+
}
|
|
497
|
+
}
|
|
498
|
+
} catch {
|
|
499
|
+
// Ignore .npmrc read errors
|
|
500
|
+
}
|
|
501
|
+
|
|
502
|
+
return ""
|
|
503
|
+
}
|
|
504
|
+
|
|
505
|
+
async function resolveNpmPackageWithFallback({ registries, name, version }) {
|
|
506
|
+
const errors = []
|
|
507
|
+
for (const registry of registries) {
|
|
508
|
+
try {
|
|
509
|
+
const result = await resolveNpmPackage({ registry, name, version })
|
|
510
|
+
return { ...result, registry }
|
|
511
|
+
} catch (error) {
|
|
512
|
+
const causeCode = error?.cause?.code || ""
|
|
513
|
+
const isNetworkError = causeCode === "ECONNREFUSED"
|
|
514
|
+
|| causeCode === "ENOTFOUND"
|
|
515
|
+
|| causeCode === "ETIMEDOUT"
|
|
516
|
+
|| causeCode === "ECONNRESET"
|
|
517
|
+
|| causeCode === "UND_ERR_CONNECT_TIMEOUT"
|
|
518
|
+
|| (error instanceof TypeError && error.message === "fetch failed")
|
|
519
|
+
const isSslError = causeCode === "UNABLE_TO_GET_ISSUER_CERT_LOCALLY"
|
|
520
|
+
|| causeCode === "CERT_HAS_EXPIRED"
|
|
521
|
+
|| causeCode === "DEPTH_ZERO_SELF_SIGNED_CERT"
|
|
522
|
+
|| causeCode === "SELF_SIGNED_CERT_IN_CHAIN"
|
|
523
|
+
|| causeCode === "ERR_TLS_CERT_ALTNAME_INVALID"
|
|
524
|
+
const isRetryable = isNetworkError || isSslError
|
|
525
|
+
errors.push({ registry, error, isRetryable, isSslError })
|
|
526
|
+
|
|
527
|
+
if (isRetryable && registries.length > 1) {
|
|
528
|
+
const hint = isSslError ? " (SSL certificate error)" : ""
|
|
529
|
+
console.error(`vantaloom: ${registry} unreachable${hint}, trying next registry...`)
|
|
530
|
+
continue
|
|
531
|
+
}
|
|
532
|
+
if (isSslError) {
|
|
533
|
+
throw new Error(
|
|
534
|
+
`SSL certificate error connecting to ${registry}: ${causeCode}\n` +
|
|
535
|
+
` Fix: run with --no-strict-ssl, or set npm config: npm config set strict-ssl false`
|
|
536
|
+
)
|
|
537
|
+
}
|
|
538
|
+
// Non-network error (404, parse error, etc.) — don't try fallbacks
|
|
539
|
+
throw error
|
|
540
|
+
}
|
|
541
|
+
}
|
|
542
|
+
|
|
543
|
+
// All registries failed
|
|
544
|
+
const hasSslError = errors.some((e) => e.isSslError)
|
|
545
|
+
const tried = errors.map((e) => e.registry).join(", ")
|
|
546
|
+
const sslHint = hasSslError
|
|
547
|
+
? `\n SSL fix: run with --no-strict-ssl, or set npm config: npm config set strict-ssl false`
|
|
548
|
+
: ""
|
|
549
|
+
throw new Error(
|
|
550
|
+
`all registries unreachable (tried: ${tried}). ` +
|
|
551
|
+
`Check your network or specify --npm-registry <url>${sslHint}`
|
|
552
|
+
)
|
|
553
|
+
}
|
|
554
|
+
|
|
349
555
|
async function resolveNpmPackage({ registry, name, version }) {
|
|
350
556
|
const metadataUrl = `${registry}/${encodeURIComponent(name).replace("%2F", "%2f")}`
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
557
|
+
let response
|
|
558
|
+
try {
|
|
559
|
+
response = await fetch(metadataUrl, {
|
|
560
|
+
headers: {
|
|
561
|
+
Accept: "application/vnd.npm.install-v1+json",
|
|
562
|
+
"User-Agent": "vantaloom-cli",
|
|
563
|
+
},
|
|
564
|
+
signal: AbortSignal.timeout(15000),
|
|
565
|
+
})
|
|
566
|
+
} catch (error) {
|
|
567
|
+
if (error instanceof TypeError && error.message === "fetch failed") {
|
|
568
|
+
const causeCode = error.cause?.code || ""
|
|
569
|
+
const causeMsg = causeCode || error.cause?.message || String(error.cause || "")
|
|
570
|
+
throw Object.assign(
|
|
571
|
+
new Error(`cannot reach registry ${registry} (${causeMsg})`),
|
|
572
|
+
{ cause: error.cause }
|
|
573
|
+
)
|
|
574
|
+
}
|
|
575
|
+
throw error
|
|
576
|
+
}
|
|
357
577
|
if (!response.ok) {
|
|
358
578
|
const detail = await response.text().catch(() => "")
|
|
359
579
|
throw new Error(`failed to inspect npm package ${name}: HTTP ${response.status}${detail ? ` ${detail.slice(0, 200)}` : ""}`)
|
|
@@ -373,11 +593,22 @@ async function resolveNpmPackage({ registry, name, version }) {
|
|
|
373
593
|
}
|
|
374
594
|
|
|
375
595
|
async function downloadNpmTarball({ tarballUrl, target, packageName, version }) {
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
596
|
+
console.log(` downloading ${packageName}@${version}...`)
|
|
597
|
+
let response
|
|
598
|
+
try {
|
|
599
|
+
response = await fetch(tarballUrl, {
|
|
600
|
+
headers: {
|
|
601
|
+
"User-Agent": "vantaloom-cli",
|
|
602
|
+
},
|
|
603
|
+
signal: AbortSignal.timeout(120000),
|
|
604
|
+
})
|
|
605
|
+
} catch (error) {
|
|
606
|
+
const causeCode = error?.cause?.code || ""
|
|
607
|
+
const causeMsg = causeCode || error?.cause?.message || error.message || ""
|
|
608
|
+
const isSsl = causeCode.includes("CERT") || causeCode === "UNABLE_TO_GET_ISSUER_CERT_LOCALLY"
|
|
609
|
+
const hint = isSsl ? `\n Fix: run with --no-strict-ssl` : ""
|
|
610
|
+
throw new Error(`failed to download ${packageName}@${version} from ${tarballUrl}: ${causeMsg}${hint}`)
|
|
611
|
+
}
|
|
381
612
|
if (!response.ok) {
|
|
382
613
|
const detail = await response.text().catch(() => "")
|
|
383
614
|
throw new Error(`failed to download ${packageName}@${version}: HTTP ${response.status}${detail ? ` ${detail.slice(0, 200)}` : ""}`)
|
|
@@ -385,6 +616,7 @@ async function downloadNpmTarball({ tarballUrl, target, packageName, version })
|
|
|
385
616
|
|
|
386
617
|
const buffer = Buffer.from(await response.arrayBuffer())
|
|
387
618
|
await writeFile(target, buffer)
|
|
619
|
+
console.log(` downloaded ${(buffer.length / 1024 / 1024).toFixed(1)} MB`)
|
|
388
620
|
}
|
|
389
621
|
|
|
390
622
|
function shouldUseSourceInstall(options) {
|
|
@@ -448,9 +680,9 @@ function mergeRuntimeConfig(packageConfig, existingConfig, overrides) {
|
|
|
448
680
|
if (!merged.releaseTag) {
|
|
449
681
|
merged.releaseTag = defaultReleaseTag
|
|
450
682
|
}
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
683
|
+
// Always force runtimePackage to match the running platform — a cross-compiled
|
|
684
|
+
// package may carry a config for a different platform (e.g. win32 inside darwin).
|
|
685
|
+
merged.runtimePackage = runtimePackageName(platformId())
|
|
454
686
|
if (!merged.runtimeVersion) {
|
|
455
687
|
merged.runtimeVersion = "latest"
|
|
456
688
|
}
|
|
@@ -470,7 +702,7 @@ function runtimeConfigFromSource(sourceRoot) {
|
|
|
470
702
|
releaseTag: defaultReleaseTag,
|
|
471
703
|
runtimePackage: runtimePackageName(platformId()),
|
|
472
704
|
runtimeVersion: "latest",
|
|
473
|
-
npmRegistry: defaultNpmRegistry,
|
|
705
|
+
npmRegistry: detectNpmRegistry() || defaultNpmRegistry,
|
|
474
706
|
}
|
|
475
707
|
}
|
|
476
708
|
|
|
@@ -776,6 +1008,9 @@ function parseOptions(args) {
|
|
|
776
1008
|
case "local":
|
|
777
1009
|
options.local = true
|
|
778
1010
|
break
|
|
1011
|
+
case "no-strict-ssl":
|
|
1012
|
+
options.noStrictSsl = true
|
|
1013
|
+
break
|
|
779
1014
|
default:
|
|
780
1015
|
throw new Error(`unknown option --${key}`)
|
|
781
1016
|
}
|
|
@@ -897,6 +1132,92 @@ async function writeText(filePath, content) {
|
|
|
897
1132
|
await writeFile(filePath, content)
|
|
898
1133
|
}
|
|
899
1134
|
|
|
1135
|
+
// ensureInPath adds the Vantaloom install directory to the user's shell PATH
|
|
1136
|
+
// on macOS and Linux, so `vantaloom` can be run directly after install.
|
|
1137
|
+
// On Windows this is not needed (vantaloom.cmd is run by full path or added via installer).
|
|
1138
|
+
function ensureInPath(prefix) {
|
|
1139
|
+
if (process.platform === "win32") return
|
|
1140
|
+
|
|
1141
|
+
// Check if already in PATH
|
|
1142
|
+
const pathDirs = (process.env.PATH || "").split(":")
|
|
1143
|
+
if (pathDirs.includes(prefix)) return
|
|
1144
|
+
|
|
1145
|
+
// Determine shell profile file
|
|
1146
|
+
const home = os.homedir()
|
|
1147
|
+
const shell = process.env.SHELL || ""
|
|
1148
|
+
let profilePath
|
|
1149
|
+
if (shell.endsWith("/zsh") || existsSync(path.join(home, ".zshrc"))) {
|
|
1150
|
+
profilePath = path.join(home, ".zshrc")
|
|
1151
|
+
} else if (shell.endsWith("/bash")) {
|
|
1152
|
+
// On macOS, bash uses .bash_profile; on Linux, .bashrc
|
|
1153
|
+
profilePath = process.platform === "darwin"
|
|
1154
|
+
? path.join(home, ".bash_profile")
|
|
1155
|
+
: path.join(home, ".bashrc")
|
|
1156
|
+
} else if (existsSync(path.join(home, ".profile"))) {
|
|
1157
|
+
profilePath = path.join(home, ".profile")
|
|
1158
|
+
} else {
|
|
1159
|
+
profilePath = path.join(home, ".profile")
|
|
1160
|
+
}
|
|
1161
|
+
|
|
1162
|
+
// Use $HOME-relative path for portability
|
|
1163
|
+
const homeRelative = prefix.startsWith(home)
|
|
1164
|
+
? `$HOME${prefix.slice(home.length)}`
|
|
1165
|
+
: prefix
|
|
1166
|
+
const exportLine = `export PATH="${homeRelative}:$PATH"`
|
|
1167
|
+
const marker = "# vantaloom"
|
|
1168
|
+
|
|
1169
|
+
// Check if already added to profile
|
|
1170
|
+
try {
|
|
1171
|
+
if (existsSync(profilePath)) {
|
|
1172
|
+
const content = readFileSync(profilePath, "utf8")
|
|
1173
|
+
if (content.includes("vantaloom") && content.includes("PATH")) return
|
|
1174
|
+
}
|
|
1175
|
+
} catch {}
|
|
1176
|
+
|
|
1177
|
+
// Append to profile
|
|
1178
|
+
try {
|
|
1179
|
+
const entry = `\n${marker}\n${exportLine}\n`
|
|
1180
|
+
appendFileSync(profilePath, entry)
|
|
1181
|
+
console.log(`PATH: added ${prefix} to ${profilePath}`)
|
|
1182
|
+
console.log(` run: source ${profilePath} (or open a new terminal)`)
|
|
1183
|
+
} catch (error) {
|
|
1184
|
+
console.log(`PATH: could not update ${profilePath}: ${error.message}`)
|
|
1185
|
+
console.log(` add manually: ${exportLine}`)
|
|
1186
|
+
}
|
|
1187
|
+
}
|
|
1188
|
+
|
|
1189
|
+
function killTrayProcess(prefix) {
|
|
1190
|
+
if (process.platform === "win32") {
|
|
1191
|
+
// Try PID file first (new tray versions write runtime/tray.pid).
|
|
1192
|
+
const pidFile = path.join(prefix, "runtime", "tray.pid")
|
|
1193
|
+
if (existsSync(pidFile)) {
|
|
1194
|
+
const pid = readFileSync(pidFile, "utf8").trim()
|
|
1195
|
+
if (pid) {
|
|
1196
|
+
spawnSync("taskkill", ["/PID", pid, "/F"], { stdio: "ignore" })
|
|
1197
|
+
try { rmSync(pidFile, { force: true }) } catch {}
|
|
1198
|
+
}
|
|
1199
|
+
}
|
|
1200
|
+
// Fallback: kill by image name if the binary is inside our prefix.
|
|
1201
|
+
const result = spawnSync("tasklist", ["/FI", "IMAGENAME eq vantaloom-tray.exe", "/FO", "CSV", "/NH"], {
|
|
1202
|
+
encoding: "utf8",
|
|
1203
|
+
windowsHide: true,
|
|
1204
|
+
})
|
|
1205
|
+
if (result.stdout) {
|
|
1206
|
+
for (const line of result.stdout.split("\n")) {
|
|
1207
|
+
const match = line.match(/"vantaloom-tray\.exe","(\d+)"/)
|
|
1208
|
+
if (match) {
|
|
1209
|
+
spawnSync("taskkill", ["/PID", match[1], "/F"], { stdio: "ignore" })
|
|
1210
|
+
}
|
|
1211
|
+
}
|
|
1212
|
+
}
|
|
1213
|
+
// Brief pause to let file handles release.
|
|
1214
|
+
spawnSync("timeout", ["/t", "1", "/nobreak"], { stdio: "ignore", windowsHide: true })
|
|
1215
|
+
} else {
|
|
1216
|
+
// Unix: pkill by name (best-effort).
|
|
1217
|
+
spawnSync("pkill", ["-f", "vantaloom-tray"], { stdio: "ignore" })
|
|
1218
|
+
}
|
|
1219
|
+
}
|
|
1220
|
+
|
|
900
1221
|
function printHelp() {
|
|
901
1222
|
console.log(`Vantaloom CLI
|
|
902
1223
|
|
package/manifest.json
CHANGED
package/package.json
CHANGED
package/web/404.html
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
<!DOCTYPE html><!--
|
|
1
|
+
<!DOCTYPE html><!--E6VnJNHPIVhiQoKxBWUU2--><html lang="zh-CN" class="font-sans antialiased" data-vtl-theme="default" data-vtl-density="default" data-vtl-motion="default"><head><meta charSet="utf-8"/><meta name="viewport" content="width=device-width, initial-scale=1"/><link rel="stylesheet" href="/_next/static/chunks/73d2c788f1076e9a.css" data-precedence="next"/><link rel="preload" as="script" fetchPriority="low" href="/_next/static/chunks/a678910d6e3629e7.js"/><script src="/_next/static/chunks/b9cfbaaba1fd82be.js" async=""></script><script src="/_next/static/chunks/757e2e1b77b5bacc.js" async=""></script><script src="/_next/static/chunks/turbopack-d8677f40582561e6.js" async=""></script><script src="/_next/static/chunks/eca64d281474b631.js" async=""></script><script src="/_next/static/chunks/7dfeab42587bcc0e.js" async=""></script><meta name="robots" content="noindex"/><title>404: This page could not be found.</title><title>Vantaloom</title><meta name="description" content="Vantaloom local agent operations console."/><script src="/_next/static/chunks/a6dad97d9634a72d.js" noModule=""></script></head><body><div hidden=""><!--$--><!--/$--></div><script>((a,b,c,d,e,f,g,h)=>{let i=document.documentElement,j=["light","dark"];function k(b){var c;(Array.isArray(a)?a:[a]).forEach(a=>{let c="class"===a,d=c&&f?e.map(a=>f[a]||a):e;c?(i.classList.remove(...d),i.classList.add(f&&f[b]?f[b]:b)):i.setAttribute(a,b)}),c=b,h&&j.includes(c)&&(i.style.colorScheme=c)}if(d)k(d);else try{let a=localStorage.getItem(b)||c,d=g&&"system"===a?window.matchMedia("(prefers-color-scheme: dark)").matches?"dark":"light":a;k(d)}catch(a){}})("class","theme","system",null,["light","dark"],null,true,true)</script><div style="font-family:system-ui,"Segoe UI",Roboto,Helvetica,Arial,sans-serif,"Apple Color Emoji","Segoe UI Emoji";height:100vh;text-align:center;display:flex;flex-direction:column;align-items:center;justify-content:center"><div><style>body{color:#000;background:#fff;margin:0}.next-error-h1{border-right:1px solid rgba(0,0,0,.3)}@media (prefers-color-scheme:dark){body{color:#fff;background:#000}.next-error-h1{border-right:1px solid rgba(255,255,255,.3)}}</style><h1 class="next-error-h1" style="display:inline-block;margin:0 20px 0 0;padding:0 23px 0 0;font-size:24px;font-weight:500;vertical-align:top;line-height:49px">404</h1><div style="display:inline-block"><h2 style="font-size:14px;font-weight:400;line-height:49px;margin:0">This page could not be found.</h2></div></div></div><!--$--><!--/$--><script src="/_next/static/chunks/a678910d6e3629e7.js" id="_R_" async=""></script><script>(self.__next_f=self.__next_f||[]).push([0])</script><script>self.__next_f.push([1,"1:\"$Sreact.fragment\"\n2:I[22332,[\"/_next/static/chunks/eca64d281474b631.js\",\"/_next/static/chunks/7dfeab42587bcc0e.js\"],\"ThemeProvider\"]\n3:I[45121,[\"/_next/static/chunks/eca64d281474b631.js\",\"/_next/static/chunks/7dfeab42587bcc0e.js\"],\"default\"]\n4:I[60512,[\"/_next/static/chunks/eca64d281474b631.js\",\"/_next/static/chunks/7dfeab42587bcc0e.js\"],\"default\"]\n5:I[35417,[\"/_next/static/chunks/eca64d281474b631.js\",\"/_next/static/chunks/7dfeab42587bcc0e.js\"],\"OutletBoundary\"]\n6:\"$Sreact.suspense\"\n8:I[35417,[\"/_next/static/chunks/eca64d281474b631.js\",\"/_next/static/chunks/7dfeab42587bcc0e.js\"],\"ViewportBoundary\"]\na:I[35417,[\"/_next/static/chunks/eca64d281474b631.js\",\"/_next/static/chunks/7dfeab42587bcc0e.js\"],\"MetadataBoundary\"]\nc:I[50025,[\"/_next/static/chunks/eca64d281474b631.js\",\"/_next/static/chunks/7dfeab42587bcc0e.js\"],\"default\"]\n:HL[\"/_next/static/chunks/73d2c788f1076e9a.css\",\"style\"]\n"])</script><script>self.__next_f.push([1,"0:{\"P\":null,\"b\":\"E6VnJNHPIVhiQoKxBWUU2\",\"c\":[\"\",\"_not-found\"],\"q\":\"\",\"i\":false,\"f\":[[[\"\",{\"children\":[\"/_not-found\",{\"children\":[\"__PAGE__\",{}]}]},\"$undefined\",\"$undefined\",true],[[\"$\",\"$1\",\"c\",{\"children\":[[[\"$\",\"link\",\"0\",{\"rel\":\"stylesheet\",\"href\":\"/_next/static/chunks/73d2c788f1076e9a.css\",\"precedence\":\"next\",\"crossOrigin\":\"$undefined\",\"nonce\":\"$undefined\"}],[\"$\",\"script\",\"script-0\",{\"src\":\"/_next/static/chunks/eca64d281474b631.js\",\"async\":true,\"nonce\":\"$undefined\"}],[\"$\",\"script\",\"script-1\",{\"src\":\"/_next/static/chunks/7dfeab42587bcc0e.js\",\"async\":true,\"nonce\":\"$undefined\"}]],[\"$\",\"html\",null,{\"lang\":\"zh-CN\",\"suppressHydrationWarning\":true,\"className\":\"font-sans antialiased\",\"data-vtl-theme\":\"default\",\"data-vtl-density\":\"default\",\"data-vtl-motion\":\"default\",\"children\":[\"$\",\"body\",null,{\"children\":[\"$\",\"$L2\",null,{\"children\":[\"$\",\"$L3\",null,{\"parallelRouterKey\":\"children\",\"error\":\"$undefined\",\"errorStyles\":\"$undefined\",\"errorScripts\":\"$undefined\",\"template\":[\"$\",\"$L4\",null,{}],\"templateStyles\":\"$undefined\",\"templateScripts\":\"$undefined\",\"notFound\":[[[\"$\",\"title\",null,{\"children\":\"404: This page could not be found.\"}],[\"$\",\"div\",null,{\"style\":{\"fontFamily\":\"system-ui,\\\"Segoe UI\\\",Roboto,Helvetica,Arial,sans-serif,\\\"Apple Color Emoji\\\",\\\"Segoe UI Emoji\\\"\",\"height\":\"100vh\",\"textAlign\":\"center\",\"display\":\"flex\",\"flexDirection\":\"column\",\"alignItems\":\"center\",\"justifyContent\":\"center\"},\"children\":[\"$\",\"div\",null,{\"children\":[[\"$\",\"style\",null,{\"dangerouslySetInnerHTML\":{\"__html\":\"body{color:#000;background:#fff;margin:0}.next-error-h1{border-right:1px solid rgba(0,0,0,.3)}@media (prefers-color-scheme:dark){body{color:#fff;background:#000}.next-error-h1{border-right:1px solid rgba(255,255,255,.3)}}\"}}],[\"$\",\"h1\",null,{\"className\":\"next-error-h1\",\"style\":{\"display\":\"inline-block\",\"margin\":\"0 20px 0 0\",\"padding\":\"0 23px 0 0\",\"fontSize\":24,\"fontWeight\":500,\"verticalAlign\":\"top\",\"lineHeight\":\"49px\"},\"children\":404}],[\"$\",\"div\",null,{\"style\":{\"display\":\"inline-block\"},\"children\":[\"$\",\"h2\",null,{\"style\":{\"fontSize\":14,\"fontWeight\":400,\"lineHeight\":\"49px\",\"margin\":0},\"children\":\"This page could not be found.\"}]}]]}]}]],[]],\"forbidden\":\"$undefined\",\"unauthorized\":\"$undefined\"}]}]}]}]]}],{\"children\":[[\"$\",\"$1\",\"c\",{\"children\":[null,[\"$\",\"$L3\",null,{\"parallelRouterKey\":\"children\",\"error\":\"$undefined\",\"errorStyles\":\"$undefined\",\"errorScripts\":\"$undefined\",\"template\":[\"$\",\"$L4\",null,{}],\"templateStyles\":\"$undefined\",\"templateScripts\":\"$undefined\",\"notFound\":\"$undefined\",\"forbidden\":\"$undefined\",\"unauthorized\":\"$undefined\"}]]}],{\"children\":[[\"$\",\"$1\",\"c\",{\"children\":[[[\"$\",\"title\",null,{\"children\":\"404: This page could not be found.\"}],[\"$\",\"div\",null,{\"style\":\"$0:f:0:1:0:props:children:1:props:children:props:children:props:children:props:notFound:0:1:props:style\",\"children\":[\"$\",\"div\",null,{\"children\":[[\"$\",\"style\",null,{\"dangerouslySetInnerHTML\":{\"__html\":\"body{color:#000;background:#fff;margin:0}.next-error-h1{border-right:1px solid rgba(0,0,0,.3)}@media (prefers-color-scheme:dark){body{color:#fff;background:#000}.next-error-h1{border-right:1px solid rgba(255,255,255,.3)}}\"}}],[\"$\",\"h1\",null,{\"className\":\"next-error-h1\",\"style\":\"$0:f:0:1:0:props:children:1:props:children:props:children:props:children:props:notFound:0:1:props:children:props:children:1:props:style\",\"children\":404}],[\"$\",\"div\",null,{\"style\":\"$0:f:0:1:0:props:children:1:props:children:props:children:props:children:props:notFound:0:1:props:children:props:children:2:props:style\",\"children\":[\"$\",\"h2\",null,{\"style\":\"$0:f:0:1:0:props:children:1:props:children:props:children:props:children:props:notFound:0:1:props:children:props:children:2:props:children:props:style\",\"children\":\"This page could not be found.\"}]}]]}]}]],null,[\"$\",\"$L5\",null,{\"children\":[\"$\",\"$6\",null,{\"name\":\"Next.MetadataOutlet\",\"children\":\"$@7\"}]}]]}],{},null,false,false]},null,false,false]},null,false,false],[\"$\",\"$1\",\"h\",{\"children\":[[\"$\",\"meta\",null,{\"name\":\"robots\",\"content\":\"noindex\"}],[\"$\",\"$L8\",null,{\"children\":\"$L9\"}],[\"$\",\"div\",null,{\"hidden\":true,\"children\":[\"$\",\"$La\",null,{\"children\":[\"$\",\"$6\",null,{\"name\":\"Next.Metadata\",\"children\":\"$Lb\"}]}]}],null]}],false]],\"m\":\"$undefined\",\"G\":[\"$c\",\"$undefined\"],\"S\":true}\n"])</script><script>self.__next_f.push([1,"9:[[\"$\",\"meta\",\"0\",{\"charSet\":\"utf-8\"}],[\"$\",\"meta\",\"1\",{\"name\":\"viewport\",\"content\":\"width=device-width, initial-scale=1\"}]]\n"])</script><script>self.__next_f.push([1,"7:null\nb:[[\"$\",\"title\",\"0\",{\"children\":\"Vantaloom\"}],[\"$\",\"meta\",\"1\",{\"name\":\"description\",\"content\":\"Vantaloom local agent operations console.\"}]]\n"])</script></body></html>
|
package/web/__next.__PAGE__.txt
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
1:"$Sreact.fragment"
|
|
2
2
|
2:I[66863,["/_next/static/chunks/7dfeab42587bcc0e.js"],"ClientPageRoot"]
|
|
3
|
-
3:I[66204,["/_next/static/chunks/eca64d281474b631.js","/_next/static/chunks/17e0384154325960.js","/_next/static/chunks/c990601c49cb69a5.js","/_next/static/chunks/
|
|
3
|
+
3:I[66204,["/_next/static/chunks/eca64d281474b631.js","/_next/static/chunks/17e0384154325960.js","/_next/static/chunks/c990601c49cb69a5.js","/_next/static/chunks/80b4a364458ec11d.js","/_next/static/chunks/742d3900ca49db0a.js"],"default"]
|
|
4
4
|
6:I[35417,["/_next/static/chunks/7dfeab42587bcc0e.js"],"OutletBoundary"]
|
|
5
5
|
7:"$Sreact.suspense"
|
|
6
|
-
0:{"buildId":"
|
|
6
|
+
0:{"buildId":"E6VnJNHPIVhiQoKxBWUU2","rsc":["$","$1","c",{"children":[["$","$L2",null,{"Component":"$3","serverProvidedParams":{"searchParams":{},"params":{},"promises":["$@4","$@5"]}}],[["$","script","script-0",{"src":"/_next/static/chunks/17e0384154325960.js","async":true}],["$","script","script-1",{"src":"/_next/static/chunks/c990601c49cb69a5.js","async":true}],["$","script","script-2",{"src":"/_next/static/chunks/80b4a364458ec11d.js","async":true}],["$","script","script-3",{"src":"/_next/static/chunks/742d3900ca49db0a.js","async":true}]],["$","$L6",null,{"children":["$","$7",null,{"name":"Next.MetadataOutlet","children":"$@8"}]}]]}],"loading":null,"isPartial":false}
|
|
7
7
|
4:{}
|
|
8
8
|
5:"$0:rsc:props:children:0:props:serverProvidedParams:params"
|
|
9
9
|
8:null
|