@agentvault/grok-bridge 0.2.1 → 0.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +125 -61
- package/dist/pending-invite.d.ts +24 -0
- package/dist/service/subcommand.d.ts.map +1 -1
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -9,9 +9,54 @@ var __export = (target, all) => {
|
|
|
9
9
|
__defProp(target, name, { get: all[name], enumerable: true });
|
|
10
10
|
};
|
|
11
11
|
|
|
12
|
+
// src/pending-invite.ts
|
|
13
|
+
import { existsSync, mkdirSync, chmodSync, readFileSync as readFileSync2, writeFileSync, rmSync } from "node:fs";
|
|
14
|
+
import { join as join5 } from "node:path";
|
|
15
|
+
function pendingInvitePath(dataDir) {
|
|
16
|
+
return join5(dataDir, PENDING_INVITE_FILE);
|
|
17
|
+
}
|
|
18
|
+
function writePendingInvite(dataDir, token) {
|
|
19
|
+
mkdirSync(dataDir, { recursive: true, mode: DIR_MODE2 });
|
|
20
|
+
chmodSync(dataDir, DIR_MODE2);
|
|
21
|
+
const p2 = pendingInvitePath(dataDir);
|
|
22
|
+
writeFileSync(p2, token, { mode: FILE_MODE2 });
|
|
23
|
+
chmodSync(p2, FILE_MODE2);
|
|
24
|
+
}
|
|
25
|
+
function readPendingInvite(dataDir) {
|
|
26
|
+
const p2 = pendingInvitePath(dataDir);
|
|
27
|
+
if (!existsSync(p2)) return void 0;
|
|
28
|
+
try {
|
|
29
|
+
const raw = readFileSync2(p2, "utf-8").trim();
|
|
30
|
+
return raw.length > 0 ? raw : void 0;
|
|
31
|
+
} catch {
|
|
32
|
+
return void 0;
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
function clearPendingInvite(dataDir) {
|
|
36
|
+
try {
|
|
37
|
+
rmSync(pendingInvitePath(dataDir), { force: true });
|
|
38
|
+
} catch {
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
function clearPendingInviteIfConsumed(dataDir, credsExist) {
|
|
42
|
+
if (!existsSync(pendingInvitePath(dataDir))) return false;
|
|
43
|
+
if (!credsExist(dataDir)) return false;
|
|
44
|
+
clearPendingInvite(dataDir);
|
|
45
|
+
return true;
|
|
46
|
+
}
|
|
47
|
+
var DIR_MODE2, FILE_MODE2, PENDING_INVITE_FILE;
|
|
48
|
+
var init_pending_invite = __esm({
|
|
49
|
+
"src/pending-invite.ts"() {
|
|
50
|
+
"use strict";
|
|
51
|
+
DIR_MODE2 = 448;
|
|
52
|
+
FILE_MODE2 = 384;
|
|
53
|
+
PENDING_INVITE_FILE = "pending-invite";
|
|
54
|
+
}
|
|
55
|
+
});
|
|
56
|
+
|
|
12
57
|
// src/config.ts
|
|
13
|
-
import { existsSync, readFileSync as
|
|
14
|
-
import { join as
|
|
58
|
+
import { existsSync as existsSync2, readFileSync as readFileSync3, mkdirSync as mkdirSync2, chmodSync as chmodSync2 } from "node:fs";
|
|
59
|
+
import { join as join6, resolve as resolve2, sep, dirname } from "node:path";
|
|
15
60
|
import { tmpdir } from "node:os";
|
|
16
61
|
function parseInfoFlags(argv) {
|
|
17
62
|
return {
|
|
@@ -32,14 +77,14 @@ function assertInstallableEntrypoint(entrypoint) {
|
|
|
32
77
|
}
|
|
33
78
|
function hasRecoverableBackup(dataDir) {
|
|
34
79
|
try {
|
|
35
|
-
const parsed = JSON.parse(
|
|
80
|
+
const parsed = JSON.parse(readFileSync3(join6(dataDir, BACKUP_FILE), "utf-8"));
|
|
36
81
|
return !!(parsed && parsed.deviceId && parsed.deviceJwt && parsed.sessions && Object.keys(parsed.sessions).length > 0);
|
|
37
82
|
} catch {
|
|
38
83
|
return false;
|
|
39
84
|
}
|
|
40
85
|
}
|
|
41
86
|
function hasPersistedCreds(dataDir) {
|
|
42
|
-
if (CRED_FILES.some((f2) =>
|
|
87
|
+
if (CRED_FILES.some((f2) => existsSync2(join6(dataDir, f2)))) return true;
|
|
43
88
|
return hasRecoverableBackup(dataDir);
|
|
44
89
|
}
|
|
45
90
|
function slugify2(name) {
|
|
@@ -47,19 +92,19 @@ function slugify2(name) {
|
|
|
47
92
|
}
|
|
48
93
|
function resolveDataDir(env) {
|
|
49
94
|
if (env.AV_DATA_DIR) return { dataDir: env.AV_DATA_DIR, source: "explicit" };
|
|
50
|
-
const base =
|
|
51
|
-
return { dataDir:
|
|
95
|
+
const base = join6(env.HOME ?? "", ".agentvault", "grok-room-bridge");
|
|
96
|
+
return { dataDir: join6(base, slugify2(env.AV_AGENT_NAME ?? "grok")), source: "per-agent" };
|
|
52
97
|
}
|
|
53
98
|
function loadConfig(env, argv = []) {
|
|
54
99
|
const { dataDir, source: dataDirSource } = resolveDataDir(env);
|
|
55
|
-
const inviteToken = (argv[0] && !argv[0].startsWith("-") ? argv[0] : "") || env.AV_INVITE_TOKEN || "";
|
|
100
|
+
const inviteToken = (argv[0] && !argv[0].startsWith("-") ? argv[0] : "") || env.AV_INVITE_TOKEN || readPendingInvite(dataDir) || "";
|
|
56
101
|
const unknownFlags = argv.filter((a2) => a2.startsWith("-") && !KNOWN_FLAGS.has(a2));
|
|
57
102
|
if (unknownFlags.length) {
|
|
58
103
|
throw new Error(
|
|
59
104
|
`unknown option(s): ${unknownFlags.join(", ")} \u2014 supported flags are ${[...KNOWN_FLAGS].join(", ")}`
|
|
60
105
|
);
|
|
61
106
|
}
|
|
62
|
-
const workspaceDir = env.AV_WORKSPACE_DIR ||
|
|
107
|
+
const workspaceDir = env.AV_WORKSPACE_DIR || join6(dirname(dataDir), "workspaces", slugify2(env.AV_AGENT_NAME ?? "grok"));
|
|
63
108
|
const wsReal = resolve2(workspaceDir);
|
|
64
109
|
const ddReal = resolve2(dataDir);
|
|
65
110
|
if (wsReal === ddReal || wsReal.startsWith(ddReal + sep) || ddReal.startsWith(wsReal + sep)) {
|
|
@@ -68,8 +113,8 @@ function loadConfig(env, argv = []) {
|
|
|
68
113
|
);
|
|
69
114
|
}
|
|
70
115
|
try {
|
|
71
|
-
|
|
72
|
-
|
|
116
|
+
mkdirSync2(workspaceDir, { recursive: true, mode: 448 });
|
|
117
|
+
chmodSync2(workspaceDir, 448);
|
|
73
118
|
} catch (e) {
|
|
74
119
|
throw new Error(
|
|
75
120
|
`Failed to create/secure the agent workspace at ${workspaceDir} (override with AV_WORKSPACE_DIR): ${e.message}`
|
|
@@ -99,7 +144,7 @@ function loadConfig(env, argv = []) {
|
|
|
99
144
|
workspaceDir,
|
|
100
145
|
grokPath: env.AV_GROK_PATH || void 0,
|
|
101
146
|
sandboxProfile: env.GROK_SANDBOX ?? "workspace",
|
|
102
|
-
fenceHome: env.AV_FENCE_HOME ||
|
|
147
|
+
fenceHome: env.AV_FENCE_HOME || join6(dataDir, "fence"),
|
|
103
148
|
apiKey: env.XAI_API_KEY || void 0,
|
|
104
149
|
systemPrompt: env.AV_SYSTEM_PROMPT || void 0
|
|
105
150
|
};
|
|
@@ -108,6 +153,7 @@ var INSTALL_FLAG, VERSION_FLAGS, HELP_FLAGS, KNOWN_FLAGS, CRED_FILES, BACKUP_FIL
|
|
|
108
153
|
var init_config = __esm({
|
|
109
154
|
"src/config.ts"() {
|
|
110
155
|
"use strict";
|
|
156
|
+
init_pending_invite();
|
|
111
157
|
INSTALL_FLAG = "--install";
|
|
112
158
|
VERSION_FLAGS = ["--version", "-v"];
|
|
113
159
|
HELP_FLAGS = ["--help", "-h"];
|
|
@@ -197,7 +243,7 @@ var init_launcher = __esm({
|
|
|
197
243
|
});
|
|
198
244
|
|
|
199
245
|
// src/service/spec.ts
|
|
200
|
-
import { join as
|
|
246
|
+
import { join as join10 } from "node:path";
|
|
201
247
|
function buildServiceSpec(cfg, opts) {
|
|
202
248
|
const env = {
|
|
203
249
|
AV_AGENT_NAME: cfg.agentName,
|
|
@@ -209,7 +255,7 @@ function buildServiceSpec(cfg, opts) {
|
|
|
209
255
|
if (cfg.workspaceDir) env.AV_WORKSPACE_DIR = cfg.workspaceDir;
|
|
210
256
|
if (cfg.roomFilter) env.AV_ROOM_ID = cfg.roomFilter;
|
|
211
257
|
if (cfg.grokPath) env.AV_GROK_PATH = cfg.grokPath;
|
|
212
|
-
const launcherPath =
|
|
258
|
+
const launcherPath = join10(cfg.dataDir, "launch-grok-bridge.sh");
|
|
213
259
|
return {
|
|
214
260
|
label: `dev.agentvault.grok-${slugify2(cfg.agentName)}`,
|
|
215
261
|
programArgs: [launcherPath],
|
|
@@ -217,8 +263,8 @@ function buildServiceSpec(cfg, opts) {
|
|
|
217
263
|
launcherScript: renderLauncher({ installPath: opts.path, entrypoint: opts.entrypoint }),
|
|
218
264
|
env,
|
|
219
265
|
workingDir: cfg.workspaceDir ? cfg.workspaceDir : opts.home,
|
|
220
|
-
logOut:
|
|
221
|
-
logErr:
|
|
266
|
+
logOut: join10(cfg.dataDir, "logs", "grok-bridge.log"),
|
|
267
|
+
logErr: join10(cfg.dataDir, "logs", "grok-bridge.error.log"),
|
|
222
268
|
keepAliveUnlessCleanExit: true,
|
|
223
269
|
runAtLoad: true
|
|
224
270
|
};
|
|
@@ -232,7 +278,7 @@ var init_spec = __esm({
|
|
|
232
278
|
});
|
|
233
279
|
|
|
234
280
|
// src/service/launchd.ts
|
|
235
|
-
import { dirname as dirname3, join as
|
|
281
|
+
import { dirname as dirname3, join as join11 } from "node:path";
|
|
236
282
|
function esc2(s2) {
|
|
237
283
|
return s2.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">");
|
|
238
284
|
}
|
|
@@ -279,7 +325,7 @@ var init_launchd = __esm({
|
|
|
279
325
|
}
|
|
280
326
|
deps;
|
|
281
327
|
plistPath(label) {
|
|
282
|
-
return
|
|
328
|
+
return join11(this.deps.home, "Library", "LaunchAgents", `${label}.plist`);
|
|
283
329
|
}
|
|
284
330
|
domain() {
|
|
285
331
|
return `gui/${this.deps.uid}`;
|
|
@@ -327,7 +373,7 @@ var init_launchd = __esm({
|
|
|
327
373
|
});
|
|
328
374
|
|
|
329
375
|
// src/service/systemd.ts
|
|
330
|
-
import { dirname as dirname4, join as
|
|
376
|
+
import { dirname as dirname4, join as join12 } from "node:path";
|
|
331
377
|
function q2(s2) {
|
|
332
378
|
const esc3 = s2.replace(/\\/g, "\\\\").replace(/"/g, '\\"').replace(/\n/g, "\\n").replace(/\r/g, "\\r").replace(/\t/g, "\\t").replace(/%/g, "%%");
|
|
333
379
|
return `"${esc3}"`;
|
|
@@ -364,7 +410,7 @@ var init_systemd = __esm({
|
|
|
364
410
|
}
|
|
365
411
|
deps;
|
|
366
412
|
unitPath(label) {
|
|
367
|
-
return
|
|
413
|
+
return join12(this.deps.home, ".config", "systemd", "user", `${label}.service`);
|
|
368
414
|
}
|
|
369
415
|
install(spec) {
|
|
370
416
|
const path2 = this.unitPath(spec.label);
|
|
@@ -404,7 +450,7 @@ __export(backend_exports, {
|
|
|
404
450
|
selectBackend: () => selectBackend
|
|
405
451
|
});
|
|
406
452
|
import { spawnSync } from "node:child_process";
|
|
407
|
-
import { mkdirSync as
|
|
453
|
+
import { mkdirSync as mkdirSync5, writeFileSync as writeFileSync3, rmSync as rmSync2, existsSync as existsSync4, chmodSync as chmodSync5 } from "node:fs";
|
|
408
454
|
import { userInfo } from "node:os";
|
|
409
455
|
function defaultDeps() {
|
|
410
456
|
return {
|
|
@@ -415,11 +461,11 @@ function defaultDeps() {
|
|
|
415
461
|
const r2 = spawnSync(cmd, args, { encoding: "utf8" });
|
|
416
462
|
return { code: r2.status ?? 1, stdout: r2.stdout ?? "" };
|
|
417
463
|
},
|
|
418
|
-
writeFile: (p2, d2) =>
|
|
419
|
-
mkdir: (p2) =>
|
|
420
|
-
chmod: (p2, m2) =>
|
|
421
|
-
rm: (p2) =>
|
|
422
|
-
exists: (p2) =>
|
|
464
|
+
writeFile: (p2, d2) => writeFileSync3(p2, d2),
|
|
465
|
+
mkdir: (p2) => mkdirSync5(p2, { recursive: true }),
|
|
466
|
+
chmod: (p2, m2) => chmodSync5(p2, m2),
|
|
467
|
+
rm: (p2) => rmSync2(p2, { force: true }),
|
|
468
|
+
exists: (p2) => existsSync4(p2)
|
|
423
469
|
};
|
|
424
470
|
}
|
|
425
471
|
function selectBackend(platform, deps) {
|
|
@@ -445,7 +491,13 @@ __export(subcommand_exports, {
|
|
|
445
491
|
maybeRunServiceSubcommand: () => maybeRunServiceSubcommand
|
|
446
492
|
});
|
|
447
493
|
function labelFor(env) {
|
|
448
|
-
|
|
494
|
+
const name = env.AV_AGENT_NAME?.trim();
|
|
495
|
+
if (!name) {
|
|
496
|
+
throw new Error(
|
|
497
|
+
"AV_AGENT_NAME is required \u2014 it names WHICH agent's service to act on. Re-run as: AV_AGENT_NAME=<agent-name> agentvault-grok-bridge <subcommand>"
|
|
498
|
+
);
|
|
499
|
+
}
|
|
500
|
+
return `dev.agentvault.grok-${slugify2(name)}`;
|
|
449
501
|
}
|
|
450
502
|
function maybeRunServiceSubcommand(argv, env, deps) {
|
|
451
503
|
const cmd = argv[2];
|
|
@@ -466,10 +518,9 @@ function maybeRunServiceSubcommand(argv, env, deps) {
|
|
|
466
518
|
try {
|
|
467
519
|
if (cmd === "install") {
|
|
468
520
|
const cfg = loadConfig(env, []);
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
);
|
|
521
|
+
const firstBoot = !hasPersistedCreds(cfg.dataDir) && !!cfg.inviteToken;
|
|
522
|
+
if (firstBoot) {
|
|
523
|
+
writePendingInvite(cfg.dataDir, cfg.inviteToken);
|
|
473
524
|
}
|
|
474
525
|
const spec = buildServiceSpec(cfg, {
|
|
475
526
|
entrypoint,
|
|
@@ -481,7 +532,13 @@ function maybeRunServiceSubcommand(argv, env, deps) {
|
|
|
481
532
|
});
|
|
482
533
|
backend.install(spec);
|
|
483
534
|
log(`installed service ${spec.label} \u2014 logs: ${spec.logErr}`);
|
|
484
|
-
|
|
535
|
+
if (firstBoot) {
|
|
536
|
+
log("now APPROVE the device in AgentVault \u2014 the service is waiting to enrol");
|
|
537
|
+
log("if it does not connect within a minute, the log above says why");
|
|
538
|
+
}
|
|
539
|
+
log(
|
|
540
|
+
`check it with: AV_AGENT_NAME=${cfg.agentName} agentvault-grok-bridge status`
|
|
541
|
+
);
|
|
485
542
|
} else if (cmd === "uninstall") {
|
|
486
543
|
const label = labelFor(env);
|
|
487
544
|
backend.uninstall(label);
|
|
@@ -509,6 +566,7 @@ var init_subcommand = __esm({
|
|
|
509
566
|
"src/service/subcommand.ts"() {
|
|
510
567
|
"use strict";
|
|
511
568
|
init_config();
|
|
569
|
+
init_pending_invite();
|
|
512
570
|
init_log();
|
|
513
571
|
init_spec();
|
|
514
572
|
init_backend();
|
|
@@ -521,12 +579,12 @@ var install_on_ready_exports = {};
|
|
|
521
579
|
__export(install_on_ready_exports, {
|
|
522
580
|
installOnReady: () => installOnReady
|
|
523
581
|
});
|
|
524
|
-
import { existsSync as
|
|
525
|
-
import { join as
|
|
582
|
+
import { existsSync as existsSync5, readFileSync as readFileSync4 } from "node:fs";
|
|
583
|
+
import { join as join13 } from "node:path";
|
|
526
584
|
function installOnReady(channel, cfg, deps) {
|
|
527
585
|
const hasCreds = deps.hasCreds ?? hasPersistedCreds;
|
|
528
|
-
const readLauncher = deps.readLauncher ?? ((p2) =>
|
|
529
|
-
const fenceAuthExists = deps.fenceAuthExists ?? ((home) =>
|
|
586
|
+
const readLauncher = deps.readLauncher ?? ((p2) => existsSync5(p2) ? readFileSync4(p2, "utf8") : void 0);
|
|
587
|
+
const fenceAuthExists = deps.fenceAuthExists ?? ((home) => existsSync5(join13(home, ".grok", "auth.json")));
|
|
530
588
|
let fired = false;
|
|
531
589
|
channel.on("ready", () => {
|
|
532
590
|
if (fired) return;
|
|
@@ -611,8 +669,8 @@ var init_install_on_ready = __esm({
|
|
|
611
669
|
|
|
612
670
|
// src/index.ts
|
|
613
671
|
import { spawn } from "node:child_process";
|
|
614
|
-
import { mkdirSync as
|
|
615
|
-
import { join as
|
|
672
|
+
import { mkdirSync as mkdirSync6 } from "node:fs";
|
|
673
|
+
import { join as join14 } from "node:path";
|
|
616
674
|
|
|
617
675
|
// ../plugin/dist/index.js
|
|
618
676
|
import * as nc from "node:crypto";
|
|
@@ -98229,28 +98287,29 @@ await init_index();
|
|
|
98229
98287
|
|
|
98230
98288
|
// src/index.ts
|
|
98231
98289
|
init_config();
|
|
98290
|
+
init_pending_invite();
|
|
98232
98291
|
init_log();
|
|
98233
98292
|
|
|
98234
98293
|
// src/fence-auth.ts
|
|
98235
|
-
import { copyFileSync, chmodSync as
|
|
98236
|
-
import { join as
|
|
98294
|
+
import { copyFileSync, chmodSync as chmodSync3, existsSync as existsSync3, mkdirSync as mkdirSync3 } from "node:fs";
|
|
98295
|
+
import { join as join7 } from "node:path";
|
|
98237
98296
|
function seedFenceCredential(opts) {
|
|
98238
98297
|
const log = opts.log ?? (() => {
|
|
98239
98298
|
});
|
|
98240
|
-
const fenceGrok =
|
|
98241
|
-
const fenceAuth =
|
|
98242
|
-
if (
|
|
98299
|
+
const fenceGrok = join7(opts.fenceHome, ".grok");
|
|
98300
|
+
const fenceAuth = join7(fenceGrok, "auth.json");
|
|
98301
|
+
if (existsSync3(fenceAuth)) {
|
|
98243
98302
|
log("[grok-bridge] fence credential already present; leaving it untouched");
|
|
98244
98303
|
return "already-present";
|
|
98245
98304
|
}
|
|
98246
|
-
const hostAuth =
|
|
98247
|
-
if (!
|
|
98305
|
+
const hostAuth = join7(opts.hostHome, ".grok", "auth.json");
|
|
98306
|
+
if (!existsSync3(hostAuth)) {
|
|
98248
98307
|
log("[grok-bridge] no host credential to seed (run `grok login`, or set XAI_API_KEY)");
|
|
98249
98308
|
return "no-host-credential";
|
|
98250
98309
|
}
|
|
98251
|
-
|
|
98310
|
+
mkdirSync3(fenceGrok, { recursive: true });
|
|
98252
98311
|
copyFileSync(hostAuth, fenceAuth);
|
|
98253
|
-
|
|
98312
|
+
chmodSync3(fenceAuth, 384);
|
|
98254
98313
|
log("[grok-bridge] seeded fence credential from the host grok login");
|
|
98255
98314
|
return "seeded";
|
|
98256
98315
|
}
|
|
@@ -98551,14 +98610,14 @@ var AcpConnection = class {
|
|
|
98551
98610
|
};
|
|
98552
98611
|
|
|
98553
98612
|
// src/grok-room-plugin.ts
|
|
98554
|
-
import { mkdirSync as
|
|
98555
|
-
import { join as
|
|
98613
|
+
import { mkdirSync as mkdirSync4, writeFileSync as writeFileSync2, chmodSync as chmodSync4 } from "node:fs";
|
|
98614
|
+
import { join as join8 } from "node:path";
|
|
98556
98615
|
var SERVER_KEY = "room";
|
|
98557
98616
|
var GROK_ROOM_SAY_TOOL_NAME = `${SERVER_KEY}__say`;
|
|
98558
98617
|
function writeRoomPluginHttp(dir, url3) {
|
|
98559
|
-
|
|
98560
|
-
|
|
98561
|
-
|
|
98618
|
+
mkdirSync4(join8(dir, ".claude-plugin"), { recursive: true });
|
|
98619
|
+
writeFileSync2(
|
|
98620
|
+
join8(dir, ".claude-plugin", "plugin.json"),
|
|
98562
98621
|
JSON.stringify(
|
|
98563
98622
|
{
|
|
98564
98623
|
name: "avroom",
|
|
@@ -98570,12 +98629,12 @@ function writeRoomPluginHttp(dir, url3) {
|
|
|
98570
98629
|
2
|
|
98571
98630
|
) + "\n"
|
|
98572
98631
|
);
|
|
98573
|
-
|
|
98574
|
-
|
|
98632
|
+
writeFileSync2(
|
|
98633
|
+
join8(dir, ".mcp.json"),
|
|
98575
98634
|
JSON.stringify({ mcpServers: { [SERVER_KEY]: { type: "http", url: url3 } } }, null, 2) + "\n",
|
|
98576
98635
|
{ mode: 384 }
|
|
98577
98636
|
);
|
|
98578
|
-
|
|
98637
|
+
chmodSync4(join8(dir, ".mcp.json"), 384);
|
|
98579
98638
|
}
|
|
98580
98639
|
|
|
98581
98640
|
// src/grok-driver.ts
|
|
@@ -98710,7 +98769,7 @@ var GrokDriver = class {
|
|
|
98710
98769
|
};
|
|
98711
98770
|
|
|
98712
98771
|
// src/grok-spawn.ts
|
|
98713
|
-
import { join as
|
|
98772
|
+
import { join as join9 } from "node:path";
|
|
98714
98773
|
function grokSpawnArgs(opts) {
|
|
98715
98774
|
const args = ["agent", "--no-leader"];
|
|
98716
98775
|
if (opts.model) args.push("--model", opts.model);
|
|
@@ -98719,7 +98778,7 @@ function grokSpawnArgs(opts) {
|
|
|
98719
98778
|
const env = {
|
|
98720
98779
|
PATH: process.env.PATH,
|
|
98721
98780
|
HOME: opts.fenceHome,
|
|
98722
|
-
GROK_HOME:
|
|
98781
|
+
GROK_HOME: join9(opts.fenceHome, ".grok")
|
|
98723
98782
|
};
|
|
98724
98783
|
if (opts.apiKey) env.XAI_API_KEY = opts.apiKey;
|
|
98725
98784
|
return { command: opts.grokPath ?? "grok", args, env, cwd: opts.workspaceDir };
|
|
@@ -99084,7 +99143,7 @@ async function main() {
|
|
|
99084
99143
|
const info = parseInfoFlags(process.argv.slice(2));
|
|
99085
99144
|
if (info.showVersion || info.showHelp) {
|
|
99086
99145
|
const version2 = buildClientVersion2(
|
|
99087
|
-
true ? "0.
|
|
99146
|
+
true ? "0.3.1" : void 0
|
|
99088
99147
|
);
|
|
99089
99148
|
if (info.showVersion) printLine(version2);
|
|
99090
99149
|
if (info.showHelp) {
|
|
@@ -99128,8 +99187,8 @@ async function main() {
|
|
|
99128
99187
|
const { selectBackend: selectBackend2 } = await Promise.resolve().then(() => (init_backend(), backend_exports));
|
|
99129
99188
|
selectBackend2(process.platform);
|
|
99130
99189
|
}
|
|
99131
|
-
|
|
99132
|
-
|
|
99190
|
+
mkdirSync6(cfg.workspaceDir, { recursive: true });
|
|
99191
|
+
mkdirSync6(cfg.fenceHome, { recursive: true });
|
|
99133
99192
|
seedFenceCredential({
|
|
99134
99193
|
fenceHome: cfg.fenceHome,
|
|
99135
99194
|
hostHome: process.env.HOME ?? "",
|
|
@@ -99142,7 +99201,7 @@ async function main() {
|
|
|
99142
99201
|
agentName: cfg.agentName,
|
|
99143
99202
|
platform: "node",
|
|
99144
99203
|
clientVersion: buildClientVersion2(
|
|
99145
|
-
true ? "0.
|
|
99204
|
+
true ? "0.3.1" : void 0
|
|
99146
99205
|
)
|
|
99147
99206
|
});
|
|
99148
99207
|
channelRef = channel;
|
|
@@ -99163,7 +99222,7 @@ async function main() {
|
|
|
99163
99222
|
},
|
|
99164
99223
|
log: (m2) => logLine(m2)
|
|
99165
99224
|
});
|
|
99166
|
-
const pluginDir =
|
|
99225
|
+
const pluginDir = join14(cfg.fenceHome, "av-room-plugin");
|
|
99167
99226
|
writeRoomPluginHttp(pluginDir, mcp.url);
|
|
99168
99227
|
const spawnSpec = grokSpawnArgs({
|
|
99169
99228
|
grokPath: cfg.grokPath,
|
|
@@ -99228,6 +99287,11 @@ async function main() {
|
|
|
99228
99287
|
log: (m2) => logLine("[grok-bridge] " + m2),
|
|
99229
99288
|
onTerminal: (_reason, o2) => void shutdown(o2.restart ? 1 : 0)
|
|
99230
99289
|
});
|
|
99290
|
+
channel.on("ready", () => {
|
|
99291
|
+
if (clearPendingInviteIfConsumed(cfg.dataDir, hasPersistedCreds)) {
|
|
99292
|
+
logLine("[grok-bridge] enrolled \u2014 pending invite consumed and removed");
|
|
99293
|
+
}
|
|
99294
|
+
});
|
|
99231
99295
|
if (cfg.installAfterEnroll) {
|
|
99232
99296
|
const { installOnReady: installOnReady2 } = await Promise.resolve().then(() => (init_install_on_ready(), install_on_ready_exports));
|
|
99233
99297
|
installOnReady2(channel, cfg, {
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
export declare function pendingInvitePath(dataDir: string): string;
|
|
2
|
+
/** Persist the token for the service's first boot. Owner-only, unconditionally. */
|
|
3
|
+
export declare function writePendingInvite(dataDir: string, token: string): void;
|
|
4
|
+
/** The pending token, or undefined when there is none to consume. */
|
|
5
|
+
export declare function readPendingInvite(dataDir: string): string | undefined;
|
|
6
|
+
/** Remove it. Idempotent: nothing to remove is a success, not an error. */
|
|
7
|
+
export declare function clearPendingInvite(dataDir: string): void;
|
|
8
|
+
/**
|
|
9
|
+
* Delete the pending invite once there is EVIDENCE it was consumed — i.e.
|
|
10
|
+
* credentials have actually persisted to the data dir.
|
|
11
|
+
*
|
|
12
|
+
* Timing is the whole design here. Deleting on READ (inside loadConfig) would
|
|
13
|
+
* throw the token away before enrolment finished, so a process that died in
|
|
14
|
+
* between would leave a service that can never enrol and a customer whose
|
|
15
|
+
* single-use invite is gone. Never deleting leaves a credential on disk long
|
|
16
|
+
* after it is useless.
|
|
17
|
+
*
|
|
18
|
+
* `credsExist` is injected so the caller supplies `hasPersistedCreds` and this
|
|
19
|
+
* module stays free of a config import cycle.
|
|
20
|
+
*
|
|
21
|
+
* @returns true when a file was actually removed.
|
|
22
|
+
*/
|
|
23
|
+
export declare function clearPendingInviteIfConsumed(dataDir: string, credsExist: (dataDir: string) => boolean): boolean;
|
|
24
|
+
//# sourceMappingURL=pending-invite.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"subcommand.d.ts","sourceRoot":"","sources":["../../src/service/subcommand.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"subcommand.d.ts","sourceRoot":"","sources":["../../src/service/subcommand.ts"],"names":[],"mappings":"AAIA,OAAO,EAAiB,KAAK,cAAc,EAAE,MAAM,cAAc,CAAC;AAElE,MAAM,WAAW,cAAc;IAC7B,OAAO,CAAC,EAAE,cAAc,CAAC;IACzB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,GAAG,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,IAAI,CAAC;CAC7B;AAkCD;;uFAEuF;AACvF,wBAAgB,yBAAyB,CACvC,IAAI,EAAE,MAAM,EAAE,EACd,GAAG,EAAE,MAAM,CAAC,UAAU,EACtB,IAAI,CAAC,EAAE,cAAc,GACpB,OAAO,CAkHT"}
|
package/package.json
CHANGED