glimmervoid 0.0.0-stage → 0.30.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/LICENSE +48 -0
- package/README.md +195 -2
- package/dist/bin/glimmervoid.js +275 -0
- package/dist/chunks/adapters-Dho1VSY5.js +2 -0
- package/dist/chunks/adapters-zPDx1Xox.js +575 -0
- package/dist/chunks/agent-api-cli-D0MmtEdz.js +71 -0
- package/dist/chunks/agent-api-core-Dz0r21y9.js +103 -0
- package/dist/chunks/agent-setup-cli-B5Atxr3F.js +139 -0
- package/dist/chunks/ascii-figure-core-pDAwtlKO.js +45 -0
- package/dist/chunks/child-process-safe-DRGsp0TE.js +69 -0
- package/dist/chunks/child-process-safe-DvQjXsgz.js +2 -0
- package/dist/chunks/config-path-core-DFt-TemS.js +38 -0
- package/dist/chunks/config-store-CC8T3okC.js +2 -0
- package/dist/chunks/config-store-mm7MgzoL.js +1412 -0
- package/dist/chunks/contracts-DGkKNh9W.js +3020 -0
- package/dist/chunks/grok-DuU8xVLZ.js +436 -0
- package/dist/chunks/hook-command-core-DclEoE9e.js +14 -0
- package/dist/chunks/hook-relay-core-BHfYFnYV.js +88 -0
- package/dist/chunks/hook-tools-pSJia7ks.js +74 -0
- package/dist/chunks/ingest-core-DWI1Mbu4.js +342 -0
- package/dist/chunks/ingest-editor-core-BuI1gMF_.js +445 -0
- package/dist/chunks/loopback-post-C7C22eYi.js +79 -0
- package/dist/chunks/main-CuIZQPhZ.js +43559 -0
- package/dist/chunks/node-pty-preflight-CK1knGIR.js +162 -0
- package/dist/chunks/pair-cli-w-gCAF-1.js +110 -0
- package/dist/chunks/path-doctor-C23VAqeu.js +63 -0
- package/dist/chunks/refocus-core-BKQKllq7.js +38 -0
- package/dist/chunks/relay-stdin-CpHvLu6M.js +20 -0
- package/dist/chunks/remote-config-C2ytQwrs.js +525 -0
- package/dist/chunks/rtk-hook-core-Bl6gYHPN.js +133 -0
- package/dist/chunks/rtk-resolver-CLo-gZzw.js +21 -0
- package/dist/chunks/rtk-resolver-CMQAidlI.js +2 -0
- package/dist/chunks/runtime-paths-Ci_ksSkj.js +75 -0
- package/dist/chunks/runtime-paths-JLrZ3wyi.js +2 -0
- package/dist/chunks/sandbox-deps-Dd5-kZnf.js +67 -0
- package/dist/chunks/session-Cez8aIWg.js +164 -0
- package/dist/chunks/spawn-command-Cc40FiZI.js +134 -0
- package/dist/chunks/visions-cli-BXQFIBCX.js +98 -0
- package/dist/chunks/visions-setup-CvVnOe1r.js +1753 -0
- package/dist/client/assets/favicon-CKygeLwW.svg +7 -0
- package/dist/client/assets/index-B1MFijjb.css +1 -0
- package/dist/client/assets/index-CU1iPPdn.js +249 -0
- package/dist/client/index.html +108 -0
- package/dist/package.json +3 -0
- package/dist/scripts/postinstall-path-check.js +36 -0
- package/dist/server/index.js +92 -0
- package/dist/session/command-hook-relay.js +16 -0
- package/dist/session/hook-relay.js +24 -0
- package/dist/session/hook-tool-relay.js +107 -0
- package/dist/session/statusline-relay.js +82 -0
- package/dist/session/visions-relay.js +627 -0
- package/dist/tools/vscode-visions/extension.js +289 -0
- package/dist/tools/vscode-visions/lsp-convert.js +80 -0
- package/dist/tools/vscode-visions/package.json +32 -0
- package/dist/tools/vscode-visions/visions-lsp-core.js +112 -0
- package/package.json +96 -4
- package/scripts/postinstall.mjs +4 -0
- package/scripts/prepare-build.js +38 -0
- package/scripts/recover-handoff.mjs +82 -0
|
@@ -0,0 +1,103 @@
|
|
|
1
|
+
import { a as AgentSpawnRequest, i as AgentAttentionRequest, t as AGENT_API_VERBS } from "./session-Cez8aIWg.js";
|
|
2
|
+
import crypto from "node:crypto";
|
|
3
|
+
var MAX_SPAWNS_IN_FLIGHT = 1;
|
|
4
|
+
var SPAWNABLE_DEPTH = 0;
|
|
5
|
+
var REFUSAL_REASON = "unknown session";
|
|
6
|
+
var INVALID_BODY_STATUS = 400;
|
|
7
|
+
function tokensMatch(presented, expected) {
|
|
8
|
+
if (presented.length !== expected.length) return false;
|
|
9
|
+
try {
|
|
10
|
+
return crypto.timingSafeEqual(Buffer.from(presented, "utf8"), Buffer.from(expected, "utf8"));
|
|
11
|
+
} catch {
|
|
12
|
+
return false;
|
|
13
|
+
}
|
|
14
|
+
}
|
|
15
|
+
function refused() {
|
|
16
|
+
return {
|
|
17
|
+
ok: false,
|
|
18
|
+
status: 404,
|
|
19
|
+
reason: REFUSAL_REASON
|
|
20
|
+
};
|
|
21
|
+
}
|
|
22
|
+
function decideAgentRequest({ sessionId, presentedToken, expectedToken, isLoopback, enabled }) {
|
|
23
|
+
if (!enabled) return refused();
|
|
24
|
+
if (!isLoopback) return refused();
|
|
25
|
+
if (!sessionId) return refused();
|
|
26
|
+
if (!expectedToken) return refused();
|
|
27
|
+
if (!presentedToken) return refused();
|
|
28
|
+
if (!tokensMatch(presentedToken, expectedToken)) return refused();
|
|
29
|
+
return { ok: true };
|
|
30
|
+
}
|
|
31
|
+
function decideSpawnAllowance({ liveChildren, lifetimeSpawns, inFlight, depth }) {
|
|
32
|
+
if (depth !== SPAWNABLE_DEPTH) return {
|
|
33
|
+
ok: false,
|
|
34
|
+
status: 403,
|
|
35
|
+
reason: "a spawned session may not spawn another"
|
|
36
|
+
};
|
|
37
|
+
if (inFlight >= MAX_SPAWNS_IN_FLIGHT) return {
|
|
38
|
+
ok: false,
|
|
39
|
+
status: 429,
|
|
40
|
+
reason: "a spawn is already in flight"
|
|
41
|
+
};
|
|
42
|
+
if (liveChildren >= 3) return {
|
|
43
|
+
ok: false,
|
|
44
|
+
status: 429,
|
|
45
|
+
reason: `at most 3 spawned sessions may be live at once`
|
|
46
|
+
};
|
|
47
|
+
if (lifetimeSpawns >= 10) return {
|
|
48
|
+
ok: false,
|
|
49
|
+
status: 429,
|
|
50
|
+
reason: `this session has used its 10 spawns`
|
|
51
|
+
};
|
|
52
|
+
return { ok: true };
|
|
53
|
+
}
|
|
54
|
+
function isAgentApiVerb(verb) {
|
|
55
|
+
return AGENT_API_VERBS.includes(verb);
|
|
56
|
+
}
|
|
57
|
+
function refuseInvalidBody(issues) {
|
|
58
|
+
return {
|
|
59
|
+
ok: false,
|
|
60
|
+
status: INVALID_BODY_STATUS,
|
|
61
|
+
error: issues[0]?.message || "invalid request"
|
|
62
|
+
};
|
|
63
|
+
}
|
|
64
|
+
function parseAgentVerb(verb, payload) {
|
|
65
|
+
if (!isAgentApiVerb(verb)) return {
|
|
66
|
+
ok: false,
|
|
67
|
+
status: 404,
|
|
68
|
+
error: REFUSAL_REASON
|
|
69
|
+
};
|
|
70
|
+
if (verb === "board") return {
|
|
71
|
+
ok: true,
|
|
72
|
+
verb
|
|
73
|
+
};
|
|
74
|
+
if (verb === "attention") {
|
|
75
|
+
const parsed = AgentAttentionRequest.safeParse(payload);
|
|
76
|
+
if (!parsed.success) return refuseInvalidBody(parsed.error.issues);
|
|
77
|
+
return {
|
|
78
|
+
ok: true,
|
|
79
|
+
verb,
|
|
80
|
+
request: parsed.data
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
const parsed = AgentSpawnRequest.safeParse(payload);
|
|
84
|
+
if (!parsed.success) return refuseInvalidBody(parsed.error.issues);
|
|
85
|
+
return {
|
|
86
|
+
ok: true,
|
|
87
|
+
verb,
|
|
88
|
+
request: parsed.data
|
|
89
|
+
};
|
|
90
|
+
}
|
|
91
|
+
function deriveChildSessionName(parentName, existingNames) {
|
|
92
|
+
const base = `${String(parentName || "").trim() || "session"} agent`;
|
|
93
|
+
const taken = new Set(existingNames);
|
|
94
|
+
let candidate = base;
|
|
95
|
+
let suffix = 1;
|
|
96
|
+
while (taken.has(candidate)) {
|
|
97
|
+
suffix += 1;
|
|
98
|
+
candidate = `${base} ${suffix}`;
|
|
99
|
+
}
|
|
100
|
+
return candidate;
|
|
101
|
+
}
|
|
102
|
+
//#endregion
|
|
103
|
+
export { isAgentApiVerb as a, deriveChildSessionName as i, decideAgentRequest as n, parseAgentVerb as o, decideSpawnAllowance as r, REFUSAL_REASON as t };
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
import { a as classifyGrokHooksFile, o as renderGrokHooksFile, t as grok } from "./grok-DuU8xVLZ.js";
|
|
2
|
+
import fs from "node:fs";
|
|
3
|
+
import path from "node:path";
|
|
4
|
+
import crypto from "node:crypto";
|
|
5
|
+
//#region server/agent-setup-cli.ts
|
|
6
|
+
var USAGE = "Usage: glimmervoid agent setup grok";
|
|
7
|
+
function errorCode(error) {
|
|
8
|
+
const code = error?.code;
|
|
9
|
+
return typeof code === "string" ? code : void 0;
|
|
10
|
+
}
|
|
11
|
+
function errorMessage(error) {
|
|
12
|
+
return error instanceof Error ? error.message : String(error);
|
|
13
|
+
}
|
|
14
|
+
function setupInputs(env = process.env) {
|
|
15
|
+
return {
|
|
16
|
+
filePath: grok.hooksFilePath(env),
|
|
17
|
+
relayPath: grok.RELAY_PATH,
|
|
18
|
+
hookToolRelayPath: grok.HOOK_TOOL_RELAY_PATH,
|
|
19
|
+
events: grok.HOOK_EVENTS,
|
|
20
|
+
managedEventSets: grok.MANAGED_HOOK_EVENT_SETS
|
|
21
|
+
};
|
|
22
|
+
}
|
|
23
|
+
function inspectGrokAgentSetup({ env = process.env, readFileSync = fs.readFileSync } = {}) {
|
|
24
|
+
const inputs = setupInputs(env);
|
|
25
|
+
let contents = null;
|
|
26
|
+
try {
|
|
27
|
+
contents = readFileSync(inputs.filePath, "utf8");
|
|
28
|
+
} catch (error) {
|
|
29
|
+
if (errorCode(error) === "ENOENT") return {
|
|
30
|
+
filePath: inputs.filePath,
|
|
31
|
+
classification: "absent"
|
|
32
|
+
};
|
|
33
|
+
return {
|
|
34
|
+
filePath: inputs.filePath,
|
|
35
|
+
classification: "unreadable",
|
|
36
|
+
reason: errorMessage(error)
|
|
37
|
+
};
|
|
38
|
+
}
|
|
39
|
+
return {
|
|
40
|
+
filePath: inputs.filePath,
|
|
41
|
+
classification: classifyGrokHooksFile(contents, inputs),
|
|
42
|
+
saneYoloReady: contents === renderGrokHooksFile(inputs)
|
|
43
|
+
};
|
|
44
|
+
}
|
|
45
|
+
function assertRealDirectory(directory, fileSystem, requireOwnership = true) {
|
|
46
|
+
const directoryStat = fileSystem.lstatSync(directory);
|
|
47
|
+
if (!directoryStat.isDirectory() || directoryStat.isSymbolicLink()) throw new Error(`refusing to write Grok hooks: ${directory} is not a real directory`);
|
|
48
|
+
if (requireOwnership && typeof process.getuid === "function" && directoryStat.uid !== process.getuid()) throw new Error(`refusing to write Grok hooks: ${directory} is owned by another account`);
|
|
49
|
+
}
|
|
50
|
+
function ensureWritableHooksDirectory(directory, fileSystem) {
|
|
51
|
+
const resolvedDirectory = path.resolve(directory);
|
|
52
|
+
const trustedParent = path.dirname(path.dirname(resolvedDirectory));
|
|
53
|
+
assertRealDirectory(trustedParent, fileSystem, false);
|
|
54
|
+
const relativeParts = path.relative(trustedParent, resolvedDirectory).split(path.sep).filter(Boolean);
|
|
55
|
+
let currentDirectory = trustedParent;
|
|
56
|
+
for (const part of relativeParts) {
|
|
57
|
+
currentDirectory = path.join(currentDirectory, part);
|
|
58
|
+
try {
|
|
59
|
+
assertRealDirectory(currentDirectory, fileSystem);
|
|
60
|
+
continue;
|
|
61
|
+
} catch (directoryError) {
|
|
62
|
+
if (errorCode(directoryError) !== "ENOENT") throw directoryError;
|
|
63
|
+
}
|
|
64
|
+
fileSystem.mkdirSync(currentDirectory, { mode: 448 });
|
|
65
|
+
assertRealDirectory(currentDirectory, fileSystem);
|
|
66
|
+
}
|
|
67
|
+
try {
|
|
68
|
+
fileSystem.chmodSync(directory, 448);
|
|
69
|
+
} catch {}
|
|
70
|
+
}
|
|
71
|
+
function replaceFileAtomically(filePath, contents, fileSystem) {
|
|
72
|
+
const temporaryPath = `${filePath}.${process.pid}.${crypto.randomBytes(8).toString("hex")}.tmp`;
|
|
73
|
+
try {
|
|
74
|
+
fileSystem.writeFileSync(temporaryPath, contents, {
|
|
75
|
+
encoding: "utf8",
|
|
76
|
+
mode: 384,
|
|
77
|
+
flag: "wx"
|
|
78
|
+
});
|
|
79
|
+
fileSystem.renameSync(temporaryPath, filePath);
|
|
80
|
+
} catch (writeError) {
|
|
81
|
+
try {
|
|
82
|
+
fileSystem.rmSync(temporaryPath, { force: true });
|
|
83
|
+
} catch {}
|
|
84
|
+
throw writeError;
|
|
85
|
+
}
|
|
86
|
+
try {
|
|
87
|
+
fileSystem.chmodSync(filePath, 384);
|
|
88
|
+
} catch {}
|
|
89
|
+
}
|
|
90
|
+
function runGrokSetup({ env, fileSystem, log, error }) {
|
|
91
|
+
const inputs = setupInputs(env);
|
|
92
|
+
const expectedContents = renderGrokHooksFile(inputs);
|
|
93
|
+
if (!expectedContents) {
|
|
94
|
+
error("Could not render the Grok hooks file. Nothing was written.");
|
|
95
|
+
return 1;
|
|
96
|
+
}
|
|
97
|
+
const inspection = inspectGrokAgentSetup({
|
|
98
|
+
env,
|
|
99
|
+
readFileSync: fileSystem.readFileSync
|
|
100
|
+
});
|
|
101
|
+
if (inspection.classification === "current" && inspection.saneYoloReady) {
|
|
102
|
+
log(`Grok hooks are already current at ${inputs.filePath}`);
|
|
103
|
+
return 0;
|
|
104
|
+
}
|
|
105
|
+
if (inspection.classification === "foreign" || inspection.classification === "unreadable") {
|
|
106
|
+
error(`Refusing to replace ${inputs.filePath}: the existing file is ${inspection.classification}.`);
|
|
107
|
+
return 1;
|
|
108
|
+
}
|
|
109
|
+
const hooksDirectory = path.dirname(inputs.filePath);
|
|
110
|
+
try {
|
|
111
|
+
ensureWritableHooksDirectory(hooksDirectory, fileSystem);
|
|
112
|
+
if (fileSystem.existsSync(inputs.filePath)) {
|
|
113
|
+
const targetStat = fileSystem.lstatSync(inputs.filePath);
|
|
114
|
+
if (!targetStat.isFile() || targetStat.isSymbolicLink()) {
|
|
115
|
+
error(`Refusing to replace ${inputs.filePath}: the target is not a real file.`);
|
|
116
|
+
return 1;
|
|
117
|
+
}
|
|
118
|
+
}
|
|
119
|
+
replaceFileAtomically(inputs.filePath, expectedContents, fileSystem);
|
|
120
|
+
} catch (writeError) {
|
|
121
|
+
error(`Could not write ${inputs.filePath}: ${errorMessage(writeError)}`);
|
|
122
|
+
return 1;
|
|
123
|
+
}
|
|
124
|
+
log(`Installed Grok hooks at ${inputs.filePath}`);
|
|
125
|
+
return 0;
|
|
126
|
+
}
|
|
127
|
+
function runAgentSetupCli(args, deps = {}) {
|
|
128
|
+
const { env = process.env, fileSystem = fs, log = console.log, error = console.error } = deps;
|
|
129
|
+
if (args[0] === "setup" && args[1] === "grok" && args.length === 2) return runGrokSetup({
|
|
130
|
+
env,
|
|
131
|
+
fileSystem,
|
|
132
|
+
log,
|
|
133
|
+
error
|
|
134
|
+
});
|
|
135
|
+
error(USAGE);
|
|
136
|
+
return 1;
|
|
137
|
+
}
|
|
138
|
+
//#endregion
|
|
139
|
+
export { inspectGrokAgentSetup, runAgentSetupCli };
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
//#region server/core/ascii-figure-core.ts
|
|
2
|
+
function widthOf(text) {
|
|
3
|
+
return Array.from(text).length;
|
|
4
|
+
}
|
|
5
|
+
function padToWidth(text, width, alignment) {
|
|
6
|
+
const paddedLength = text.length + Math.max(0, width - widthOf(text));
|
|
7
|
+
return alignment === "right" ? text.padStart(paddedLength) : text.padEnd(paddedLength);
|
|
8
|
+
}
|
|
9
|
+
function splitIntoPhysicalRows(row) {
|
|
10
|
+
const linesPerCell = row.map((cell) => cell.split(/\r?\n/));
|
|
11
|
+
const rowHeight = Math.max(1, ...linesPerCell.map((cellLines) => cellLines.length));
|
|
12
|
+
return Array.from({ length: rowHeight }, (_, lineIndex) => linesPerCell.map((cellLines) => cellLines[lineIndex] ?? ""));
|
|
13
|
+
}
|
|
14
|
+
function renderTable({ title, headers, rows, align, terminalColumns }) {
|
|
15
|
+
const headerRows = headers ? splitIntoPhysicalRows(headers) : [];
|
|
16
|
+
const bodyRows = rows.flatMap(splitIntoPhysicalRows);
|
|
17
|
+
const allRows = [...headerRows, ...bodyRows];
|
|
18
|
+
const columnCount = Math.max(1, ...allRows.map((row) => row.length));
|
|
19
|
+
const widths = Array.from({ length: columnCount }, (_, index) => Math.max(0, ...allRows.map((row) => widthOf(row[index] ?? ""))));
|
|
20
|
+
const separator = headers ? " | " : " ";
|
|
21
|
+
const renderCells = (row) => Array.from({ length: columnCount }, (_, index) => padToWidth(row[index] ?? "", widths[index] ?? 0, align?.[index] ?? (index === 0 || !headers ? "left" : "right"))).join(separator);
|
|
22
|
+
const lines = headers ? [
|
|
23
|
+
...headerRows.map(renderCells),
|
|
24
|
+
widths.map((width) => "-".repeat(width)).join("-+-"),
|
|
25
|
+
...bodyRows.map(renderCells)
|
|
26
|
+
] : bodyRows.map(renderCells);
|
|
27
|
+
const caption = title.trim() ? `[ ${title.trim().toUpperCase()} ]` : "";
|
|
28
|
+
const availableColumns = typeof terminalColumns === "number" && Number.isFinite(terminalColumns) ? terminalColumns : 80;
|
|
29
|
+
const innerWidth = Math.max(0, ...lines.map(widthOf), caption ? widthOf(caption) + 4 : 0, Math.min(48, availableColumns - 4));
|
|
30
|
+
const span = innerWidth + 2;
|
|
31
|
+
const captionLabel = ` ${caption} `;
|
|
32
|
+
const remainingDashes = Math.max(0, span - widthOf(captionLabel));
|
|
33
|
+
const leftDashes = Math.floor(remainingDashes / 2);
|
|
34
|
+
const top = caption ? `+${"-".repeat(leftDashes)}${captionLabel}${"-".repeat(remainingDashes - leftDashes)}+` : `+${"-".repeat(span)}+`;
|
|
35
|
+
const empty = `| ${" ".repeat(innerWidth)} |`;
|
|
36
|
+
return [
|
|
37
|
+
top,
|
|
38
|
+
empty,
|
|
39
|
+
...lines.map((line) => `| ${padToWidth(line, innerWidth, "left")} |`),
|
|
40
|
+
empty,
|
|
41
|
+
`+${"-".repeat(span)}+`
|
|
42
|
+
].join("\n");
|
|
43
|
+
}
|
|
44
|
+
//#endregion
|
|
45
|
+
export { renderTable as t };
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
import cp from "node:child_process";
|
|
2
|
+
import { promisify } from "node:util";
|
|
3
|
+
//#region server/child-process-safe.ts
|
|
4
|
+
function hide(options) {
|
|
5
|
+
if (!options || typeof options !== "object") return { windowsHide: true };
|
|
6
|
+
return {
|
|
7
|
+
...options,
|
|
8
|
+
windowsHide: true
|
|
9
|
+
};
|
|
10
|
+
}
|
|
11
|
+
function split(rest) {
|
|
12
|
+
let args;
|
|
13
|
+
let options;
|
|
14
|
+
let callback;
|
|
15
|
+
for (const v of rest) {
|
|
16
|
+
if (Array.isArray(v) && v.every((entry) => typeof entry === "string")) args = v;
|
|
17
|
+
if (typeof v === "function") callback = v;
|
|
18
|
+
if (v && typeof v === "object" && !Array.isArray(v)) options = v;
|
|
19
|
+
}
|
|
20
|
+
return {
|
|
21
|
+
args,
|
|
22
|
+
options,
|
|
23
|
+
callback
|
|
24
|
+
};
|
|
25
|
+
}
|
|
26
|
+
var execFile = Object.assign(function execFile(file, ...rest) {
|
|
27
|
+
const { args, options, callback } = split(rest);
|
|
28
|
+
const execOptions = hide(options);
|
|
29
|
+
return cp.execFile(file, args, execOptions, callback);
|
|
30
|
+
}, { [promisify.custom]: (file, ...rest) => new Promise((resolve, reject) => {
|
|
31
|
+
const { args, options } = split(rest);
|
|
32
|
+
const { input, ...commandOptions } = options ?? {};
|
|
33
|
+
const execOptions = hide(commandOptions);
|
|
34
|
+
const callback = (err, stdout, stderr) => {
|
|
35
|
+
if (err) {
|
|
36
|
+
const failure = err;
|
|
37
|
+
failure.stdout = stdout;
|
|
38
|
+
failure.stderr = stderr;
|
|
39
|
+
return reject(failure);
|
|
40
|
+
}
|
|
41
|
+
resolve({
|
|
42
|
+
stdout,
|
|
43
|
+
stderr
|
|
44
|
+
});
|
|
45
|
+
};
|
|
46
|
+
const child = cp.execFile(file, args, execOptions, callback);
|
|
47
|
+
if (typeof input !== "string") return;
|
|
48
|
+
if (!child.stdin) return reject(/* @__PURE__ */ new Error("execFile stdin unavailable"));
|
|
49
|
+
child.stdin.on("error", reject);
|
|
50
|
+
child.stdin.end(input);
|
|
51
|
+
}) });
|
|
52
|
+
function execFileSync(file, ...rest) {
|
|
53
|
+
const { args, options } = split(rest);
|
|
54
|
+
const execOptions = hide(options);
|
|
55
|
+
if (args) return cp.execFileSync(file, args, execOptions);
|
|
56
|
+
return cp.execFileSync(file, execOptions);
|
|
57
|
+
}
|
|
58
|
+
function execSync(command, options) {
|
|
59
|
+
return cp.execSync(command, hide(options));
|
|
60
|
+
}
|
|
61
|
+
function spawn(file, ...rest) {
|
|
62
|
+
const { args, options } = split(rest);
|
|
63
|
+
const spawnOptions = hide(options);
|
|
64
|
+
if (args) return cp.spawn(file, args, spawnOptions);
|
|
65
|
+
return cp.spawn(file, spawnOptions);
|
|
66
|
+
}
|
|
67
|
+
var execFileAsync = promisify(execFile);
|
|
68
|
+
//#endregion
|
|
69
|
+
export { hide as a, execSync as i, execFileAsync as n, spawn as o, execFileSync as r, execFile as t };
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import path from "node:path";
|
|
2
|
+
//#region server/core/config-path-core.ts
|
|
3
|
+
function glimmervoidHomeDir(homeDirectory, env) {
|
|
4
|
+
if (env.GLIMMERVOID_HOME) return path.resolve(env.GLIMMERVOID_HOME);
|
|
5
|
+
return path.join(homeDirectory, ".glimmervoid");
|
|
6
|
+
}
|
|
7
|
+
function decideConfigPath({ env = {}, homeDir }, exists) {
|
|
8
|
+
const homePath = path.join(homeDir, "config.json");
|
|
9
|
+
if (env.GLIMMERVOID_CONFIG) {
|
|
10
|
+
const envPath = path.resolve(env.GLIMMERVOID_CONFIG);
|
|
11
|
+
if (exists(envPath)) return {
|
|
12
|
+
path: envPath,
|
|
13
|
+
source: "env",
|
|
14
|
+
homePath,
|
|
15
|
+
envPath
|
|
16
|
+
};
|
|
17
|
+
return {
|
|
18
|
+
path: null,
|
|
19
|
+
source: "env",
|
|
20
|
+
homePath,
|
|
21
|
+
envPath
|
|
22
|
+
};
|
|
23
|
+
}
|
|
24
|
+
if (exists(homePath)) return {
|
|
25
|
+
path: homePath,
|
|
26
|
+
source: "home",
|
|
27
|
+
homePath,
|
|
28
|
+
envPath: null
|
|
29
|
+
};
|
|
30
|
+
return {
|
|
31
|
+
path: null,
|
|
32
|
+
source: "none",
|
|
33
|
+
homePath,
|
|
34
|
+
envPath: null
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
//#endregion
|
|
38
|
+
export { glimmervoidHomeDir as n, decideConfigPath as t };
|