@brainbase-labs/cli 0.25.0-eng1209.9 → 0.26.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/index.js +984 -494
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -31708,8 +31708,8 @@ var require_utils = __commonJS((exports, module) => {
|
|
|
31708
31708
|
}
|
|
31709
31709
|
return ind;
|
|
31710
31710
|
}
|
|
31711
|
-
function removeDotSegments(
|
|
31712
|
-
let input =
|
|
31711
|
+
function removeDotSegments(path89) {
|
|
31712
|
+
let input = path89;
|
|
31713
31713
|
const output = [];
|
|
31714
31714
|
let nextSlash = -1;
|
|
31715
31715
|
let len = 0;
|
|
@@ -31952,8 +31952,8 @@ var require_schemes = __commonJS((exports, module) => {
|
|
|
31952
31952
|
wsComponent.secure = undefined;
|
|
31953
31953
|
}
|
|
31954
31954
|
if (wsComponent.resourceName) {
|
|
31955
|
-
const [
|
|
31956
|
-
wsComponent.path =
|
|
31955
|
+
const [path89, query] = wsComponent.resourceName.split("?");
|
|
31956
|
+
wsComponent.path = path89 && path89 !== "/" ? path89 : undefined;
|
|
31957
31957
|
wsComponent.query = query;
|
|
31958
31958
|
wsComponent.resourceName = undefined;
|
|
31959
31959
|
}
|
|
@@ -35141,7 +35141,7 @@ var require_dist2 = __commonJS((exports, module) => {
|
|
|
35141
35141
|
});
|
|
35142
35142
|
|
|
35143
35143
|
// src/index.ts
|
|
35144
|
-
var
|
|
35144
|
+
var import_picocolors53 = __toESM(require_picocolors(), 1);
|
|
35145
35145
|
import process14 from "node:process";
|
|
35146
35146
|
import fs83 from "node:fs";
|
|
35147
35147
|
|
|
@@ -36008,7 +36008,7 @@ function padStart(s, n) {
|
|
|
36008
36008
|
// package.json
|
|
36009
36009
|
var package_default = {
|
|
36010
36010
|
name: "@brainbase-labs/cli",
|
|
36011
|
-
version: "0.
|
|
36011
|
+
version: "0.26.0",
|
|
36012
36012
|
description: "Pack, share, and install agent templates across harnesses (Claude Code, Codex, ...).",
|
|
36013
36013
|
type: "module",
|
|
36014
36014
|
bin: {
|
|
@@ -61950,6 +61950,7 @@ import fs66 from "node:fs";
|
|
|
61950
61950
|
// src/core/agent-manifest.ts
|
|
61951
61951
|
import path73 from "node:path";
|
|
61952
61952
|
import fs65 from "node:fs";
|
|
61953
|
+
import { randomBytes } from "node:crypto";
|
|
61953
61954
|
var import_yaml2 = __toESM(require_dist(), 1);
|
|
61954
61955
|
var AGENT_MANIFEST_FILE = "brainbase.agent.yaml";
|
|
61955
61956
|
var LEGACY_AGENT_MANIFEST_FILE = "brainbase.yaml";
|
|
@@ -62121,30 +62122,54 @@ function existingManifestPath(cwd2) {
|
|
|
62121
62122
|
function hasManifest(cwd2) {
|
|
62122
62123
|
return existingManifestPath(cwd2) !== null;
|
|
62123
62124
|
}
|
|
62124
|
-
function
|
|
62125
|
-
const p2 = existingManifestPath(cwd2);
|
|
62126
|
-
if (!p2)
|
|
62127
|
-
return null;
|
|
62128
|
-
const raw = fs65.readFileSync(p2, "utf8");
|
|
62125
|
+
function parseManifest(raw, label = AGENT_MANIFEST_FILE) {
|
|
62129
62126
|
let parsed;
|
|
62130
62127
|
try {
|
|
62131
62128
|
parsed = import_yaml2.default.parse(raw);
|
|
62132
62129
|
} catch (err) {
|
|
62133
|
-
throw new Error(`${
|
|
62130
|
+
throw new Error(`${label} is not valid YAML: ${err.message}`);
|
|
62134
62131
|
}
|
|
62135
62132
|
const result2 = AgentManifestSchema.safeParse(parsed);
|
|
62136
62133
|
if (!result2.success) {
|
|
62137
|
-
throw new Error(`${
|
|
62134
|
+
throw new Error(`${label} is invalid: ${result2.error.issues.map((i) => `${i.path.join(".") || "(root)"} — ${i.message}`).join("; ")}`);
|
|
62138
62135
|
}
|
|
62139
62136
|
return result2.data;
|
|
62140
62137
|
}
|
|
62141
|
-
function
|
|
62138
|
+
function readManifest(cwd2) {
|
|
62139
|
+
const p2 = existingManifestPath(cwd2);
|
|
62140
|
+
if (!p2)
|
|
62141
|
+
return null;
|
|
62142
|
+
return parseManifest(fs65.readFileSync(p2, "utf8"), path73.basename(p2));
|
|
62143
|
+
}
|
|
62144
|
+
function renderManifest(manifest) {
|
|
62142
62145
|
const doc = new import_yaml2.default.Document;
|
|
62143
62146
|
doc.contents = manifest;
|
|
62144
62147
|
doc.commentBefore = ` brainbase.agent.yaml — declarative agent manifest.
|
|
62145
62148
|
` + " Committed to source control. Edit by hand, then `brainbase agent push`.";
|
|
62146
|
-
|
|
62147
|
-
|
|
62149
|
+
return String(doc);
|
|
62150
|
+
}
|
|
62151
|
+
function writeManifestText(cwd2, body) {
|
|
62152
|
+
const target = manifestPath(cwd2);
|
|
62153
|
+
const tmp = `${target}.${randomBytes(8).toString("hex")}.tmp`;
|
|
62154
|
+
const fd = fs65.openSync(tmp, "wx");
|
|
62155
|
+
let closed = false;
|
|
62156
|
+
try {
|
|
62157
|
+
fs65.writeFileSync(fd, body, "utf8");
|
|
62158
|
+
fs65.closeSync(fd);
|
|
62159
|
+
closed = true;
|
|
62160
|
+
fs65.renameSync(tmp, target);
|
|
62161
|
+
} catch (err) {
|
|
62162
|
+
if (!closed) {
|
|
62163
|
+
try {
|
|
62164
|
+
fs65.closeSync(fd);
|
|
62165
|
+
} catch {}
|
|
62166
|
+
}
|
|
62167
|
+
fs65.rmSync(tmp, { force: true });
|
|
62168
|
+
throw err;
|
|
62169
|
+
}
|
|
62170
|
+
}
|
|
62171
|
+
function writeManifest(cwd2, manifest) {
|
|
62172
|
+
writeManifestText(cwd2, renderManifest(manifest));
|
|
62148
62173
|
}
|
|
62149
62174
|
function resolveInstructionsPath(cwd2, manifest) {
|
|
62150
62175
|
if (!manifest.instructions?.file)
|
|
@@ -62318,7 +62343,9 @@ var AgentMetaSnapshotSchema = exports_external.object({
|
|
|
62318
62343
|
tagline: exports_external.string().nullish().transform((v3) => v3 ?? undefined),
|
|
62319
62344
|
entrypoint: exports_external.string().optional(),
|
|
62320
62345
|
machine_kind: exports_external.string().min(1).optional(),
|
|
62321
|
-
default_model: exports_external.string().nullable().optional()
|
|
62346
|
+
default_model: exports_external.string().nullable().optional(),
|
|
62347
|
+
memory: exports_external.boolean().nullable().optional(),
|
|
62348
|
+
browser: exports_external.boolean().nullable().optional()
|
|
62322
62349
|
});
|
|
62323
62350
|
var SyncStateSchema = exports_external.object({
|
|
62324
62351
|
schemaVersion: exports_external.literal(1),
|
|
@@ -63518,7 +63545,7 @@ function runHarnessInstall(harnessId, components, opts, agentName) {
|
|
|
63518
63545
|
}
|
|
63519
63546
|
|
|
63520
63547
|
// src/cli/agent.ts
|
|
63521
|
-
var
|
|
63548
|
+
var import_picocolors38 = __toESM(require_picocolors(), 1);
|
|
63522
63549
|
|
|
63523
63550
|
// src/cli/agent-pull.ts
|
|
63524
63551
|
import { spawn as spawn2 } from "node:child_process";
|
|
@@ -63931,9 +63958,44 @@ function diffAgentMeta(manifestMeta, lockMeta, cloudMeta) {
|
|
|
63931
63958
|
cloudChanged: !!cloudMeta && !!lockMeta && !eq(cloudMeta, lockMeta)
|
|
63932
63959
|
};
|
|
63933
63960
|
}
|
|
63961
|
+
var WRITABLE_CAPABILITIES = ["memory", "browser"];
|
|
63962
|
+
var MIRRORED_CAPABILITIES = ["slack", "meeting", "github"];
|
|
63963
|
+
function manifestConfigState(manifest) {
|
|
63964
|
+
return {
|
|
63965
|
+
...manifest.machine_kind !== undefined ? { machine_kind: manifest.machine_kind } : {},
|
|
63966
|
+
...hasOwn(manifest, "default_model") ? { default_model: manifest.default_model ?? null } : {},
|
|
63967
|
+
...manifest.capabilities?.memory !== undefined ? { memory: manifest.capabilities.memory } : {},
|
|
63968
|
+
...manifest.capabilities?.browser !== undefined ? { browser: manifest.capabilities.browser } : {}
|
|
63969
|
+
};
|
|
63970
|
+
}
|
|
63971
|
+
function cloudConfigState(agent) {
|
|
63972
|
+
return {
|
|
63973
|
+
...agent.machine_kind !== undefined ? { machine_kind: agent.machine_kind } : {},
|
|
63974
|
+
...hasOwn(agent, "default_model") ? { default_model: agent.default_model ?? null } : {},
|
|
63975
|
+
...agent.memory_enabled !== undefined ? { memory: agent.memory_enabled } : {},
|
|
63976
|
+
...agent.browser_enabled !== undefined ? { browser: agent.browser_enabled } : {}
|
|
63977
|
+
};
|
|
63978
|
+
}
|
|
63934
63979
|
function hasOwn(value, key2) {
|
|
63935
63980
|
return !!value && Object.prototype.hasOwnProperty.call(value, key2);
|
|
63936
63981
|
}
|
|
63982
|
+
function staleConnectionMirrors(manifest, cloud) {
|
|
63983
|
+
const actualByName = {
|
|
63984
|
+
slack: cloud.slack_connected,
|
|
63985
|
+
meeting: cloud.meeting_connected,
|
|
63986
|
+
github: cloud.github_connected
|
|
63987
|
+
};
|
|
63988
|
+
const stale = [];
|
|
63989
|
+
for (const name of MIRRORED_CAPABILITIES) {
|
|
63990
|
+
const authored = manifest.capabilities?.[name];
|
|
63991
|
+
const actual = actualByName[name];
|
|
63992
|
+
if (authored === undefined || actual === undefined)
|
|
63993
|
+
continue;
|
|
63994
|
+
if (authored !== actual)
|
|
63995
|
+
stale.push({ name, authored, actual });
|
|
63996
|
+
}
|
|
63997
|
+
return stale;
|
|
63998
|
+
}
|
|
63937
63999
|
function diffAgentConfig(manifest, lock, cloud) {
|
|
63938
64000
|
const unsupported = [];
|
|
63939
64001
|
const machineSupported = cloud.machine_kind !== undefined;
|
|
@@ -63948,42 +64010,94 @@ function diffAgentConfig(manifest, lock, cloud) {
|
|
|
63948
64010
|
const machineLocalChanged = manifest.machine_kind !== undefined && machineSupported && (lock?.machine_kind !== undefined ? manifest.machine_kind !== lock.machine_kind && manifest.machine_kind !== cloud.machine_kind : manifest.machine_kind !== cloud.machine_kind);
|
|
63949
64011
|
const machineCloudChanged = lock?.machine_kind !== undefined && machineSupported && lock.machine_kind !== cloud.machine_kind && manifest.machine_kind !== cloud.machine_kind;
|
|
63950
64012
|
const machineConverged = manifest.machine_kind !== undefined && machineSupported && manifest.machine_kind === cloud.machine_kind && (lock?.machine_kind === undefined || lock.machine_kind !== cloud.machine_kind);
|
|
63951
|
-
|
|
63952
|
-
|
|
63953
|
-
|
|
63954
|
-
|
|
63955
|
-
|
|
63956
|
-
|
|
63957
|
-
|
|
63958
|
-
|
|
63959
|
-
if (localAuthored) {
|
|
63960
|
-
const localValue = manifest.default_model ?? null;
|
|
63961
|
-
if (lockSupported) {
|
|
63962
|
-
const lockValue = lock?.default_model ?? null;
|
|
63963
|
-
const localMoved = localValue !== lockValue;
|
|
63964
|
-
const cloudMoved = cloudValue !== lockValue;
|
|
63965
|
-
defaultModelConflict = localMoved && cloudMoved && localValue !== cloudValue;
|
|
63966
|
-
defaultModelLocalChanged = localMoved && localValue !== cloudValue;
|
|
63967
|
-
defaultModelCloudChanged = cloudMoved && localValue !== cloudValue;
|
|
63968
|
-
defaultModelConverged = localMoved && cloudMoved && localValue === cloudValue;
|
|
63969
|
-
} else {
|
|
63970
|
-
defaultModelLocalChanged = localValue !== cloudValue;
|
|
63971
|
-
defaultModelConverged = localValue === cloudValue;
|
|
63972
|
-
}
|
|
63973
|
-
} else if (lockSupported) {
|
|
63974
|
-
defaultModelCloudChanged = cloudValue !== (lock?.default_model ?? null);
|
|
63975
|
-
}
|
|
64013
|
+
const defaultModel = threeWayField(defaultModelSupported, manifest.default_model, cloud.default_model, lock, "default_model");
|
|
64014
|
+
const memory = threeWayField(hasOwn(cloud, "memory"), manifest.memory, cloud.memory, lock, "memory");
|
|
64015
|
+
const browser = threeWayField(hasOwn(cloud, "browser"), manifest.browser, cloud.browser, lock, "browser");
|
|
64016
|
+
if (manifest.memory !== undefined && !hasOwn(cloud, "memory")) {
|
|
64017
|
+
unsupported.push("memory");
|
|
64018
|
+
}
|
|
64019
|
+
if (manifest.browser !== undefined && !hasOwn(cloud, "browser")) {
|
|
64020
|
+
unsupported.push("browser");
|
|
63976
64021
|
}
|
|
63977
64022
|
return {
|
|
63978
64023
|
unsupported,
|
|
63979
64024
|
machineMismatch,
|
|
63980
64025
|
machineLocalChanged,
|
|
63981
64026
|
machineCloudChanged,
|
|
63982
|
-
defaultModelLocalChanged,
|
|
63983
|
-
defaultModelCloudChanged,
|
|
63984
|
-
defaultModelConflict,
|
|
63985
|
-
|
|
64027
|
+
defaultModelLocalChanged: defaultModel.localChanged,
|
|
64028
|
+
defaultModelCloudChanged: defaultModel.cloudChanged,
|
|
64029
|
+
defaultModelConflict: defaultModel.conflict,
|
|
64030
|
+
memory,
|
|
64031
|
+
browser,
|
|
64032
|
+
baselineConverged: machineConverged || defaultModel.converged || memory.converged || browser.converged
|
|
64033
|
+
};
|
|
64034
|
+
}
|
|
64035
|
+
function threeWayField(supported, authored, cloudRaw, lock, key2) {
|
|
64036
|
+
const result2 = {
|
|
64037
|
+
localChanged: false,
|
|
64038
|
+
cloudChanged: false,
|
|
64039
|
+
conflict: false,
|
|
64040
|
+
converged: false
|
|
63986
64041
|
};
|
|
64042
|
+
if (!supported)
|
|
64043
|
+
return result2;
|
|
64044
|
+
const cloudValue = cloudRaw ?? null;
|
|
64045
|
+
const lockSupported = hasOwn(lock, key2);
|
|
64046
|
+
const lockValue = lock?.[key2] ?? null;
|
|
64047
|
+
if (authored === undefined) {
|
|
64048
|
+
if (lockSupported)
|
|
64049
|
+
result2.cloudChanged = cloudValue !== lockValue;
|
|
64050
|
+
return result2;
|
|
64051
|
+
}
|
|
64052
|
+
const localValue = authored ?? null;
|
|
64053
|
+
if (!lockSupported) {
|
|
64054
|
+
result2.localChanged = localValue !== cloudValue;
|
|
64055
|
+
result2.converged = localValue === cloudValue;
|
|
64056
|
+
return result2;
|
|
64057
|
+
}
|
|
64058
|
+
const localMoved = localValue !== lockValue;
|
|
64059
|
+
const cloudMoved = cloudValue !== lockValue;
|
|
64060
|
+
result2.conflict = localMoved && cloudMoved && localValue !== cloudValue;
|
|
64061
|
+
result2.localChanged = localMoved && localValue !== cloudValue;
|
|
64062
|
+
result2.cloudChanged = cloudMoved && localValue !== cloudValue;
|
|
64063
|
+
result2.converged = localMoved && cloudMoved && localValue === cloudValue;
|
|
64064
|
+
return result2;
|
|
64065
|
+
}
|
|
64066
|
+
|
|
64067
|
+
// src/core/capability-baseline.ts
|
|
64068
|
+
var CLOUD_KEY = {
|
|
64069
|
+
memory: "memory_enabled",
|
|
64070
|
+
browser: "browser_enabled"
|
|
64071
|
+
};
|
|
64072
|
+
function carryForward(previous, name) {
|
|
64073
|
+
return previous && Object.prototype.hasOwnProperty.call(previous, name) ? { [name]: previous[name] ?? null } : {};
|
|
64074
|
+
}
|
|
64075
|
+
function capabilityBaseline(cloudAgent, previous) {
|
|
64076
|
+
const out = {};
|
|
64077
|
+
for (const name of WRITABLE_CAPABILITIES) {
|
|
64078
|
+
const fromCloud = cloudAgent?.[CLOUD_KEY[name]];
|
|
64079
|
+
if (fromCloud !== undefined) {
|
|
64080
|
+
out[name] = fromCloud;
|
|
64081
|
+
continue;
|
|
64082
|
+
}
|
|
64083
|
+
Object.assign(out, carryForward(previous, name));
|
|
64084
|
+
}
|
|
64085
|
+
return out;
|
|
64086
|
+
}
|
|
64087
|
+
function capabilityBaselineAfterPush(cloudAgent, previous, diff2) {
|
|
64088
|
+
const out = {};
|
|
64089
|
+
for (const name of WRITABLE_CAPABILITIES) {
|
|
64090
|
+
if (diff2[name].cloudChanged && !diff2[name].localChanged) {
|
|
64091
|
+
Object.assign(out, carryForward(previous, name));
|
|
64092
|
+
continue;
|
|
64093
|
+
}
|
|
64094
|
+
const fromCloud = cloudAgent[CLOUD_KEY[name]];
|
|
64095
|
+
if (fromCloud !== undefined)
|
|
64096
|
+
out[name] = fromCloud;
|
|
64097
|
+
else
|
|
64098
|
+
Object.assign(out, carryForward(previous, name));
|
|
64099
|
+
}
|
|
64100
|
+
return out;
|
|
63987
64101
|
}
|
|
63988
64102
|
|
|
63989
64103
|
// src/core/secrets-env.ts
|
|
@@ -64650,7 +64764,8 @@ async function runAgentPull(cwd2, args) {
|
|
|
64650
64764
|
tagline: cloudAgent.tagline,
|
|
64651
64765
|
...cloudAgent.entrypoint ? { entrypoint: cloudAgent.entrypoint.trim() } : {},
|
|
64652
64766
|
...cloudAgent.machine_kind ? { machine_kind: cloudAgent.machine_kind } : lock?.agentMeta?.machine_kind ? { machine_kind: lock.agentMeta.machine_kind } : {},
|
|
64653
|
-
...Object.prototype.hasOwnProperty.call(cloudAgent, "default_model") ? { default_model: cloudAgent.default_model ?? null } : Object.prototype.hasOwnProperty.call(lock?.agentMeta ?? {}, "default_model") ? { default_model: lock.agentMeta.default_model ?? null } : {}
|
|
64767
|
+
...Object.prototype.hasOwnProperty.call(cloudAgent, "default_model") ? { default_model: cloudAgent.default_model ?? null } : Object.prototype.hasOwnProperty.call(lock?.agentMeta ?? {}, "default_model") ? { default_model: lock.agentMeta.default_model ?? null } : {},
|
|
64768
|
+
...capabilityBaseline(cloudAgent, lock?.agentMeta)
|
|
64654
64769
|
}
|
|
64655
64770
|
};
|
|
64656
64771
|
writeSyncState(cwd2, newState);
|
|
@@ -64941,7 +65056,8 @@ function buildLockFromCloud(agent_id, cloud, prev, cloudAgent) {
|
|
|
64941
65056
|
tagline: cloudAgent.tagline,
|
|
64942
65057
|
...cloudAgent.entrypoint ? { entrypoint: cloudAgent.entrypoint.trim() } : {},
|
|
64943
65058
|
...cloudAgent.machine_kind ? { machine_kind: cloudAgent.machine_kind } : prev?.agentMeta?.machine_kind ? { machine_kind: prev.agentMeta.machine_kind } : {},
|
|
64944
|
-
...Object.prototype.hasOwnProperty.call(cloudAgent, "default_model") ? { default_model: cloudAgent.default_model ?? null } : Object.prototype.hasOwnProperty.call(prev?.agentMeta ?? {}, "default_model") ? { default_model: prev.agentMeta.default_model ?? null } : {}
|
|
65059
|
+
...Object.prototype.hasOwnProperty.call(cloudAgent, "default_model") ? { default_model: cloudAgent.default_model ?? null } : Object.prototype.hasOwnProperty.call(prev?.agentMeta ?? {}, "default_model") ? { default_model: prev.agentMeta.default_model ?? null } : {},
|
|
65060
|
+
...capabilityBaseline(cloudAgent, prev?.agentMeta)
|
|
64945
65061
|
} : prev?.agentMeta
|
|
64946
65062
|
};
|
|
64947
65063
|
}
|
|
@@ -65289,13 +65405,25 @@ async function runAgentPush(cwd2, args) {
|
|
|
65289
65405
|
lock: lock?.components ?? [],
|
|
65290
65406
|
cloud: cloud.components
|
|
65291
65407
|
});
|
|
65292
|
-
const config = diffAgentConfig(manifest, lock?.agentMeta, cloudAgent);
|
|
65408
|
+
const config = diffAgentConfig(manifestConfigState(manifest), lock?.agentMeta, cloudConfigState(cloudAgent));
|
|
65293
65409
|
if (config.unsupported.length > 0) {
|
|
65294
65410
|
f2.error(`This control plane does not support declarative ${config.unsupported.join(" / ")} config.`);
|
|
65295
65411
|
f2.info(`Use the MAS control plane, then run ${import_picocolors28.default.cyan("brainbase agent pull")} before retrying.`);
|
|
65296
65412
|
process.exitCode = 1;
|
|
65297
65413
|
return;
|
|
65298
65414
|
}
|
|
65415
|
+
const staleMirrors = staleConnectionMirrors(manifest, cloudAgent);
|
|
65416
|
+
if (staleMirrors.length > 0) {
|
|
65417
|
+
f2.error(`This manifest's connection state is out of date: ${staleMirrors.map((m3) => `${m3.name} says ${m3.authored}, actually ${m3.actual}`).join("; ")}.`);
|
|
65418
|
+
f2.info(`Run ${import_picocolors28.default.cyan("brainbase agent pull")} to refresh it. These are reported by the cloud, not set from the manifest.`);
|
|
65419
|
+
for (const m3 of staleMirrors) {
|
|
65420
|
+
if (!m3.actual) {
|
|
65421
|
+
f2.info(`To actually connect ${m3.name}, run ${import_picocolors28.default.cyan(`brainbase agent connect ${m3.name}`)}.`);
|
|
65422
|
+
}
|
|
65423
|
+
}
|
|
65424
|
+
process.exitCode = 1;
|
|
65425
|
+
return;
|
|
65426
|
+
}
|
|
65299
65427
|
if (config.machineMismatch) {
|
|
65300
65428
|
if (config.machineCloudChanged && !config.machineLocalChanged) {
|
|
65301
65429
|
f2.error("Cannot push: machine_kind changed on the cloud.");
|
|
@@ -65316,6 +65444,17 @@ async function runAgentPush(cwd2, args) {
|
|
|
65316
65444
|
if (config.defaultModelConflict && args.force) {
|
|
65317
65445
|
f2.warn(`${import_picocolors28.default.yellow("--force")}: overwriting the cloud default_model with the local value.`);
|
|
65318
65446
|
}
|
|
65447
|
+
const conflictedCapabilities = WRITABLE_CAPABILITIES.filter((name) => config[name].conflict);
|
|
65448
|
+
if (conflictedCapabilities.length > 0) {
|
|
65449
|
+
const label = conflictedCapabilities.map((name) => `capabilities.${name}`).join(" and ");
|
|
65450
|
+
if (!args.force) {
|
|
65451
|
+
f2.error(`Cannot push: ${label} changed both locally and on the cloud.`);
|
|
65452
|
+
f2.info(`Run ${import_picocolors28.default.cyan("brainbase agent pull")} first to reconcile, or ${import_picocolors28.default.cyan("brainbase agent push --force")} to keep the local value.`);
|
|
65453
|
+
process.exitCode = 1;
|
|
65454
|
+
return;
|
|
65455
|
+
}
|
|
65456
|
+
f2.warn(`${import_picocolors28.default.yellow("--force")}: overwriting the cloud ${label} with the local value.`);
|
|
65457
|
+
}
|
|
65319
65458
|
const registryRefs = new Map;
|
|
65320
65459
|
for (const entry of manifest.skills) {
|
|
65321
65460
|
try {
|
|
@@ -65455,7 +65594,7 @@ async function runAgentPush(cwd2, args) {
|
|
|
65455
65594
|
f2.warn(`Cloud runtime config changed since the last sync. Run ${import_picocolors28.default.cyan("brainbase agent pull")} to accept it locally.`);
|
|
65456
65595
|
}
|
|
65457
65596
|
const shouldPushManifest = meta.localChanged || entrypointChanged || toSend.length > 0;
|
|
65458
|
-
const shouldUpdateAgent = meta.localChanged || entrypointChanged || config.defaultModelLocalChanged;
|
|
65597
|
+
const shouldUpdateAgent = meta.localChanged || entrypointChanged || config.defaultModelLocalChanged || config.memory.localChanged || config.browser.localChanged;
|
|
65459
65598
|
const hasAgentChanges = shouldPushManifest || shouldUpdateAgent;
|
|
65460
65599
|
const outgoing = hasAgentChanges ? await buildOutgoingComponents(cwd2, manifest, cloud, resolvedVersions) : null;
|
|
65461
65600
|
if (hasAgentChanges && outgoing === null) {
|
|
@@ -65499,7 +65638,7 @@ async function runAgentPush(cwd2, args) {
|
|
|
65499
65638
|
});
|
|
65500
65639
|
}
|
|
65501
65640
|
if (!hasAgentChanges && !secretPlan) {
|
|
65502
|
-
if (config.defaultModelCloudChanged || config.machineCloudChanged) {
|
|
65641
|
+
if (config.defaultModelCloudChanged || config.machineCloudChanged || config.memory.cloudChanged || config.browser.cloudChanged) {
|
|
65503
65642
|
f2.info("Nothing local to push; cloud runtime config is awaiting pull.");
|
|
65504
65643
|
return;
|
|
65505
65644
|
}
|
|
@@ -65571,7 +65710,7 @@ async function runAgentPush(cwd2, args) {
|
|
|
65571
65710
|
$e(`Pushed secrets for ${manifest.agent.name}.`);
|
|
65572
65711
|
return;
|
|
65573
65712
|
}
|
|
65574
|
-
if (meta.localChanged || entrypointChanged || config.defaultModelLocalChanged) {
|
|
65713
|
+
if (meta.localChanged || entrypointChanged || config.defaultModelLocalChanged || config.memory.localChanged || config.browser.localChanged) {
|
|
65575
65714
|
const metaSpinner = de();
|
|
65576
65715
|
metaSpinner.start("Updating agent config…");
|
|
65577
65716
|
try {
|
|
@@ -65586,6 +65725,12 @@ async function runAgentPush(cwd2, args) {
|
|
|
65586
65725
|
if (config.defaultModelLocalChanged) {
|
|
65587
65726
|
update2.default_model = manifest.default_model ?? null;
|
|
65588
65727
|
}
|
|
65728
|
+
if (config.memory.localChanged) {
|
|
65729
|
+
update2.memory_enabled = manifest.capabilities?.memory;
|
|
65730
|
+
}
|
|
65731
|
+
if (config.browser.localChanged) {
|
|
65732
|
+
update2.browser_enabled = manifest.capabilities?.browser;
|
|
65733
|
+
}
|
|
65589
65734
|
cloudAgent = await api.updateAgent(agentId, update2);
|
|
65590
65735
|
metaSpinner.stop("Agent config updated.");
|
|
65591
65736
|
} catch (err) {
|
|
@@ -65702,7 +65847,8 @@ function buildAgentMetaAfterPush({
|
|
|
65702
65847
|
tagline: manifest.agent.tagline,
|
|
65703
65848
|
entrypoint: resolvedEntrypoint !== undefined ? resolvedEntrypoint.trim() : lock?.agentMeta?.entrypoint,
|
|
65704
65849
|
...config.machineCloudChanged ? lock?.agentMeta?.machine_kind ? { machine_kind: lock.agentMeta.machine_kind } : {} : cloudAgent.machine_kind ? { machine_kind: cloudAgent.machine_kind } : lock?.agentMeta?.machine_kind ? { machine_kind: lock.agentMeta.machine_kind } : {},
|
|
65705
|
-
...config.defaultModelCloudChanged && !config.defaultModelLocalChanged ? Object.prototype.hasOwnProperty.call(lock?.agentMeta ?? {}, "default_model") ? { default_model: lock.agentMeta.default_model ?? null } : {} : Object.prototype.hasOwnProperty.call(cloudAgent, "default_model") ? { default_model: cloudAgent.default_model ?? null } : Object.prototype.hasOwnProperty.call(lock?.agentMeta ?? {}, "default_model") ? { default_model: lock.agentMeta.default_model ?? null } : {}
|
|
65850
|
+
...config.defaultModelCloudChanged && !config.defaultModelLocalChanged ? Object.prototype.hasOwnProperty.call(lock?.agentMeta ?? {}, "default_model") ? { default_model: lock.agentMeta.default_model ?? null } : {} : Object.prototype.hasOwnProperty.call(cloudAgent, "default_model") ? { default_model: cloudAgent.default_model ?? null } : Object.prototype.hasOwnProperty.call(lock?.agentMeta ?? {}, "default_model") ? { default_model: lock.agentMeta.default_model ?? null } : {},
|
|
65851
|
+
...capabilityBaselineAfterPush(cloudAgent, lock?.agentMeta, config)
|
|
65706
65852
|
};
|
|
65707
65853
|
}
|
|
65708
65854
|
async function planSecretPush(cwd2, agentId) {
|
|
@@ -65751,6 +65897,9 @@ function handleApiError3(err) {
|
|
|
65751
65897
|
// src/cli/agent-status.ts
|
|
65752
65898
|
import path81 from "node:path";
|
|
65753
65899
|
var import_picocolors29 = __toESM(require_picocolors(), 1);
|
|
65900
|
+
function capabilityDrifted(field) {
|
|
65901
|
+
return field.localChanged || field.cloudChanged || field.conflict;
|
|
65902
|
+
}
|
|
65754
65903
|
async function runAgentStatus(cwd2, args = {}) {
|
|
65755
65904
|
const json = args.json === true;
|
|
65756
65905
|
if (!json)
|
|
@@ -65818,7 +65967,7 @@ async function runAgentStatus(cwd2, args = {}) {
|
|
|
65818
65967
|
cloud: cloud.components
|
|
65819
65968
|
});
|
|
65820
65969
|
const meta = diffAgentMeta(manifest.agent, lock?.agentMeta, cloudAgent);
|
|
65821
|
-
const config = diffAgentConfig(manifest, lock?.agentMeta, cloudAgent);
|
|
65970
|
+
const config = diffAgentConfig(manifestConfigState(manifest), lock?.agentMeta, cloudConfigState(cloudAgent));
|
|
65822
65971
|
const toPush = [];
|
|
65823
65972
|
const toPull = [];
|
|
65824
65973
|
const conflicts = [];
|
|
@@ -65865,7 +66014,7 @@ async function runAgentStatus(cwd2, args = {}) {
|
|
|
65865
66014
|
}
|
|
65866
66015
|
const componentsDrifted = conflicts.length > 0 || toPush.length > 0 || toPull.length > 0;
|
|
65867
66016
|
const metaDrifted = meta.localChanged || meta.cloudChanged;
|
|
65868
|
-
const configDrifted = config.unsupported.length > 0 || config.machineMismatch || config.machineCloudChanged || config.defaultModelLocalChanged || config.defaultModelCloudChanged;
|
|
66017
|
+
const configDrifted = config.unsupported.length > 0 || config.machineMismatch || config.machineCloudChanged || config.defaultModelLocalChanged || config.defaultModelCloudChanged || capabilityDrifted(config.memory) || capabilityDrifted(config.browser);
|
|
65869
66018
|
const secretsDrifted = secretDrift.localOnly.length > 0 || secretDrift.cloudOnly.length > 0 || secretDrift.changed.length > 0;
|
|
65870
66019
|
const everythingInSync = !componentsDrifted && !metaDrifted && !configDrifted && !secretsDrifted;
|
|
65871
66020
|
const unchecked = secretsChecked ? [] : [{ signal: "secrets", reason: secretsUncheckedReason }];
|
|
@@ -65883,7 +66032,9 @@ async function runAgentStatus(cwd2, args = {}) {
|
|
|
65883
66032
|
machineCloudChanged: config.machineCloudChanged,
|
|
65884
66033
|
defaultModelLocalChanged: config.defaultModelLocalChanged,
|
|
65885
66034
|
defaultModelCloudChanged: config.defaultModelCloudChanged,
|
|
65886
|
-
defaultModelConflict: config.defaultModelConflict
|
|
66035
|
+
defaultModelConflict: config.defaultModelConflict,
|
|
66036
|
+
memory: config.memory,
|
|
66037
|
+
browser: config.browser
|
|
65887
66038
|
},
|
|
65888
66039
|
secrets: secretsChecked ? {
|
|
65889
66040
|
localOnly: secretDrift.localOnly,
|
|
@@ -65944,6 +66095,19 @@ async function runAgentStatus(cwd2, args = {}) {
|
|
|
65944
66095
|
lines.push(` ${import_picocolors29.default.cyan("← pull")} default_model changed on cloud`);
|
|
65945
66096
|
}
|
|
65946
66097
|
}
|
|
66098
|
+
for (const name of WRITABLE_CAPABILITIES) {
|
|
66099
|
+
const field = config[name];
|
|
66100
|
+
if (field.conflict) {
|
|
66101
|
+
lines.push(` ${import_picocolors29.default.red("! conflict")} capabilities.${name} changed locally and on cloud`);
|
|
66102
|
+
continue;
|
|
66103
|
+
}
|
|
66104
|
+
if (field.localChanged) {
|
|
66105
|
+
lines.push(` ${import_picocolors29.default.yellow("→ push")} capabilities.${name} edited locally`);
|
|
66106
|
+
}
|
|
66107
|
+
if (field.cloudChanged) {
|
|
66108
|
+
lines.push(` ${import_picocolors29.default.cyan("← pull")} capabilities.${name} changed on cloud`);
|
|
66109
|
+
}
|
|
66110
|
+
}
|
|
65947
66111
|
lines.push("");
|
|
65948
66112
|
}
|
|
65949
66113
|
if (secretsDrifted || !secretsChecked) {
|
|
@@ -66065,7 +66229,6 @@ function formatExport(shell, key2, value) {
|
|
|
66065
66229
|
}
|
|
66066
66230
|
|
|
66067
66231
|
// src/cli/agent-create.ts
|
|
66068
|
-
import path82 from "node:path";
|
|
66069
66232
|
var import_picocolors32 = __toESM(require_picocolors(), 1);
|
|
66070
66233
|
|
|
66071
66234
|
// src/ui/box.ts
|
|
@@ -66258,6 +66421,153 @@ async function listTeamsPerOrg(orgs) {
|
|
|
66258
66421
|
return { entries, resolved, failures };
|
|
66259
66422
|
}
|
|
66260
66423
|
|
|
66424
|
+
// src/core/agent-scaffold.ts
|
|
66425
|
+
var import_yaml4 = __toESM(require_dist(), 1);
|
|
66426
|
+
import path82 from "node:path";
|
|
66427
|
+
var STARTER_TAGLINE = "A starter agent.";
|
|
66428
|
+
var FALLBACK_NAME = "my-agent";
|
|
66429
|
+
var FALLBACK_HARNESS = "claude-code";
|
|
66430
|
+
function isKnownHarness(id) {
|
|
66431
|
+
return adapters.some((a3) => a3.id === id);
|
|
66432
|
+
}
|
|
66433
|
+
function knownHarnessIds() {
|
|
66434
|
+
return adapters.map((a3) => a3.id);
|
|
66435
|
+
}
|
|
66436
|
+
async function resolveScaffoldHarness(cwd2, flag) {
|
|
66437
|
+
const forced = flag?.trim();
|
|
66438
|
+
if (forced)
|
|
66439
|
+
return { id: normalizeHarnessId(forced), source: "flag" };
|
|
66440
|
+
const detections = await detectHarnesses(cwd2);
|
|
66441
|
+
const inProject = detections.find((d3) => d3.detection.hasProject);
|
|
66442
|
+
if (inProject)
|
|
66443
|
+
return { id: inProject.adapter.id, source: "project" };
|
|
66444
|
+
const installed = detections.find((d3) => d3.detection.detected);
|
|
66445
|
+
if (installed)
|
|
66446
|
+
return { id: installed.adapter.id, source: "installed" };
|
|
66447
|
+
return { id: FALLBACK_HARNESS, source: "default" };
|
|
66448
|
+
}
|
|
66449
|
+
function describeHarnessSource(source) {
|
|
66450
|
+
switch (source) {
|
|
66451
|
+
case "flag":
|
|
66452
|
+
return "from --harness";
|
|
66453
|
+
case "project":
|
|
66454
|
+
return "detected in this folder";
|
|
66455
|
+
case "installed":
|
|
66456
|
+
return "installed on this machine";
|
|
66457
|
+
case "default":
|
|
66458
|
+
return "nothing detected — pass --harness to change it";
|
|
66459
|
+
default: {
|
|
66460
|
+
const never = source;
|
|
66461
|
+
return never;
|
|
66462
|
+
}
|
|
66463
|
+
}
|
|
66464
|
+
}
|
|
66465
|
+
function singleLine(value) {
|
|
66466
|
+
return (value ?? "").replace(/\s+/g, " ").trim();
|
|
66467
|
+
}
|
|
66468
|
+
function resolveScaffoldName(cwd2, flag) {
|
|
66469
|
+
return singleLine(flag) || singleLine(path82.basename(path82.resolve(cwd2))) || FALLBACK_NAME;
|
|
66470
|
+
}
|
|
66471
|
+
function harnessDisplayName(id) {
|
|
66472
|
+
try {
|
|
66473
|
+
return getAdapter(id).displayName;
|
|
66474
|
+
} catch {
|
|
66475
|
+
return id;
|
|
66476
|
+
}
|
|
66477
|
+
}
|
|
66478
|
+
function starterInstructions(harnessId) {
|
|
66479
|
+
return `You are a helpful ${harnessDisplayName(harnessId)} agent.`;
|
|
66480
|
+
}
|
|
66481
|
+
function buildStarterManifest(seed) {
|
|
66482
|
+
return {
|
|
66483
|
+
schema: 1,
|
|
66484
|
+
harness: seed.harness,
|
|
66485
|
+
agent: {
|
|
66486
|
+
name: seed.name,
|
|
66487
|
+
tagline: singleLine(seed.tagline) || STARTER_TAGLINE
|
|
66488
|
+
},
|
|
66489
|
+
instructions: { text: starterInstructions(seed.harness) }
|
|
66490
|
+
};
|
|
66491
|
+
}
|
|
66492
|
+
function scalar(value) {
|
|
66493
|
+
return import_yaml4.default.stringify(value, { lineWidth: 0 }).trimEnd();
|
|
66494
|
+
}
|
|
66495
|
+
function renderFullTemplate(seed) {
|
|
66496
|
+
return `# ${AGENT_MANIFEST_FILE} — declarative agent manifest.
|
|
66497
|
+
# Committed to source control. Edit by hand, then \`brainbase agent push\`.
|
|
66498
|
+
#
|
|
66499
|
+
# Only \`schema\` and \`agent.name\` are required — uncomment the blocks you
|
|
66500
|
+
# need and delete the rest. Full reference:
|
|
66501
|
+
# https://docs.brainbaselabs.com/cli/reference/agent-manifest
|
|
66502
|
+
|
|
66503
|
+
schema: 1
|
|
66504
|
+
|
|
66505
|
+
# Which harness runs this agent locally. One of:
|
|
66506
|
+
# ${knownHarnessIds().join(", ")}.
|
|
66507
|
+
harness: ${scalar(seed.harness)}
|
|
66508
|
+
|
|
66509
|
+
# Sandbox provider, applied when \`brainbase agent create\` claims this file.
|
|
66510
|
+
# Immutable afterwards — recreate the agent to change it.
|
|
66511
|
+
# machine_kind: daytona
|
|
66512
|
+
|
|
66513
|
+
# Agent-level model override. Omit it to leave the cloud value alone, or set
|
|
66514
|
+
# null to clear an override that is already set.
|
|
66515
|
+
# default_model: openai/gpt-5.6-terra
|
|
66516
|
+
|
|
66517
|
+
agent:
|
|
66518
|
+
name: ${scalar(seed.name)}
|
|
66519
|
+
tagline: ${scalar(singleLine(seed.tagline) || STARTER_TAGLINE)}
|
|
66520
|
+
|
|
66521
|
+
# The agent's system prompt. Exactly one of \`text\` or \`file\`.
|
|
66522
|
+
instructions:
|
|
66523
|
+
text: ${scalar(starterInstructions(seed.harness))}
|
|
66524
|
+
# file: ./.brainbase/instructions.md
|
|
66525
|
+
|
|
66526
|
+
# Bash that runs in the sandbox before the agent starts. Exactly one of
|
|
66527
|
+
# \`commands\`, \`file\`, or \`text\`.
|
|
66528
|
+
# entrypoint:
|
|
66529
|
+
# commands:
|
|
66530
|
+
# - npm install
|
|
66531
|
+
|
|
66532
|
+
# Named procedures the agent can follow. Each \`content\` takes exactly one of
|
|
66533
|
+
# \`text\` or \`file\`.
|
|
66534
|
+
# playbooks:
|
|
66535
|
+
# - title: Release checklist
|
|
66536
|
+
# description: Steps to cut a release
|
|
66537
|
+
# content:
|
|
66538
|
+
# file: ./playbooks/release.md
|
|
66539
|
+
|
|
66540
|
+
# Skills to install. A registry ref pins an exact version or omits it to track
|
|
66541
|
+
# the latest; ranges are not supported. Local paths start with \`./\`.
|
|
66542
|
+
# skills:
|
|
66543
|
+
# - source: registry:brainbase/changelog@1.0.0
|
|
66544
|
+
# - source: ./skills/local-linter
|
|
66545
|
+
|
|
66546
|
+
# MCP servers. Each entry needs either \`url\` or \`command\`. Keep tokens out
|
|
66547
|
+
# of this file — put them in the gitignored \`.brainbase/secrets.env\`.
|
|
66548
|
+
# mcp:
|
|
66549
|
+
# - name: github
|
|
66550
|
+
# url: https://api.githubcopilot.com/mcp/
|
|
66551
|
+
# is_enabled: true
|
|
66552
|
+
|
|
66553
|
+
# Criteria a judge scores every completed turn against.
|
|
66554
|
+
# evals:
|
|
66555
|
+
# - slug: answered-the-question
|
|
66556
|
+
# criteria: The reply answers what was asked without inventing facts.
|
|
66557
|
+
|
|
66558
|
+
# Not shown above: \`capabilities\` is written by \`brainbase agent pull\` from
|
|
66559
|
+
# the cloud and never pushed, and \`commands\` / \`hooks\` / \`files\` parse but
|
|
66560
|
+
# no command syncs them yet — \`agent push\` refuses them rather than dropping
|
|
66561
|
+
# them silently.
|
|
66562
|
+
`;
|
|
66563
|
+
}
|
|
66564
|
+
function writeStarterManifest(cwd2, seed, opts = {}) {
|
|
66565
|
+
const body = opts.full ? renderFullTemplate(seed) : renderManifest(buildStarterManifest(seed));
|
|
66566
|
+
const manifest = parseManifest(body);
|
|
66567
|
+
writeManifestText(cwd2, body);
|
|
66568
|
+
return manifest;
|
|
66569
|
+
}
|
|
66570
|
+
|
|
66261
66571
|
// src/cli/agent-create.ts
|
|
66262
66572
|
async function runAgentCreate(cwd2, args) {
|
|
66263
66573
|
banner("agent create — claim a brainbase.agent.yaml and link this folder");
|
|
@@ -66495,7 +66805,8 @@ async function runAgentCreate(cwd2, args) {
|
|
|
66495
66805
|
tagline: agent.tagline,
|
|
66496
66806
|
...resolvedEntrypoint ? { entrypoint: resolvedEntrypoint.trim() } : {},
|
|
66497
66807
|
...agent.machine_kind ? { machine_kind: agent.machine_kind } : {},
|
|
66498
|
-
...Object.prototype.hasOwnProperty.call(agent, "default_model") ? { default_model: agent.default_model ?? null } : {}
|
|
66808
|
+
...Object.prototype.hasOwnProperty.call(agent, "default_model") ? { default_model: agent.default_model ?? null } : {},
|
|
66809
|
+
...capabilityBaseline(agent, undefined)
|
|
66499
66810
|
}
|
|
66500
66811
|
};
|
|
66501
66812
|
writeSyncState(cwd2, state);
|
|
@@ -66528,12 +66839,9 @@ async function loadOrScaffoldManifest(cwd2, args) {
|
|
|
66528
66839
|
}
|
|
66529
66840
|
}
|
|
66530
66841
|
f2.warn(`No ${import_picocolors32.default.bold(AGENT_MANIFEST_FILE)} here.`);
|
|
66531
|
-
if (!args.yes) {
|
|
66532
|
-
if (!isInteractive()) {
|
|
66533
|
-
throw new NonInteractiveError(`No ${AGENT_MANIFEST_FILE} here. Create one first, or re-run with --yes to scaffold a minimal one.`);
|
|
66534
|
-
}
|
|
66842
|
+
if (!autoProceed(args.yes)) {
|
|
66535
66843
|
const ans = await se({
|
|
66536
|
-
message: `Scaffold a
|
|
66844
|
+
message: `Scaffold a starter ${import_picocolors32.default.bold(AGENT_MANIFEST_FILE)} and continue?`,
|
|
66537
66845
|
initialValue: true
|
|
66538
66846
|
});
|
|
66539
66847
|
if (!ensureNotCancelled(ans)) {
|
|
@@ -66541,25 +66849,21 @@ async function loadOrScaffoldManifest(cwd2, args) {
|
|
|
66541
66849
|
return null;
|
|
66542
66850
|
}
|
|
66543
66851
|
}
|
|
66544
|
-
const
|
|
66545
|
-
const seedHarness = args.harness ? normalizeHarnessId(args.harness) : undefined;
|
|
66546
|
-
const scaffold = {
|
|
66547
|
-
schema: 1,
|
|
66548
|
-
...seedHarness ? { harness: seedHarness } : {},
|
|
66549
|
-
agent: { name: seedName, ...args.tagline ? { tagline: args.tagline } : {} },
|
|
66550
|
-
playbooks: [],
|
|
66551
|
-
evals: [],
|
|
66552
|
-
skills: [],
|
|
66553
|
-
mcp: []
|
|
66554
|
-
};
|
|
66852
|
+
const harness = await resolveScaffoldHarness(cwd2, args.harness);
|
|
66555
66853
|
try {
|
|
66556
|
-
|
|
66854
|
+
const scaffold = writeStarterManifest(cwd2, {
|
|
66855
|
+
name: resolveScaffoldName(cwd2, args.name),
|
|
66856
|
+
harness: harness.id,
|
|
66857
|
+
tagline: args.tagline
|
|
66858
|
+
});
|
|
66859
|
+
f2.info(`harness ${import_picocolors32.default.bold(harness.id)} ${import_picocolors32.default.dim(`(${describeHarnessSource(harness.source)})`)}`);
|
|
66557
66860
|
f2.info(`Wrote ${import_picocolors32.default.bold(AGENT_MANIFEST_FILE)}.`);
|
|
66861
|
+
return scaffold;
|
|
66558
66862
|
} catch (err) {
|
|
66559
66863
|
f2.error(`Failed to write manifest: ${err.message}`);
|
|
66864
|
+
process.exitCode = 1;
|
|
66560
66865
|
return null;
|
|
66561
66866
|
}
|
|
66562
|
-
return scaffold;
|
|
66563
66867
|
}
|
|
66564
66868
|
async function pickHarness2(cwd2) {
|
|
66565
66869
|
const detections = await detectHarnesses(cwd2);
|
|
@@ -66591,8 +66895,83 @@ function handleApiError4(err) {
|
|
|
66591
66895
|
$e("Aborted.");
|
|
66592
66896
|
}
|
|
66593
66897
|
|
|
66594
|
-
// src/cli/agent-
|
|
66898
|
+
// src/cli/agent-init.ts
|
|
66899
|
+
import path83 from "node:path";
|
|
66595
66900
|
var import_picocolors33 = __toESM(require_picocolors(), 1);
|
|
66901
|
+
function emit(result2) {
|
|
66902
|
+
console.log(JSON.stringify(result2, null, 2));
|
|
66903
|
+
}
|
|
66904
|
+
async function runAgentInit(cwd2, args = {}) {
|
|
66905
|
+
const json = args.json === true;
|
|
66906
|
+
const target = manifestPath(cwd2);
|
|
66907
|
+
if (args.minimal && args.full) {
|
|
66908
|
+
return refuse(json, {
|
|
66909
|
+
path: target,
|
|
66910
|
+
created: false,
|
|
66911
|
+
reason: "conflicting-flags",
|
|
66912
|
+
message: `Pass either ${import_picocolors33.default.cyan("--minimal")} or ${import_picocolors33.default.cyan("--full")}, not both.`
|
|
66913
|
+
});
|
|
66914
|
+
}
|
|
66915
|
+
const existing = existingManifestPath(cwd2);
|
|
66916
|
+
if (existing && !args.force) {
|
|
66917
|
+
return refuse(json, {
|
|
66918
|
+
path: existing,
|
|
66919
|
+
created: false,
|
|
66920
|
+
reason: "manifest-exists",
|
|
66921
|
+
message: `${import_picocolors33.default.bold(path83.basename(existing))} already exists here. Edit it, or pass ${import_picocolors33.default.cyan("--force")} to overwrite it.`
|
|
66922
|
+
});
|
|
66923
|
+
}
|
|
66924
|
+
const harness = await resolveScaffoldHarness(cwd2, args.harness);
|
|
66925
|
+
if (!isKnownHarness(harness.id)) {
|
|
66926
|
+
return refuse(json, {
|
|
66927
|
+
path: target,
|
|
66928
|
+
created: false,
|
|
66929
|
+
reason: "unknown-harness",
|
|
66930
|
+
message: `Unknown harness ${import_picocolors33.default.bold(harness.id)}. Pick one of: ${knownHarnessIds().join(", ")}.`
|
|
66931
|
+
});
|
|
66932
|
+
}
|
|
66933
|
+
const name = resolveScaffoldName(cwd2, args.name);
|
|
66934
|
+
const template2 = args.full ? "full" : "minimal";
|
|
66935
|
+
if (!json)
|
|
66936
|
+
banner("agent init — write a starter brainbase.agent.yaml");
|
|
66937
|
+
try {
|
|
66938
|
+
writeStarterManifest(cwd2, { name, harness: harness.id, tagline: args.tagline }, { full: args.full });
|
|
66939
|
+
} catch (err) {
|
|
66940
|
+
console.error(import_picocolors33.default.red(`Failed to write ${AGENT_MANIFEST_FILE}: ${err.message}`));
|
|
66941
|
+
process.exitCode = 1;
|
|
66942
|
+
return;
|
|
66943
|
+
}
|
|
66944
|
+
if (json) {
|
|
66945
|
+
emit({
|
|
66946
|
+
path: target,
|
|
66947
|
+
created: true,
|
|
66948
|
+
name,
|
|
66949
|
+
harness: harness.id,
|
|
66950
|
+
harness_source: harness.source,
|
|
66951
|
+
template: template2
|
|
66952
|
+
});
|
|
66953
|
+
return;
|
|
66954
|
+
}
|
|
66955
|
+
f2.info(`harness ${import_picocolors33.default.bold(harness.id)} ${import_picocolors33.default.dim(`(${describeHarnessSource(harness.source)})`)}`);
|
|
66956
|
+
f2.success(`Wrote ${import_picocolors33.default.bold(AGENT_MANIFEST_FILE)}${existing ? " (overwritten)" : ""}.`);
|
|
66957
|
+
console.log();
|
|
66958
|
+
console.log(tip(`Edit it, then run ${import_picocolors33.default.cyan("brainbase agent create")} ${import_picocolors33.default.dim("— creates the cloud agent and stamps its id back into the file.")}`));
|
|
66959
|
+
console.log();
|
|
66960
|
+
}
|
|
66961
|
+
function refuse(json, outcome) {
|
|
66962
|
+
const { message, ...result2 } = outcome;
|
|
66963
|
+
process.exitCode = 1;
|
|
66964
|
+
if (json) {
|
|
66965
|
+
emit(result2);
|
|
66966
|
+
return;
|
|
66967
|
+
}
|
|
66968
|
+
console.error(`
|
|
66969
|
+
${import_picocolors33.default.red(message)}
|
|
66970
|
+
`);
|
|
66971
|
+
}
|
|
66972
|
+
|
|
66973
|
+
// src/cli/agent-list.ts
|
|
66974
|
+
var import_picocolors34 = __toESM(require_picocolors(), 1);
|
|
66596
66975
|
async function runAgentList(args) {
|
|
66597
66976
|
if (!args.json)
|
|
66598
66977
|
banner("agent list — agents in this team");
|
|
@@ -66612,27 +66991,27 @@ async function runAgentList(args) {
|
|
|
66612
66991
|
function formatAgentList(agents, labels) {
|
|
66613
66992
|
const lines = [""];
|
|
66614
66993
|
if (agents.length === 0) {
|
|
66615
|
-
lines.push(` ${
|
|
66994
|
+
lines.push(` ${import_picocolors34.default.dim(`No agents in ${labels.orgName} → ${labels.teamName} yet.`)}`, "", ` ${import_picocolors34.default.dim("create one with")} ${import_picocolors34.default.cyan("brainbase agent create")}`, "");
|
|
66616
66995
|
return lines.join(`
|
|
66617
66996
|
`);
|
|
66618
66997
|
}
|
|
66619
66998
|
for (const agent of agents) {
|
|
66620
|
-
lines.push(` ${
|
|
66999
|
+
lines.push(` ${import_picocolors34.default.bold(agent.name)} ${import_picocolors34.default.dim(agent.slug)}`);
|
|
66621
67000
|
if (agent.tagline)
|
|
66622
|
-
lines.push(` ${
|
|
67001
|
+
lines.push(` ${import_picocolors34.default.dim(agent.tagline)}`);
|
|
66623
67002
|
const meta = [agent.harness, agent.machine_kind, agent.default_model].filter((value) => !!value).join(" · ");
|
|
66624
67003
|
if (meta)
|
|
66625
|
-
lines.push(` ${
|
|
66626
|
-
lines.push(` ${
|
|
67004
|
+
lines.push(` ${import_picocolors34.default.dim(meta)}`);
|
|
67005
|
+
lines.push(` ${import_picocolors34.default.dim(agent.id)}`);
|
|
66627
67006
|
lines.push("");
|
|
66628
67007
|
}
|
|
66629
|
-
lines.push(` ${
|
|
67008
|
+
lines.push(` ${import_picocolors34.default.dim("link this folder to one with")} ${import_picocolors34.default.cyan("brainbase link --agent <id>")}`, "");
|
|
66630
67009
|
return lines.join(`
|
|
66631
67010
|
`);
|
|
66632
67011
|
}
|
|
66633
67012
|
|
|
66634
67013
|
// src/cli/agent-connections.ts
|
|
66635
|
-
var
|
|
67014
|
+
var import_picocolors36 = __toESM(require_picocolors(), 1);
|
|
66636
67015
|
|
|
66637
67016
|
// src/core/integrations.ts
|
|
66638
67017
|
var IMPLEMENTED_INTEGRATIONS = ["slack", "meeting"];
|
|
@@ -66664,7 +67043,7 @@ function explain(state) {
|
|
|
66664
67043
|
}
|
|
66665
67044
|
|
|
66666
67045
|
// src/cli/agent-connect.ts
|
|
66667
|
-
var
|
|
67046
|
+
var import_picocolors35 = __toESM(require_picocolors(), 1);
|
|
66668
67047
|
|
|
66669
67048
|
// src/core/secret-input.ts
|
|
66670
67049
|
import fs74 from "node:fs";
|
|
@@ -66915,9 +67294,9 @@ function report(result2, json) {
|
|
|
66915
67294
|
console.log(JSON.stringify(result2, null, 2));
|
|
66916
67295
|
return;
|
|
66917
67296
|
}
|
|
66918
|
-
const detail = result2.detail ? ` ${
|
|
67297
|
+
const detail = result2.detail ? ` ${import_picocolors35.default.dim(`(${result2.detail})`)}` : "";
|
|
66919
67298
|
f2.success(`${result2.name} connected${detail}`);
|
|
66920
|
-
f2.info(`Run ${
|
|
67299
|
+
f2.info(`Run ${import_picocolors35.default.cyan("brainbase agent pull")} to pick up the built-in ${result2.name} MCP server.`);
|
|
66921
67300
|
}
|
|
66922
67301
|
|
|
66923
67302
|
// src/cli/agent-connections.ts
|
|
@@ -66933,7 +67312,7 @@ async function runAgentConnections(cwd2, args) {
|
|
|
66933
67312
|
return;
|
|
66934
67313
|
}
|
|
66935
67314
|
f2.warn("This folder is not linked to any agent.");
|
|
66936
|
-
f2.info(`Run ${
|
|
67315
|
+
f2.info(`Run ${import_picocolors36.default.cyan("brainbase link")} first.`);
|
|
66937
67316
|
process.exitCode = 1;
|
|
66938
67317
|
return;
|
|
66939
67318
|
}
|
|
@@ -66955,22 +67334,22 @@ async function runAgentConnections(cwd2, args) {
|
|
|
66955
67334
|
function formatConnections(connections) {
|
|
66956
67335
|
const lines = [""];
|
|
66957
67336
|
for (const integration of connections.integrations) {
|
|
66958
|
-
lines.push(` ${statusMark(integration)} ${
|
|
67337
|
+
lines.push(` ${statusMark(integration)} ${import_picocolors36.default.bold(integration.name)}${describe(integration)}`);
|
|
66959
67338
|
const hint = hintFor(integration);
|
|
66960
67339
|
if (hint)
|
|
66961
|
-
lines.push(` ${
|
|
67340
|
+
lines.push(` ${import_picocolors36.default.dim(hint)}`);
|
|
66962
67341
|
}
|
|
66963
67342
|
lines.push("");
|
|
66964
67343
|
return lines.join(`
|
|
66965
67344
|
`);
|
|
66966
67345
|
}
|
|
66967
67346
|
function statusMark(integration) {
|
|
66968
|
-
return integration.connected ?
|
|
67347
|
+
return integration.connected ? import_picocolors36.default.green("✓") : import_picocolors36.default.dim("·");
|
|
66969
67348
|
}
|
|
66970
67349
|
function describe(integration) {
|
|
66971
67350
|
if (!integration.connected)
|
|
66972
|
-
return ` ${
|
|
66973
|
-
return integration.detail ? ` ${
|
|
67351
|
+
return ` ${import_picocolors36.default.dim("not connected")}`;
|
|
67352
|
+
return integration.detail ? ` ${import_picocolors36.default.dim(integration.detail)}` : ` ${import_picocolors36.default.dim("connected")}`;
|
|
66974
67353
|
}
|
|
66975
67354
|
function hintFor(integration) {
|
|
66976
67355
|
const action = actionability(integration);
|
|
@@ -66981,7 +67360,7 @@ function hintFor(integration) {
|
|
|
66981
67360
|
}
|
|
66982
67361
|
|
|
66983
67362
|
// src/cli/agent-disconnect.ts
|
|
66984
|
-
var
|
|
67363
|
+
var import_picocolors37 = __toESM(require_picocolors(), 1);
|
|
66985
67364
|
async function runAgentDisconnect(cwd2, target, args) {
|
|
66986
67365
|
const json = Boolean(args.json);
|
|
66987
67366
|
try {
|
|
@@ -67018,7 +67397,7 @@ async function disconnect(cwd2, target, args, json) {
|
|
|
67018
67397
|
return;
|
|
67019
67398
|
}
|
|
67020
67399
|
f2.success(`${target} disconnected`);
|
|
67021
|
-
f2.info(`Run ${
|
|
67400
|
+
f2.info(`Run ${import_picocolors37.default.cyan("brainbase agent pull")} to drop the built-in ${target} MCP server locally.`);
|
|
67022
67401
|
}
|
|
67023
67402
|
|
|
67024
67403
|
// src/cli/agent.ts
|
|
@@ -67028,6 +67407,17 @@ async function runAgent(cwd2, sub, args, opts) {
|
|
|
67028
67407
|
return;
|
|
67029
67408
|
}
|
|
67030
67409
|
switch (sub) {
|
|
67410
|
+
case "init":
|
|
67411
|
+
await runAgentInit(cwd2, {
|
|
67412
|
+
name: opts.name,
|
|
67413
|
+
tagline: opts.tagline,
|
|
67414
|
+
harness: opts.harness,
|
|
67415
|
+
minimal: opts.minimal,
|
|
67416
|
+
full: opts.full,
|
|
67417
|
+
force: opts.force,
|
|
67418
|
+
json: opts.json
|
|
67419
|
+
});
|
|
67420
|
+
return;
|
|
67031
67421
|
case "create":
|
|
67032
67422
|
await runAgentCreate(cwd2, {
|
|
67033
67423
|
yes: opts.yes,
|
|
@@ -67107,31 +67497,32 @@ async function runAgent(cwd2, sub, args, opts) {
|
|
|
67107
67497
|
function printHelp() {
|
|
67108
67498
|
const out = [];
|
|
67109
67499
|
out.push("");
|
|
67110
|
-
out.push(` ${
|
|
67500
|
+
out.push(` ${import_picocolors38.default.bold("brainbase agent")} ${import_picocolors38.default.dim("<sub> [options]")}`);
|
|
67111
67501
|
out.push("");
|
|
67112
|
-
out.push(` ${
|
|
67113
|
-
out.push(` ${
|
|
67114
|
-
out.push(` ${
|
|
67115
|
-
out.push(` ${
|
|
67116
|
-
out.push(` ${
|
|
67117
|
-
out.push(` ${
|
|
67118
|
-
out.push(` ${
|
|
67119
|
-
out.push(` ${
|
|
67120
|
-
out.push(` ${
|
|
67121
|
-
out.push(` ${
|
|
67502
|
+
out.push(` ${import_picocolors38.default.cyan("list")} ${import_picocolors38.default.dim("show the agents in a team, with the ids `brainbase link` takes (--json for scripts)")}`);
|
|
67503
|
+
out.push(` ${import_picocolors38.default.cyan("init")} ${import_picocolors38.default.dim("write a starter brainbase.agent.yaml here — offline, no login (--full for a commented template, --force to overwrite)")}`);
|
|
67504
|
+
out.push(` ${import_picocolors38.default.cyan("create")} ${import_picocolors38.default.dim("claim an unclaimed brainbase.agent.yaml and create the cloud agent (scaffolds one if the folder has none)")}`);
|
|
67505
|
+
out.push(` ${import_picocolors38.default.cyan("pull")} ${import_picocolors38.default.dim("[<id>]")} ${import_picocolors38.default.dim("apply cloud changes into this folder — pass <id> to switch (--force to override); --run-entrypoint to also execute the agent entrypoint")}`);
|
|
67506
|
+
out.push(` ${import_picocolors38.default.cyan("push")} ${import_picocolors38.default.dim("send local changes to the cloud — instructions, playbooks, skills, MCPs, entrypoint (--force to overwrite cloud-side conflicts with local)")}`);
|
|
67507
|
+
out.push(` ${import_picocolors38.default.cyan("unpack")} ${import_picocolors38.default.dim("install the claimed agent into a harness layout (--harness to override)")}`);
|
|
67508
|
+
out.push(` ${import_picocolors38.default.cyan("status")} ${import_picocolors38.default.dim("show what would push, what would pull, and which manifest blocks are ignored (--json for scripts)")}`);
|
|
67509
|
+
out.push(` ${import_picocolors38.default.cyan("connections")} ${import_picocolors38.default.dim("show which integrations this agent is wired to (--json for scripts)")}`);
|
|
67510
|
+
out.push(` ${import_picocolors38.default.cyan("connect")} ${import_picocolors38.default.dim("<name>")} ${import_picocolors38.default.dim("connect slack or meeting — credentials come from flags, env, or stdin")}`);
|
|
67511
|
+
out.push(` ${import_picocolors38.default.cyan("disconnect")} ${import_picocolors38.default.dim("<name>")} ${import_picocolors38.default.dim("revoke a slack or meeting install")}`);
|
|
67512
|
+
out.push(` ${import_picocolors38.default.cyan("env")} ${import_picocolors38.default.dim('print export statements — use with `eval "$(brainbase agent env)"`')}`);
|
|
67122
67513
|
out.push("");
|
|
67123
|
-
out.push(` ${
|
|
67124
|
-
out.push(` ${
|
|
67514
|
+
out.push(` ${import_picocolors38.default.dim("Slack credentials:")} ${import_picocolors38.default.dim("--bot-token / BRAINBASE_SLACK_BOT_TOKEN, --signing-secret / BRAINBASE_SLACK_SIGNING_SECRET,")}`);
|
|
67515
|
+
out.push(` ${import_picocolors38.default.dim('or pipe {"bot_token":"…","signing_secret":"…"} on stdin to keep them out of argv.')}`);
|
|
67125
67516
|
out.push("");
|
|
67126
67517
|
console.log(out.join(`
|
|
67127
67518
|
`));
|
|
67128
67519
|
}
|
|
67129
67520
|
|
|
67130
67521
|
// src/cli/team.ts
|
|
67131
|
-
var
|
|
67522
|
+
var import_picocolors40 = __toESM(require_picocolors(), 1);
|
|
67132
67523
|
|
|
67133
67524
|
// src/cli/team-list.ts
|
|
67134
|
-
var
|
|
67525
|
+
var import_picocolors39 = __toESM(require_picocolors(), 1);
|
|
67135
67526
|
async function runTeamList(args) {
|
|
67136
67527
|
if (!args.json)
|
|
67137
67528
|
banner("team list — teams you can put agents in");
|
|
@@ -67151,25 +67542,25 @@ async function runTeamList(args) {
|
|
|
67151
67542
|
function formatTeamList(grouped) {
|
|
67152
67543
|
const lines = [""];
|
|
67153
67544
|
if (grouped.length === 0) {
|
|
67154
|
-
lines.push(` ${
|
|
67545
|
+
lines.push(` ${import_picocolors39.default.dim("You are not a member of any organization.")}`, "");
|
|
67155
67546
|
return lines.join(`
|
|
67156
67547
|
`);
|
|
67157
67548
|
}
|
|
67158
67549
|
const nameWidth = Math.max(...grouped.flatMap(({ teams }) => teams.map((t) => t.name.length)), 0);
|
|
67159
67550
|
for (const { org, teams, error } of grouped) {
|
|
67160
|
-
const slug = org.slug ? ` ${
|
|
67161
|
-
lines.push(` ${
|
|
67551
|
+
const slug = org.slug ? ` ${import_picocolors39.default.dim(org.slug)}` : "";
|
|
67552
|
+
lines.push(` ${import_picocolors39.default.bold(org.name)}${slug}`);
|
|
67162
67553
|
if (error) {
|
|
67163
|
-
lines.push(` ${
|
|
67554
|
+
lines.push(` ${import_picocolors39.default.red(`could not load teams: ${error}`)}`);
|
|
67164
67555
|
} else if (teams.length === 0) {
|
|
67165
|
-
lines.push(` ${
|
|
67556
|
+
lines.push(` ${import_picocolors39.default.dim("no teams yet — create one in the web app")}`);
|
|
67166
67557
|
}
|
|
67167
67558
|
for (const team of teams) {
|
|
67168
|
-
lines.push(` ${team.name.padEnd(nameWidth)} ${
|
|
67559
|
+
lines.push(` ${team.name.padEnd(nameWidth)} ${import_picocolors39.default.dim(team.id)}`);
|
|
67169
67560
|
}
|
|
67170
67561
|
lines.push("");
|
|
67171
67562
|
}
|
|
67172
|
-
lines.push(` ${
|
|
67563
|
+
lines.push(` ${import_picocolors39.default.dim("list a team’s agents with")} ${import_picocolors39.default.cyan("brainbase agent list --team <id>")}`, "");
|
|
67173
67564
|
return lines.join(`
|
|
67174
67565
|
`);
|
|
67175
67566
|
}
|
|
@@ -67200,29 +67591,29 @@ async function runTeam(sub, args, opts) {
|
|
|
67200
67591
|
function printHelp2() {
|
|
67201
67592
|
const out = [];
|
|
67202
67593
|
out.push("");
|
|
67203
|
-
out.push(` ${
|
|
67594
|
+
out.push(` ${import_picocolors40.default.bold("brainbase team")} ${import_picocolors40.default.dim("<sub> [options]")}`);
|
|
67204
67595
|
out.push("");
|
|
67205
|
-
out.push(` ${
|
|
67596
|
+
out.push(` ${import_picocolors40.default.cyan("list")} ${import_picocolors40.default.dim("show the teams you can create agents in, grouped by organization")}`);
|
|
67206
67597
|
out.push("");
|
|
67207
|
-
out.push(` ${
|
|
67208
|
-
out.push(` ${
|
|
67598
|
+
out.push(` ${import_picocolors40.default.dim("--org <id-or-slug>")} ${import_picocolors40.default.dim("limit to one organization")}`);
|
|
67599
|
+
out.push(` ${import_picocolors40.default.dim("--json")} ${import_picocolors40.default.dim("machine-readable output")}`);
|
|
67209
67600
|
out.push("");
|
|
67210
67601
|
console.log(out.join(`
|
|
67211
67602
|
`));
|
|
67212
67603
|
}
|
|
67213
67604
|
|
|
67214
67605
|
// src/cli/orchestration.ts
|
|
67215
|
-
var
|
|
67606
|
+
var import_picocolors47 = __toESM(require_picocolors(), 1);
|
|
67216
67607
|
|
|
67217
67608
|
// src/cli/orchestration-pull.ts
|
|
67218
|
-
import
|
|
67609
|
+
import path87 from "node:path";
|
|
67219
67610
|
import fs78 from "node:fs";
|
|
67220
|
-
var
|
|
67611
|
+
var import_picocolors41 = __toESM(require_picocolors(), 1);
|
|
67221
67612
|
|
|
67222
67613
|
// src/core/orchestration-manifest.ts
|
|
67223
|
-
import
|
|
67614
|
+
import path84 from "node:path";
|
|
67224
67615
|
import fs75 from "node:fs";
|
|
67225
|
-
var
|
|
67616
|
+
var import_yaml5 = __toESM(require_dist(), 1);
|
|
67226
67617
|
var ORCH_MANIFEST_FILE = "brainbase-orchestration.yaml";
|
|
67227
67618
|
var ORCH_MEMBERS_DIR = "agents";
|
|
67228
67619
|
var OrchMetaSchema = exports_external.object({
|
|
@@ -67274,7 +67665,7 @@ var OrchestrationManifestSchema = exports_external.object({
|
|
|
67274
67665
|
triggers: exports_external.array(TriggerSchema).optional()
|
|
67275
67666
|
});
|
|
67276
67667
|
function orchManifestPath(cwd2) {
|
|
67277
|
-
return
|
|
67668
|
+
return path84.join(cwd2, ORCH_MANIFEST_FILE);
|
|
67278
67669
|
}
|
|
67279
67670
|
function hasOrchManifest(cwd2) {
|
|
67280
67671
|
return fs75.existsSync(orchManifestPath(cwd2));
|
|
@@ -67286,7 +67677,7 @@ function readOrchManifest(cwd2) {
|
|
|
67286
67677
|
const raw = fs75.readFileSync(p2, "utf8");
|
|
67287
67678
|
let parsed;
|
|
67288
67679
|
try {
|
|
67289
|
-
parsed =
|
|
67680
|
+
parsed = import_yaml5.default.parse(raw);
|
|
67290
67681
|
} catch (err) {
|
|
67291
67682
|
throw new Error(`${ORCH_MANIFEST_FILE} is not valid YAML: ${err.message}`);
|
|
67292
67683
|
}
|
|
@@ -67297,7 +67688,7 @@ function readOrchManifest(cwd2) {
|
|
|
67297
67688
|
return result2.data;
|
|
67298
67689
|
}
|
|
67299
67690
|
function writeOrchManifest(cwd2, manifest) {
|
|
67300
|
-
const doc = new
|
|
67691
|
+
const doc = new import_yaml5.default.Document;
|
|
67301
67692
|
doc.contents = manifest;
|
|
67302
67693
|
doc.commentBefore = ` brainbase-orchestration.yaml — declarative orchestration manifest.
|
|
67303
67694
|
` + ` Committed to source control. Edit by hand, then
|
|
@@ -67307,7 +67698,7 @@ function writeOrchManifest(cwd2, manifest) {
|
|
|
67307
67698
|
fs75.writeFileSync(orchManifestPath(cwd2), String(doc), "utf8");
|
|
67308
67699
|
}
|
|
67309
67700
|
function memberDir(cwd2, slug) {
|
|
67310
|
-
return
|
|
67701
|
+
return path84.join(cwd2, ORCH_MEMBERS_DIR, slug);
|
|
67311
67702
|
}
|
|
67312
67703
|
var MEMBER_SLUG_MAX = 50;
|
|
67313
67704
|
function slugifyRaw(raw) {
|
|
@@ -67341,7 +67732,7 @@ function resolveMemberSlugs(members) {
|
|
|
67341
67732
|
}
|
|
67342
67733
|
|
|
67343
67734
|
// src/core/orchestration-link.ts
|
|
67344
|
-
import
|
|
67735
|
+
import path85 from "node:path";
|
|
67345
67736
|
import fs76 from "node:fs";
|
|
67346
67737
|
var ORCH_LINK_FILE = "orchestration-link.json";
|
|
67347
67738
|
var ORCH_SYNC_STATE_FILE = "orchestration-sync-state.json";
|
|
@@ -67376,10 +67767,10 @@ var OrchestrationSyncStateSchema = exports_external.object({
|
|
|
67376
67767
|
edges: exports_external.array(SyncedEdgeSchema)
|
|
67377
67768
|
});
|
|
67378
67769
|
function orchLinkPath(cwd2) {
|
|
67379
|
-
return
|
|
67770
|
+
return path85.join(cwd2, LINK_DIR, ORCH_LINK_FILE);
|
|
67380
67771
|
}
|
|
67381
67772
|
function orchSyncStatePath(cwd2) {
|
|
67382
|
-
return
|
|
67773
|
+
return path85.join(cwd2, LINK_DIR, ORCH_SYNC_STATE_FILE);
|
|
67383
67774
|
}
|
|
67384
67775
|
function readOrchLink(cwd2) {
|
|
67385
67776
|
const p2 = orchLinkPath(cwd2);
|
|
@@ -67392,7 +67783,7 @@ function readOrchLink(cwd2) {
|
|
|
67392
67783
|
}
|
|
67393
67784
|
}
|
|
67394
67785
|
function writeOrchLink(cwd2, link2) {
|
|
67395
|
-
ensureDir(
|
|
67786
|
+
ensureDir(path85.join(cwd2, LINK_DIR));
|
|
67396
67787
|
const clean2 = {};
|
|
67397
67788
|
for (const [k3, v3] of Object.entries(link2)) {
|
|
67398
67789
|
if (v3 !== null && v3 !== undefined)
|
|
@@ -67412,12 +67803,12 @@ function readOrchSyncState(cwd2) {
|
|
|
67412
67803
|
}
|
|
67413
67804
|
}
|
|
67414
67805
|
function writeOrchSyncState(cwd2, state) {
|
|
67415
|
-
ensureDir(
|
|
67806
|
+
ensureDir(path85.join(cwd2, LINK_DIR));
|
|
67416
67807
|
writeJson(orchSyncStatePath(cwd2), state);
|
|
67417
67808
|
ensureGitignore2(cwd2);
|
|
67418
67809
|
}
|
|
67419
67810
|
function ensureGitignore2(cwd2) {
|
|
67420
|
-
const ignorePath =
|
|
67811
|
+
const ignorePath = path85.join(cwd2, LINK_DIR, ".gitignore");
|
|
67421
67812
|
const desired = `${ORCH_SYNC_STATE_FILE}
|
|
67422
67813
|
`;
|
|
67423
67814
|
try {
|
|
@@ -67435,7 +67826,7 @@ function ensureGitignore2(cwd2) {
|
|
|
67435
67826
|
}
|
|
67436
67827
|
|
|
67437
67828
|
// src/core/agent-fresh-install.ts
|
|
67438
|
-
import
|
|
67829
|
+
import path86 from "node:path";
|
|
67439
67830
|
import fs77 from "node:fs";
|
|
67440
67831
|
import os15 from "node:os";
|
|
67441
67832
|
async function installAgentFresh(input) {
|
|
@@ -67458,7 +67849,7 @@ async function installAgentFresh(input) {
|
|
|
67458
67849
|
type: c2.type,
|
|
67459
67850
|
slug: c2.slug,
|
|
67460
67851
|
scope,
|
|
67461
|
-
rootDir:
|
|
67852
|
+
rootDir: path86.join(stageRoot, c2.type, c2.slug),
|
|
67462
67853
|
description: c2.description,
|
|
67463
67854
|
meta: c2.meta,
|
|
67464
67855
|
payload: proxifyMcpPayload(structuredClone(c2.meta?.mcp)),
|
|
@@ -67483,7 +67874,7 @@ async function installAgentFresh(input) {
|
|
|
67483
67874
|
const claimedByOther = folderClaimedByOtherAgent(cwd2, agent.id);
|
|
67484
67875
|
const localOnly = input.preserveManifest || claimedByOther ? {} : readLocalOnlyContentReporting(cwd2);
|
|
67485
67876
|
if (claimedByOther) {
|
|
67486
|
-
f2.warn(`${
|
|
67877
|
+
f2.warn(`${path86.basename(cwd2)} was linked to a different agent; its local-only blocks were left out of the rebuilt manifest.`);
|
|
67487
67878
|
}
|
|
67488
67879
|
const manifest = input.preserveManifest ? null : buildManifestFromCloud(cloud, agent, localOnly);
|
|
67489
67880
|
if (manifest)
|
|
@@ -67516,7 +67907,8 @@ async function installAgentFresh(input) {
|
|
|
67516
67907
|
name: agent.name,
|
|
67517
67908
|
tagline: agent.tagline,
|
|
67518
67909
|
...agent.machine_kind ? { machine_kind: agent.machine_kind } : {},
|
|
67519
|
-
...Object.prototype.hasOwnProperty.call(agent, "default_model") ? { default_model: agent.default_model ?? null } : {}
|
|
67910
|
+
...Object.prototype.hasOwnProperty.call(agent, "default_model") ? { default_model: agent.default_model ?? null } : {},
|
|
67911
|
+
...capabilityBaseline(agent, undefined)
|
|
67520
67912
|
}
|
|
67521
67913
|
});
|
|
67522
67914
|
const returnedManifest = manifest ?? buildManifestFromCloud(cloud, agent, localOnly);
|
|
@@ -67532,13 +67924,13 @@ async function installAgentFresh(input) {
|
|
|
67532
67924
|
}
|
|
67533
67925
|
}
|
|
67534
67926
|
function stageManifestComponents2(components) {
|
|
67535
|
-
const root = fs77.mkdtempSync(
|
|
67927
|
+
const root = fs77.mkdtempSync(path86.join(os15.tmpdir(), "brainbase-orch-pull-"));
|
|
67536
67928
|
for (const c2 of components) {
|
|
67537
|
-
const compDir =
|
|
67929
|
+
const compDir = path86.join(root, c2.type, c2.slug);
|
|
67538
67930
|
ensureDir(compDir);
|
|
67539
67931
|
for (const f4 of c2.files) {
|
|
67540
|
-
const target =
|
|
67541
|
-
ensureDir(
|
|
67932
|
+
const target = path86.join(compDir, f4.path);
|
|
67933
|
+
ensureDir(path86.dirname(target));
|
|
67542
67934
|
fs77.writeFileSync(target, f4.content);
|
|
67543
67935
|
}
|
|
67544
67936
|
}
|
|
@@ -67572,8 +67964,8 @@ function materializeInstructions2(cwd2, cloud) {
|
|
|
67572
67964
|
const body = c2.files[0]?.content ?? "";
|
|
67573
67965
|
if (!body.trim())
|
|
67574
67966
|
continue;
|
|
67575
|
-
const target =
|
|
67576
|
-
ensureDir(
|
|
67967
|
+
const target = path86.join(cwd2, DEFAULT_INSTRUCTIONS_FILE);
|
|
67968
|
+
ensureDir(path86.dirname(target));
|
|
67577
67969
|
fs77.writeFileSync(target, normalizeInstructionBody(body), "utf8");
|
|
67578
67970
|
return;
|
|
67579
67971
|
}
|
|
@@ -67586,8 +67978,8 @@ function materializePlaybooks2(cwd2, cloud) {
|
|
|
67586
67978
|
if (!raw.trim())
|
|
67587
67979
|
continue;
|
|
67588
67980
|
const { body } = stripPlaybookFrontmatter(raw);
|
|
67589
|
-
const target =
|
|
67590
|
-
ensureDir(
|
|
67981
|
+
const target = path86.join(cwd2, DEFAULT_PLAYBOOKS_DIR, `${c2.slug}.md`);
|
|
67982
|
+
ensureDir(path86.dirname(target));
|
|
67591
67983
|
fs77.writeFileSync(target, body, "utf8");
|
|
67592
67984
|
}
|
|
67593
67985
|
}
|
|
@@ -67630,7 +68022,7 @@ function buildManifestFromCloud(cloud, agent, localOnly = {}) {
|
|
|
67630
68022
|
title,
|
|
67631
68023
|
...description ? { description } : {},
|
|
67632
68024
|
...typeof pbMeta.icon === "string" && pbMeta.icon ? { icon: pbMeta.icon } : {},
|
|
67633
|
-
content: { file:
|
|
68025
|
+
content: { file: path86.join(DEFAULT_PLAYBOOKS_DIR, `${c2.slug}.md`) }
|
|
67634
68026
|
};
|
|
67635
68027
|
});
|
|
67636
68028
|
const caps = capabilitiesFromAgent(agent);
|
|
@@ -67737,8 +68129,8 @@ async function runOrchestrationPull(cwd2, args) {
|
|
|
67737
68129
|
orchId = args.orchestrationId;
|
|
67738
68130
|
} else {
|
|
67739
68131
|
f2.warn("This folder is not linked to any orchestration.");
|
|
67740
|
-
f2.info(`Run ${
|
|
67741
|
-
or ${
|
|
68132
|
+
f2.info(`Run ${import_picocolors41.default.cyan("brainbase orchestration pull <id>")} with an orchestration id,
|
|
68133
|
+
or ${import_picocolors41.default.cyan("brainbase orchestration list")} to find one.`);
|
|
67742
68134
|
return;
|
|
67743
68135
|
}
|
|
67744
68136
|
const sp = de();
|
|
@@ -67757,24 +68149,24 @@ async function runOrchestrationPull(cwd2, args) {
|
|
|
67757
68149
|
const slugFor = (agentId) => slugByAgent.get(agentId) ?? agentId;
|
|
67758
68150
|
const planLines = [];
|
|
67759
68151
|
planLines.push("");
|
|
67760
|
-
planLines.push(` ${
|
|
68152
|
+
planLines.push(` ${import_picocolors41.default.bold(cloud.name)} ${import_picocolors41.default.dim(`(${cloud.id})`)}`);
|
|
67761
68153
|
if (cloud.description)
|
|
67762
|
-
planLines.push(` ${
|
|
68154
|
+
planLines.push(` ${import_picocolors41.default.dim(cloud.description)}`);
|
|
67763
68155
|
planLines.push("");
|
|
67764
|
-
planLines.push(` ${
|
|
68156
|
+
planLines.push(` ${import_picocolors41.default.dim("members:")}`);
|
|
67765
68157
|
for (const m3 of cloud.members) {
|
|
67766
68158
|
const skipped = !m3.manifest;
|
|
67767
|
-
const tail2 = skipped ?
|
|
67768
|
-
planLines.push(` ${
|
|
68159
|
+
const tail2 = skipped ? import_picocolors41.default.red(" (manifest unavailable — skipped)") : "";
|
|
68160
|
+
planLines.push(` ${import_picocolors41.default.cyan("•")} ${import_picocolors41.default.bold(slugFor(m3.agent_id))} ${import_picocolors41.default.dim(`(${m3.name})`)}${tail2}`);
|
|
67769
68161
|
}
|
|
67770
68162
|
if (cloud.edges.length) {
|
|
67771
68163
|
planLines.push("");
|
|
67772
|
-
planLines.push(` ${
|
|
68164
|
+
planLines.push(` ${import_picocolors41.default.dim("edges:")}`);
|
|
67773
68165
|
for (const e2 of cloud.edges) {
|
|
67774
68166
|
const from = slugFor(e2.from_agent_id);
|
|
67775
68167
|
const to2 = slugFor(e2.to_agent_id);
|
|
67776
|
-
const desc = e2.description ? ` ${
|
|
67777
|
-
planLines.push(` ${
|
|
68168
|
+
const desc = e2.description ? ` ${import_picocolors41.default.dim("— " + e2.description)}` : "";
|
|
68169
|
+
planLines.push(` ${import_picocolors41.default.cyan(from)} ${import_picocolors41.default.dim("→")} ${import_picocolors41.default.cyan(to2)}${desc}`);
|
|
67778
68170
|
}
|
|
67779
68171
|
}
|
|
67780
68172
|
planLines.push("");
|
|
@@ -67783,7 +68175,7 @@ async function runOrchestrationPull(cwd2, args) {
|
|
|
67783
68175
|
const isRefresh = !!existingLink;
|
|
67784
68176
|
if (!autoProceed(args.yes) && !isRefresh) {
|
|
67785
68177
|
const ok = await se({
|
|
67786
|
-
message: `Pull into ${
|
|
68178
|
+
message: `Pull into ${import_picocolors41.default.bold(cwd2)}?`,
|
|
67787
68179
|
initialValue: true
|
|
67788
68180
|
});
|
|
67789
68181
|
if (!ensureNotCancelled(ok)) {
|
|
@@ -67827,7 +68219,7 @@ async function runOrchestrationPull(cwd2, args) {
|
|
|
67827
68219
|
scope: "project",
|
|
67828
68220
|
pullSecrets: true
|
|
67829
68221
|
});
|
|
67830
|
-
memberSp.stop(`Installed ${
|
|
68222
|
+
memberSp.stop(`Installed ${import_picocolors41.default.bold(slug)} ${import_picocolors41.default.dim(`(${m3.manifest.components.length} components)`)}.`);
|
|
67831
68223
|
installedMembers.push({
|
|
67832
68224
|
agent_id: m3.agent_id,
|
|
67833
68225
|
slug,
|
|
@@ -67888,7 +68280,7 @@ async function runOrchestrationPull(cwd2, args) {
|
|
|
67888
68280
|
payload_schema: e2.payload_schema ?? {}
|
|
67889
68281
|
}))
|
|
67890
68282
|
});
|
|
67891
|
-
$e(`Pulled ${cloud.name} at revision ${cloud.revision} into ${
|
|
68283
|
+
$e(`Pulled ${cloud.name} at revision ${cloud.revision} into ${path87.basename(cwd2)}/ ${import_picocolors41.default.dim(`(${installedMembers.length}/${cloud.members.length} members)`)}.`);
|
|
67892
68284
|
}
|
|
67893
68285
|
function handleApiError5(err) {
|
|
67894
68286
|
if (err instanceof ApiError) {
|
|
@@ -67905,7 +68297,7 @@ function handleApiError5(err) {
|
|
|
67905
68297
|
}
|
|
67906
68298
|
|
|
67907
68299
|
// src/cli/orchestration-push.ts
|
|
67908
|
-
var
|
|
68300
|
+
var import_picocolors42 = __toESM(require_picocolors(), 1);
|
|
67909
68301
|
|
|
67910
68302
|
// src/core/orchestration-outgoing.ts
|
|
67911
68303
|
function buildOrchestrationGraphPayload(manifest, slugToAgentId) {
|
|
@@ -67988,7 +68380,7 @@ function findUnpushableMembers(cwd2, members) {
|
|
|
67988
68380
|
continue;
|
|
67989
68381
|
}
|
|
67990
68382
|
if (!memberManifest.id) {
|
|
67991
|
-
f2.error(`${m3.slug}: ${AGENT_MANIFEST_FILE} is unclaimed (no ${
|
|
68383
|
+
f2.error(`${m3.slug}: ${AGENT_MANIFEST_FILE} is unclaimed (no ${import_picocolors42.default.cyan("id")}), so there is nothing to push to.`);
|
|
67992
68384
|
blocked.push(m3.slug);
|
|
67993
68385
|
continue;
|
|
67994
68386
|
}
|
|
@@ -68003,12 +68395,12 @@ async function runOrchestrationPush(cwd2, args) {
|
|
|
68003
68395
|
const link2 = readOrchLink(cwd2);
|
|
68004
68396
|
if (!link2) {
|
|
68005
68397
|
f2.warn("This folder is not linked to any orchestration.");
|
|
68006
|
-
f2.info(`Run ${
|
|
68398
|
+
f2.info(`Run ${import_picocolors42.default.cyan("brainbase orchestration pull <id>")} first.`);
|
|
68007
68399
|
return;
|
|
68008
68400
|
}
|
|
68009
68401
|
if (!hasOrchManifest(cwd2)) {
|
|
68010
|
-
f2.warn(`No ${
|
|
68011
|
-
f2.info(`Run ${
|
|
68402
|
+
f2.warn(`No ${import_picocolors42.default.bold(ORCH_MANIFEST_FILE)} here.`);
|
|
68403
|
+
f2.info(`Run ${import_picocolors42.default.cyan("brainbase orchestration pull")} to materialise the manifest before pushing.`);
|
|
68012
68404
|
return;
|
|
68013
68405
|
}
|
|
68014
68406
|
let manifest;
|
|
@@ -68032,7 +68424,7 @@ async function runOrchestrationPush(cwd2, args) {
|
|
|
68032
68424
|
}
|
|
68033
68425
|
if (missing.length) {
|
|
68034
68426
|
f2.error(`Missing local checkouts for: ${missing.join(", ")}.`);
|
|
68035
|
-
f2.info(`Run ${
|
|
68427
|
+
f2.info(`Run ${import_picocolors42.default.cyan("brainbase orchestration pull")} to materialise the missing folders.`);
|
|
68036
68428
|
process.exitCode = 1;
|
|
68037
68429
|
return;
|
|
68038
68430
|
}
|
|
@@ -68053,13 +68445,13 @@ async function runOrchestrationPush(cwd2, args) {
|
|
|
68053
68445
|
}
|
|
68054
68446
|
}
|
|
68055
68447
|
const plan = [""];
|
|
68056
|
-
plan.push(` ${
|
|
68057
|
-
plan.push(` ${
|
|
68448
|
+
plan.push(` ${import_picocolors42.default.bold(link2.name)} ${import_picocolors42.default.dim(`(${link2.orchestration_id})`)}`);
|
|
68449
|
+
plan.push(` ${import_picocolors42.default.dim(`${manifest.members.length} member${manifest.members.length === 1 ? "" : "s"}, ${manifest.edges.length} edge${manifest.edges.length === 1 ? "" : "s"}, ${graph.triggers.length} trigger${graph.triggers.length === 1 ? "" : "s"}`)}`);
|
|
68058
68450
|
plan.push("");
|
|
68059
68451
|
if (!args.graphOnly) {
|
|
68060
|
-
plan.push(` ${
|
|
68452
|
+
plan.push(` ${import_picocolors42.default.dim("per-member agent push:")}`);
|
|
68061
68453
|
for (const m3 of manifest.members) {
|
|
68062
|
-
plan.push(` ${
|
|
68454
|
+
plan.push(` ${import_picocolors42.default.cyan("•")} ${import_picocolors42.default.bold(m3.slug)}`);
|
|
68063
68455
|
}
|
|
68064
68456
|
plan.push("");
|
|
68065
68457
|
}
|
|
@@ -68079,7 +68471,7 @@ async function runOrchestrationPush(cwd2, args) {
|
|
|
68079
68471
|
for (const m3 of manifest.members) {
|
|
68080
68472
|
const dir = memberDir(cwd2, m3.slug);
|
|
68081
68473
|
console.log("");
|
|
68082
|
-
console.log(`${
|
|
68474
|
+
console.log(`${import_picocolors42.default.dim("───")} ${import_picocolors42.default.bold(m3.slug)} ${import_picocolors42.default.dim("───")}`);
|
|
68083
68475
|
const exitCodeBeforePush = process.exitCode;
|
|
68084
68476
|
try {
|
|
68085
68477
|
await runAgentPush(dir, { yes: true });
|
|
@@ -68143,7 +68535,7 @@ function handleApiError6(err) {
|
|
|
68143
68535
|
f2.error("You do not have access to this orchestration.");
|
|
68144
68536
|
} else if (err.status === 409) {
|
|
68145
68537
|
f2.error(err.message);
|
|
68146
|
-
f2.info(`Run ${
|
|
68538
|
+
f2.info(`Run ${import_picocolors42.default.cyan("brainbase orchestration pull")} to reconcile, then push again.`);
|
|
68147
68539
|
} else {
|
|
68148
68540
|
f2.error(err.message);
|
|
68149
68541
|
}
|
|
@@ -68153,13 +68545,13 @@ function handleApiError6(err) {
|
|
|
68153
68545
|
}
|
|
68154
68546
|
|
|
68155
68547
|
// src/cli/orchestration-status.ts
|
|
68156
|
-
var
|
|
68548
|
+
var import_picocolors43 = __toESM(require_picocolors(), 1);
|
|
68157
68549
|
async function runOrchestrationStatus(cwd2) {
|
|
68158
68550
|
banner("orchestration status — what changed locally, remotely, both");
|
|
68159
68551
|
const link2 = readOrchLink(cwd2);
|
|
68160
68552
|
if (!link2) {
|
|
68161
68553
|
f2.warn("This folder is not linked to any orchestration.");
|
|
68162
|
-
f2.info(`Run ${
|
|
68554
|
+
f2.info(`Run ${import_picocolors43.default.cyan("brainbase orchestration pull <id>")} first.`);
|
|
68163
68555
|
return;
|
|
68164
68556
|
}
|
|
68165
68557
|
const localManifest = hasOrchManifest(cwd2) ? readOrchManifest(cwd2) : null;
|
|
@@ -68182,8 +68574,8 @@ async function runOrchestrationStatus(cwd2) {
|
|
|
68182
68574
|
}
|
|
68183
68575
|
const lines = [];
|
|
68184
68576
|
lines.push("");
|
|
68185
|
-
lines.push(` ${
|
|
68186
|
-
lines.push(` ${
|
|
68577
|
+
lines.push(` ${import_picocolors43.default.bold(link2.name)} ${import_picocolors43.default.dim(`(${link2.orchestration_id})`)}`);
|
|
68578
|
+
lines.push(` ${import_picocolors43.default.dim("revision")} cloud ${cloud.revision}${lock ? ` · lock ${lock.revision}` : " · never pulled"}`);
|
|
68187
68579
|
lines.push("");
|
|
68188
68580
|
const localSlugByAgentId = new Map;
|
|
68189
68581
|
for (const m3 of localManifest?.members ?? []) {
|
|
@@ -68197,12 +68589,12 @@ async function runOrchestrationStatus(cwd2) {
|
|
|
68197
68589
|
const membersAdded = [...localMemberSet].filter((s3) => !cloudMemberSet.has(s3));
|
|
68198
68590
|
const membersRemoved = [...cloudMemberSet].filter((s3) => !localMemberSet.has(s3));
|
|
68199
68591
|
if (membersAdded.length || membersRemoved.length) {
|
|
68200
|
-
lines.push(` ${
|
|
68592
|
+
lines.push(` ${import_picocolors43.default.bold("members")}`);
|
|
68201
68593
|
for (const slug of membersAdded) {
|
|
68202
|
-
lines.push(` ${
|
|
68594
|
+
lines.push(` ${import_picocolors43.default.yellow("→ push")} added in yaml: ${import_picocolors43.default.bold(slug)}`);
|
|
68203
68595
|
}
|
|
68204
68596
|
for (const slug of membersRemoved) {
|
|
68205
|
-
lines.push(` ${
|
|
68597
|
+
lines.push(` ${import_picocolors43.default.cyan("← pull")} added on cloud: ${import_picocolors43.default.bold(slug)}`);
|
|
68206
68598
|
}
|
|
68207
68599
|
lines.push("");
|
|
68208
68600
|
}
|
|
@@ -68217,11 +68609,11 @@ async function runOrchestrationStatus(cwd2) {
|
|
|
68217
68609
|
const edgesAdded = [...localEdges.keys()].filter((k3) => !cloudEdges.has(k3));
|
|
68218
68610
|
const edgesRemoved = [...cloudEdges.keys()].filter((k3) => !localEdges.has(k3));
|
|
68219
68611
|
if (edgesAdded.length || edgesRemoved.length) {
|
|
68220
|
-
lines.push(` ${
|
|
68612
|
+
lines.push(` ${import_picocolors43.default.bold("edges")}`);
|
|
68221
68613
|
for (const k3 of edgesAdded)
|
|
68222
|
-
lines.push(` ${
|
|
68614
|
+
lines.push(` ${import_picocolors43.default.yellow("→ push")} added in yaml: ${k3}`);
|
|
68223
68615
|
for (const k3 of edgesRemoved)
|
|
68224
|
-
lines.push(` ${
|
|
68616
|
+
lines.push(` ${import_picocolors43.default.cyan("← pull")} added on cloud: ${k3}`);
|
|
68225
68617
|
lines.push("");
|
|
68226
68618
|
}
|
|
68227
68619
|
const cloudTriggerKey = (t) => {
|
|
@@ -68259,11 +68651,11 @@ async function runOrchestrationStatus(cwd2) {
|
|
|
68259
68651
|
const triggersAdded = [...localTriggers.keys()].filter((k3) => !cloudTriggers.has(k3));
|
|
68260
68652
|
const triggersRemoved = [...cloudTriggers.keys()].filter((k3) => !localTriggers.has(k3));
|
|
68261
68653
|
if (triggersAdded.length || triggersRemoved.length) {
|
|
68262
|
-
lines.push(` ${
|
|
68654
|
+
lines.push(` ${import_picocolors43.default.bold("schedule triggers")}`);
|
|
68263
68655
|
for (const k3 of triggersAdded)
|
|
68264
|
-
lines.push(` ${
|
|
68656
|
+
lines.push(` ${import_picocolors43.default.yellow("→ push")} added/changed in yaml: ${localTriggers.get(k3) ?? k3}`);
|
|
68265
68657
|
for (const k3 of triggersRemoved)
|
|
68266
|
-
lines.push(` ${
|
|
68658
|
+
lines.push(` ${import_picocolors43.default.cyan("← pull")} added/changed on cloud: ${cloudTriggers.get(k3) ?? k3}`);
|
|
68267
68659
|
lines.push("");
|
|
68268
68660
|
}
|
|
68269
68661
|
const lockByAgentId = new Map((lock?.members ?? []).map((m3) => [m3.agent_id, m3]));
|
|
@@ -68286,27 +68678,27 @@ async function runOrchestrationStatus(cwd2) {
|
|
|
68286
68678
|
}
|
|
68287
68679
|
}
|
|
68288
68680
|
if (memberDrift.length) {
|
|
68289
|
-
lines.push(` ${
|
|
68681
|
+
lines.push(` ${import_picocolors43.default.bold("member content drift")}`);
|
|
68290
68682
|
for (const d3 of memberDrift) {
|
|
68291
|
-
lines.push(` ${
|
|
68683
|
+
lines.push(` ${import_picocolors43.default.cyan("?")} ${import_picocolors43.default.bold(d3.slug)} ${import_picocolors43.default.dim("— " + d3.reason)}`);
|
|
68292
68684
|
}
|
|
68293
|
-
lines.push(` ${
|
|
68685
|
+
lines.push(` ${import_picocolors43.default.dim("cd into each member folder and run")} ${import_picocolors43.default.cyan("brainbase agent status")}`);
|
|
68294
68686
|
lines.push("");
|
|
68295
68687
|
}
|
|
68296
68688
|
const revisionDrift = lock?.revision != null && cloud.revision !== lock.revision;
|
|
68297
68689
|
if (revisionDrift) {
|
|
68298
|
-
lines.push(` ${
|
|
68299
|
-
lines.push(` ${
|
|
68690
|
+
lines.push(` ${import_picocolors43.default.bold("cloud revision")}`);
|
|
68691
|
+
lines.push(` ${import_picocolors43.default.cyan("← pull")} cloud changed since last pull: ${import_picocolors43.default.dim(`lock ${lock.revision} → cloud ${cloud.revision}`)}`);
|
|
68300
68692
|
lines.push("");
|
|
68301
68693
|
}
|
|
68302
68694
|
if (!membersAdded.length && !membersRemoved.length && !edgesAdded.length && !edgesRemoved.length && !triggersAdded.length && !triggersRemoved.length && !memberDrift.length && !revisionDrift) {
|
|
68303
|
-
lines.push(` ${
|
|
68695
|
+
lines.push(` ${import_picocolors43.default.green("✓")} everything is in sync`);
|
|
68304
68696
|
lines.push("");
|
|
68305
68697
|
console.log(lines.join(`
|
|
68306
68698
|
`));
|
|
68307
68699
|
return;
|
|
68308
68700
|
}
|
|
68309
|
-
lines.push(` ${
|
|
68701
|
+
lines.push(` ${import_picocolors43.default.dim("run")} ${import_picocolors43.default.cyan("brainbase orchestration pull")} ${import_picocolors43.default.dim("to apply cloud changes,")} ${import_picocolors43.default.cyan("brainbase orchestration push")} ${import_picocolors43.default.dim("to send yours")}`);
|
|
68310
68702
|
lines.push("");
|
|
68311
68703
|
console.log(lines.join(`
|
|
68312
68704
|
`));
|
|
@@ -68321,7 +68713,7 @@ function stableJson(value) {
|
|
|
68321
68713
|
}
|
|
68322
68714
|
|
|
68323
68715
|
// src/cli/orchestration-list.ts
|
|
68324
|
-
var
|
|
68716
|
+
var import_picocolors44 = __toESM(require_picocolors(), 1);
|
|
68325
68717
|
async function runOrchestrationList(args) {
|
|
68326
68718
|
banner("orchestration list — orchestrations under a team");
|
|
68327
68719
|
const { org, team } = await resolveOrgAndTeam({
|
|
@@ -68345,13 +68737,13 @@ async function runOrchestrationList(args) {
|
|
|
68345
68737
|
}
|
|
68346
68738
|
const lines = [""];
|
|
68347
68739
|
for (const o2 of items) {
|
|
68348
|
-
lines.push(` ${
|
|
68740
|
+
lines.push(` ${import_picocolors44.default.bold(o2.name)} ${import_picocolors44.default.dim(o2.id)}`);
|
|
68349
68741
|
if (o2.description)
|
|
68350
|
-
lines.push(` ${
|
|
68351
|
-
lines.push(` ${
|
|
68742
|
+
lines.push(` ${import_picocolors44.default.dim(o2.description)}`);
|
|
68743
|
+
lines.push(` ${import_picocolors44.default.dim(`${o2.member_count} member${o2.member_count === 1 ? "" : "s"} · ${o2.edge_count} edge${o2.edge_count === 1 ? "" : "s"}`)}`);
|
|
68352
68744
|
lines.push("");
|
|
68353
68745
|
}
|
|
68354
|
-
lines.push(` ${
|
|
68746
|
+
lines.push(` ${import_picocolors44.default.dim("pull one with")} ${import_picocolors44.default.cyan("brainbase orchestration pull <id>")}`);
|
|
68355
68747
|
lines.push("");
|
|
68356
68748
|
console.log(lines.join(`
|
|
68357
68749
|
`));
|
|
@@ -68359,7 +68751,7 @@ async function runOrchestrationList(args) {
|
|
|
68359
68751
|
|
|
68360
68752
|
// src/cli/orchestration-add-agent.ts
|
|
68361
68753
|
import fs79 from "node:fs";
|
|
68362
|
-
var
|
|
68754
|
+
var import_picocolors45 = __toESM(require_picocolors(), 1);
|
|
68363
68755
|
|
|
68364
68756
|
// src/core/orchestration-add.ts
|
|
68365
68757
|
function resolveOrgIdForGroup(groupId, orgsWithTeams) {
|
|
@@ -68424,7 +68816,7 @@ async function runOrchestrationAddAgent(cwd2, args) {
|
|
|
68424
68816
|
const link2 = readOrchLink(cwd2);
|
|
68425
68817
|
if (!link2 || !hasOrchManifest(cwd2)) {
|
|
68426
68818
|
f2.warn("This folder is not a linked orchestration.");
|
|
68427
|
-
f2.info(`Run ${
|
|
68819
|
+
f2.info(`Run ${import_picocolors45.default.cyan("brainbase orchestration pull <id>")} first.`);
|
|
68428
68820
|
return;
|
|
68429
68821
|
}
|
|
68430
68822
|
let manifest;
|
|
@@ -68450,7 +68842,7 @@ async function runOrchestrationAddAgent(cwd2, args) {
|
|
|
68450
68842
|
while (manifest.members.some((m3) => m3.slug === candidate) || fs79.existsSync(memberDir(cwd2, candidate))) {
|
|
68451
68843
|
candidate = `${slug}-${++n}`;
|
|
68452
68844
|
}
|
|
68453
|
-
f2.info(`Slug ${
|
|
68845
|
+
f2.info(`Slug ${import_picocolors45.default.bold(slug)} is taken — using ${import_picocolors45.default.bold(candidate)}.`);
|
|
68454
68846
|
slug = candidate;
|
|
68455
68847
|
}
|
|
68456
68848
|
let payloadSchema;
|
|
@@ -68474,7 +68866,7 @@ async function runOrchestrationAddAgent(cwd2, args) {
|
|
|
68474
68866
|
const resolved = resolveOrgIdForGroup(link2.group_id, orgsWithTeams);
|
|
68475
68867
|
if (!resolved) {
|
|
68476
68868
|
sp.stop("Failed.");
|
|
68477
|
-
f2.error(`Could not find an org that owns group ${
|
|
68869
|
+
f2.error(`Could not find an org that owns group ${import_picocolors45.default.bold(link2.group_id)}. ` + `Pass ${import_picocolors45.default.cyan("--org <id>")} explicitly.`);
|
|
68478
68870
|
return;
|
|
68479
68871
|
}
|
|
68480
68872
|
orgId = resolved;
|
|
@@ -68491,14 +68883,14 @@ async function runOrchestrationAddAgent(cwd2, args) {
|
|
|
68491
68883
|
if (from.length === 0 && to2.length === 0 && isInteractive() && manifest.members.length > 0) {
|
|
68492
68884
|
const memberOptions = manifest.members.map((m3) => ({ value: m3.slug, label: m3.slug }));
|
|
68493
68885
|
const pickedFrom = await ae({
|
|
68494
|
-
message: `Connect ${
|
|
68886
|
+
message: `Connect ${import_picocolors45.default.bold(slug)} FROM which member(s)? — edges INTO ${slug} (space to select, enter to skip)`,
|
|
68495
68887
|
options: memberOptions,
|
|
68496
68888
|
required: false
|
|
68497
68889
|
});
|
|
68498
68890
|
if (Array.isArray(pickedFrom))
|
|
68499
68891
|
from = pickedFrom;
|
|
68500
68892
|
const pickedTo = await ae({
|
|
68501
|
-
message: `Connect ${
|
|
68893
|
+
message: `Connect ${import_picocolors45.default.bold(slug)} TO which member(s)? — edges OUT of ${slug} (space to select, enter to skip)`,
|
|
68502
68894
|
options: memberOptions,
|
|
68503
68895
|
required: false
|
|
68504
68896
|
});
|
|
@@ -68537,23 +68929,23 @@ async function runOrchestrationAddAgent(cwd2, args) {
|
|
|
68537
68929
|
}
|
|
68538
68930
|
writeOrchManifest(cwd2, updated);
|
|
68539
68931
|
if (args.noPush) {
|
|
68540
|
-
f2.info(`Manifest updated. Run ${
|
|
68932
|
+
f2.info(`Manifest updated. Run ${import_picocolors45.default.cyan("brainbase orchestration push")} to apply.`);
|
|
68541
68933
|
return;
|
|
68542
68934
|
}
|
|
68543
68935
|
await runOrchestrationPush(cwd2, { yes: true, graphOnly: true });
|
|
68544
68936
|
}
|
|
68545
68937
|
|
|
68546
68938
|
// src/cli/orchestration-create.ts
|
|
68547
|
-
var
|
|
68939
|
+
var import_picocolors46 = __toESM(require_picocolors(), 1);
|
|
68548
68940
|
async function runOrchestrationCreate(cwd2, args) {
|
|
68549
68941
|
banner("orchestration create — claim a brainbase-orchestration.yaml");
|
|
68550
68942
|
if (readOrchLink(cwd2)) {
|
|
68551
68943
|
f2.warn("This folder is already linked to an orchestration.");
|
|
68552
|
-
f2.info(`Run ${
|
|
68944
|
+
f2.info(`Run ${import_picocolors46.default.cyan("brainbase orchestration push")} to update it.`);
|
|
68553
68945
|
return;
|
|
68554
68946
|
}
|
|
68555
68947
|
if (!hasOrchManifest(cwd2)) {
|
|
68556
|
-
f2.warn(`No ${
|
|
68948
|
+
f2.warn(`No ${import_picocolors46.default.bold(ORCH_MANIFEST_FILE)} here.`);
|
|
68557
68949
|
f2.info(`Create one, or pull an existing orchestration first.`);
|
|
68558
68950
|
return;
|
|
68559
68951
|
}
|
|
@@ -68586,10 +68978,10 @@ async function runOrchestrationCreate(cwd2, args) {
|
|
|
68586
68978
|
});
|
|
68587
68979
|
const plan = [
|
|
68588
68980
|
"",
|
|
68589
|
-
` ${
|
|
68590
|
-
` ${
|
|
68591
|
-
` ${
|
|
68592
|
-
` ${
|
|
68981
|
+
` ${import_picocolors46.default.bold(manifest.orchestration.name)}`,
|
|
68982
|
+
` ${import_picocolors46.default.dim("org")} ${import_picocolors46.default.bold(target.org.name)}`,
|
|
68983
|
+
` ${import_picocolors46.default.dim("team")} ${import_picocolors46.default.bold(target.team.name)}`,
|
|
68984
|
+
` ${import_picocolors46.default.dim("graph")} ${manifest.members.length} member${manifest.members.length === 1 ? "" : "s"}, ${manifest.edges.length} edge${manifest.edges.length === 1 ? "" : "s"}, ${graph.triggers.length} trigger${graph.triggers.length === 1 ? "" : "s"}`,
|
|
68593
68985
|
""
|
|
68594
68986
|
];
|
|
68595
68987
|
console.log(plan.join(`
|
|
@@ -68619,7 +69011,7 @@ async function runOrchestrationCreate(cwd2, args) {
|
|
|
68619
69011
|
edges: graph.edges,
|
|
68620
69012
|
triggers: graph.triggers
|
|
68621
69013
|
});
|
|
68622
|
-
sp.stop(`Created ${
|
|
69014
|
+
sp.stop(`Created ${import_picocolors46.default.bold(created.name)}.`);
|
|
68623
69015
|
writeOrchLink(cwd2, {
|
|
68624
69016
|
schemaVersion: 1,
|
|
68625
69017
|
orchestration_id: created.id,
|
|
@@ -68732,21 +69124,21 @@ async function runOrchestration(cwd2, sub, args, opts) {
|
|
|
68732
69124
|
function printHelp3() {
|
|
68733
69125
|
const out = [];
|
|
68734
69126
|
out.push("");
|
|
68735
|
-
out.push(` ${
|
|
69127
|
+
out.push(` ${import_picocolors47.default.bold("brainbase orchestration")} ${import_picocolors47.default.dim("<sub> [options]")}`);
|
|
68736
69128
|
out.push("");
|
|
68737
|
-
out.push(` ${
|
|
68738
|
-
out.push(` ${
|
|
68739
|
-
out.push(` ${
|
|
68740
|
-
out.push(` ${
|
|
68741
|
-
out.push(` ${
|
|
68742
|
-
out.push(` ${
|
|
69129
|
+
out.push(` ${import_picocolors47.default.cyan("create")} ${import_picocolors47.default.dim("claim a local orchestration manifest and create it in the cloud")}`);
|
|
69130
|
+
out.push(` ${import_picocolors47.default.cyan("pull")} ${import_picocolors47.default.dim("<id>")} ${import_picocolors47.default.dim("fetch orchestration + every member agent into this folder")}`);
|
|
69131
|
+
out.push(` ${import_picocolors47.default.cyan("push")} ${import_picocolors47.default.dim("push each member, then update the orchestration graph")}`);
|
|
69132
|
+
out.push(` ${import_picocolors47.default.cyan("add-agent")} ${import_picocolors47.default.dim("<name>")} ${import_picocolors47.default.dim("create a member agent, wire edges (--from/--to), and push")}`);
|
|
69133
|
+
out.push(` ${import_picocolors47.default.cyan("status")} ${import_picocolors47.default.dim("show what would push and what would pull")}`);
|
|
69134
|
+
out.push(` ${import_picocolors47.default.cyan("list")} ${import_picocolors47.default.dim("list orchestrations under a team")}`);
|
|
68743
69135
|
out.push("");
|
|
68744
|
-
out.push(` ${
|
|
68745
|
-
out.push(` ${
|
|
68746
|
-
out.push(` ${
|
|
68747
|
-
out.push(` ${
|
|
68748
|
-
out.push(` ${
|
|
68749
|
-
out.push(` ${
|
|
69136
|
+
out.push(` ${import_picocolors47.default.bold("Flags")}`);
|
|
69137
|
+
out.push(` ${import_picocolors47.default.dim("--yes, -y")} skip confirmations`);
|
|
69138
|
+
out.push(` ${import_picocolors47.default.dim("--harness <id>")} harness for newly-created member folders (default claude-code)`);
|
|
69139
|
+
out.push(` ${import_picocolors47.default.dim("--graph-only")} for push: only update members + edges, skip per-member push`);
|
|
69140
|
+
out.push(` ${import_picocolors47.default.dim("--org <id>")} for create/list: org id or slug (CLI vocab — DB teams.id)`);
|
|
69141
|
+
out.push(` ${import_picocolors47.default.dim("--team <id>")} for create/list: team id (CLI vocab — DB groups.id)`);
|
|
68750
69142
|
out.push("");
|
|
68751
69143
|
console.log(out.join(`
|
|
68752
69144
|
`));
|
|
@@ -68791,11 +69183,11 @@ async function runRun(cwd2, args) {
|
|
|
68791
69183
|
}
|
|
68792
69184
|
|
|
68793
69185
|
// src/cli/publish.ts
|
|
68794
|
-
var
|
|
69186
|
+
var import_picocolors48 = __toESM(require_picocolors(), 1);
|
|
68795
69187
|
function runPublish() {
|
|
68796
69188
|
banner("publish — moved");
|
|
68797
|
-
f2.error(`${
|
|
68798
|
-
f2.info(`Use ${
|
|
69189
|
+
f2.error(`${import_picocolors48.default.bold("brainbase publish")} does not exist.`);
|
|
69190
|
+
f2.info(`Use ${import_picocolors48.default.cyan("brainbase agent push")} to send your local changes to the cloud.`);
|
|
68799
69191
|
process.exit(1);
|
|
68800
69192
|
}
|
|
68801
69193
|
|
|
@@ -69094,7 +69486,7 @@ async function runStatus(cwd2) {
|
|
|
69094
69486
|
}
|
|
69095
69487
|
|
|
69096
69488
|
// src/cli/token.ts
|
|
69097
|
-
var
|
|
69489
|
+
var import_picocolors49 = __toESM(require_picocolors(), 1);
|
|
69098
69490
|
|
|
69099
69491
|
// src/ui/ink/TokenCards.tsx
|
|
69100
69492
|
var jsx_dev_runtime17 = __toESM(require_jsx_dev_runtime(), 1);
|
|
@@ -69516,7 +69908,7 @@ async function runTokenRename(args) {
|
|
|
69516
69908
|
}
|
|
69517
69909
|
}
|
|
69518
69910
|
if (name === target.name.trim()) {
|
|
69519
|
-
console.log(`${sym.ok} ${
|
|
69911
|
+
console.log(`${sym.ok} ${import_picocolors49.default.bold(target.name.trim())} already has that label; nothing to do.`);
|
|
69520
69912
|
return;
|
|
69521
69913
|
}
|
|
69522
69914
|
try {
|
|
@@ -69524,7 +69916,7 @@ async function runTokenRename(args) {
|
|
|
69524
69916
|
} catch (error) {
|
|
69525
69917
|
throw withLoginHint(error);
|
|
69526
69918
|
}
|
|
69527
|
-
console.log(`${sym.ok} Renamed ${
|
|
69919
|
+
console.log(`${sym.ok} Renamed ${import_picocolors49.default.dim(target.name)} → ${import_picocolors49.default.bold(name)}`);
|
|
69528
69920
|
}
|
|
69529
69921
|
async function runTokenRevoke(args) {
|
|
69530
69922
|
if (!args.id) {
|
|
@@ -69542,14 +69934,14 @@ async function runTokenRevoke(args) {
|
|
|
69542
69934
|
throw new Error(`No token with id ${args.id}. Run \`brainbase token list\` to see yours.`);
|
|
69543
69935
|
}
|
|
69544
69936
|
if (target.revoked_at) {
|
|
69545
|
-
reconcileDeadToken(target, `${
|
|
69937
|
+
reconcileDeadToken(target, `${import_picocolors49.default.bold(target.name)} is already revoked.`);
|
|
69546
69938
|
return;
|
|
69547
69939
|
}
|
|
69548
69940
|
const stored = readToken();
|
|
69549
69941
|
const isLocalToken = Boolean(stored && stored.token.startsWith(target.prefix));
|
|
69550
69942
|
if (!autoProceed(args.yes)) {
|
|
69551
69943
|
const ok = await se({
|
|
69552
|
-
message: isLocalToken ? `Revoke ${
|
|
69944
|
+
message: isLocalToken ? `Revoke ${import_picocolors49.default.bold(target.name)} (${args.id})? This is the token this CLI is using, so it will stop working here too.` : `Revoke ${import_picocolors49.default.bold(target.name)} (${args.id})? CIs and machines using it will stop working.`,
|
|
69553
69945
|
initialValue: false
|
|
69554
69946
|
});
|
|
69555
69947
|
if (!ensureNotCancelled(ok))
|
|
@@ -69560,14 +69952,14 @@ async function runTokenRevoke(args) {
|
|
|
69560
69952
|
} catch (error) {
|
|
69561
69953
|
if (error instanceof ApiError && error.status === 404) {
|
|
69562
69954
|
if (isExpired2(target)) {
|
|
69563
|
-
reconcileDeadToken(target, `${
|
|
69955
|
+
reconcileDeadToken(target, `${import_picocolors49.default.bold(target.name)} had already expired.`);
|
|
69564
69956
|
return;
|
|
69565
69957
|
}
|
|
69566
69958
|
throw new Error(`The server reported no active token with id ${args.id}, but it listed one a moment ago. ` + "The local token has been left alone, since that key may still work. " + "If this server predates `DELETE /v1/registry/cli-tokens/{id}`, revoke from the web app instead.");
|
|
69567
69959
|
}
|
|
69568
69960
|
throw withLoginHint(error);
|
|
69569
69961
|
}
|
|
69570
|
-
reconcileDeadToken(target, `Revoked ${
|
|
69962
|
+
reconcileDeadToken(target, `Revoked ${import_picocolors49.default.bold(target.name)}.`);
|
|
69571
69963
|
}
|
|
69572
69964
|
function reconcileDeadToken(target, headline) {
|
|
69573
69965
|
let outcome;
|
|
@@ -69601,7 +69993,7 @@ function reportLocalToken(headline, outcome) {
|
|
|
69601
69993
|
}
|
|
69602
69994
|
async function runTokenClear() {
|
|
69603
69995
|
if (!readToken()) {
|
|
69604
|
-
console.log(
|
|
69996
|
+
console.log(import_picocolors49.default.dim("No local token stored."));
|
|
69605
69997
|
return;
|
|
69606
69998
|
}
|
|
69607
69999
|
clearToken();
|
|
@@ -69701,31 +70093,31 @@ async function runToken(sub, rest2, args) {
|
|
|
69701
70093
|
function printTokenHelp() {
|
|
69702
70094
|
const out = [];
|
|
69703
70095
|
out.push("");
|
|
69704
|
-
out.push(` ${
|
|
70096
|
+
out.push(` ${import_picocolors49.default.bold("brainbase token")} ${import_picocolors49.default.dim("<command>")}`);
|
|
69705
70097
|
out.push("");
|
|
69706
|
-
out.push(` ${
|
|
69707
|
-
out.push(` ${
|
|
69708
|
-
out.push(` ${
|
|
69709
|
-
out.push(` ${
|
|
69710
|
-
out.push(` ${
|
|
70098
|
+
out.push(` ${import_picocolors49.default.cyan("create")} ${import_picocolors49.default.dim("issue a new long-lived CLI key (PAT)")}`);
|
|
70099
|
+
out.push(` ${import_picocolors49.default.cyan("list")} ${import_picocolors49.default.dim("show your tokens")}`);
|
|
70100
|
+
out.push(` ${import_picocolors49.default.cyan("rename")} ${import_picocolors49.default.dim("<id>")} ${import_picocolors49.default.dim("relabel a token by id")}`);
|
|
70101
|
+
out.push(` ${import_picocolors49.default.cyan("revoke")} ${import_picocolors49.default.dim("<id>")} ${import_picocolors49.default.dim("revoke a token by id")}`);
|
|
70102
|
+
out.push(` ${import_picocolors49.default.cyan("clear")} ${import_picocolors49.default.dim("forget the local token (does not revoke)")}`);
|
|
69711
70103
|
out.push("");
|
|
69712
|
-
out.push(` ${
|
|
69713
|
-
out.push(` ${
|
|
69714
|
-
out.push(` ${
|
|
69715
|
-
out.push(` ${
|
|
70104
|
+
out.push(` ${import_picocolors49.default.bold("create flags")}`);
|
|
70105
|
+
out.push(` ${import_picocolors49.default.cyan("--name, -n")} ${import_picocolors49.default.dim("<label>")} ${import_picocolors49.default.dim("token label (prompted if omitted)")}`);
|
|
70106
|
+
out.push(` ${import_picocolors49.default.cyan("--scopes")} ${import_picocolors49.default.dim("<list>")} ${import_picocolors49.default.dim("comma-separated; allowed: read, publish, admin")}`);
|
|
70107
|
+
out.push(` ${import_picocolors49.default.dim("default: read,publish")}`);
|
|
69716
70108
|
out.push("");
|
|
69717
|
-
out.push(` ${
|
|
69718
|
-
out.push(` ${
|
|
70109
|
+
out.push(` ${import_picocolors49.default.bold("rename flags")}`);
|
|
70110
|
+
out.push(` ${import_picocolors49.default.cyan("--name, -n")} ${import_picocolors49.default.dim("<label>")} ${import_picocolors49.default.dim("new label (prompted if omitted)")}`);
|
|
69719
70111
|
out.push("");
|
|
69720
70112
|
console.log(out.join(`
|
|
69721
70113
|
`));
|
|
69722
70114
|
}
|
|
69723
70115
|
|
|
69724
70116
|
// src/cli/mcp.ts
|
|
69725
|
-
var
|
|
70117
|
+
var import_picocolors50 = __toESM(require_picocolors(), 1);
|
|
69726
70118
|
|
|
69727
70119
|
// src/core/mcp-check/collect-servers.ts
|
|
69728
|
-
import
|
|
70120
|
+
import path88 from "node:path";
|
|
69729
70121
|
import fs80 from "node:fs";
|
|
69730
70122
|
function collectServers(cwd2, env3 = process.env) {
|
|
69731
70123
|
const out = [];
|
|
@@ -69777,7 +70169,7 @@ function pushResolved(out, seen, name, entry, env3) {
|
|
|
69777
70169
|
out.push({ name, url: finalUrl, headers });
|
|
69778
70170
|
}
|
|
69779
70171
|
function* readResolvedMcps(cwd2) {
|
|
69780
|
-
const p2 =
|
|
70172
|
+
const p2 = path88.join(cwd2, ".brainbase", "resolved-mcps.json");
|
|
69781
70173
|
let raw;
|
|
69782
70174
|
try {
|
|
69783
70175
|
raw = fs80.readFileSync(p2, "utf-8");
|
|
@@ -69804,12 +70196,12 @@ function* readResolvedMcps(cwd2) {
|
|
|
69804
70196
|
}
|
|
69805
70197
|
}
|
|
69806
70198
|
function readClaudeCode(cwd2) {
|
|
69807
|
-
const file =
|
|
70199
|
+
const file = path88.join(cwd2, ".mcp.json");
|
|
69808
70200
|
const map2 = listMcpServersFromMcpJson(file);
|
|
69809
70201
|
return Object.entries(map2);
|
|
69810
70202
|
}
|
|
69811
70203
|
function readCodex(cwd2) {
|
|
69812
|
-
const file =
|
|
70204
|
+
const file = path88.join(cwd2, ".codex", "config.toml");
|
|
69813
70205
|
try {
|
|
69814
70206
|
return Object.entries(listMcpServers2(file));
|
|
69815
70207
|
} catch {
|
|
@@ -69817,7 +70209,7 @@ function readCodex(cwd2) {
|
|
|
69817
70209
|
}
|
|
69818
70210
|
}
|
|
69819
70211
|
function readKafka(cwd2) {
|
|
69820
|
-
const file =
|
|
70212
|
+
const file = path88.join(cwd2, ".kafka", "kafka.json");
|
|
69821
70213
|
try {
|
|
69822
70214
|
return Object.entries(listMcpServers3(file));
|
|
69823
70215
|
} catch {
|
|
@@ -70105,10 +70497,10 @@ function assignProp(target, prop, value) {
|
|
|
70105
70497
|
configurable: true
|
|
70106
70498
|
});
|
|
70107
70499
|
}
|
|
70108
|
-
function getElementAtPath(obj,
|
|
70109
|
-
if (!
|
|
70500
|
+
function getElementAtPath(obj, path89) {
|
|
70501
|
+
if (!path89)
|
|
70110
70502
|
return obj;
|
|
70111
|
-
return
|
|
70503
|
+
return path89.reduce((acc, key2) => acc?.[key2], obj);
|
|
70112
70504
|
}
|
|
70113
70505
|
function promiseAllObject(promisesObj) {
|
|
70114
70506
|
const keys2 = Object.keys(promisesObj);
|
|
@@ -70424,11 +70816,11 @@ function aborted(x3, startIndex = 0) {
|
|
|
70424
70816
|
}
|
|
70425
70817
|
return false;
|
|
70426
70818
|
}
|
|
70427
|
-
function prefixIssues(
|
|
70819
|
+
function prefixIssues(path89, issues) {
|
|
70428
70820
|
return issues.map((iss) => {
|
|
70429
70821
|
var _a;
|
|
70430
70822
|
(_a = iss).path ?? (_a.path = []);
|
|
70431
|
-
iss.path.unshift(
|
|
70823
|
+
iss.path.unshift(path89);
|
|
70432
70824
|
return iss;
|
|
70433
70825
|
});
|
|
70434
70826
|
}
|
|
@@ -76194,8 +76586,8 @@ async function random2(size2) {
|
|
|
76194
76586
|
const evenDistCutoff = Math.pow(2, 8) - Math.pow(2, 8) % mask.length;
|
|
76195
76587
|
let result2 = "";
|
|
76196
76588
|
while (result2.length < size2) {
|
|
76197
|
-
const
|
|
76198
|
-
for (const randomByte of
|
|
76589
|
+
const randomBytes2 = await getRandomValues(size2 - result2.length);
|
|
76590
|
+
for (const randomByte of randomBytes2) {
|
|
76199
76591
|
if (randomByte < evenDistCutoff) {
|
|
76200
76592
|
result2 += mask[randomByte % mask.length];
|
|
76201
76593
|
}
|
|
@@ -78079,17 +78471,17 @@ async function runMcpCheck(cwd2, options) {
|
|
|
78079
78471
|
function renderHuman(report2) {
|
|
78080
78472
|
const lines = [];
|
|
78081
78473
|
if (report2.check_status === "skipped") {
|
|
78082
|
-
lines.push(
|
|
78474
|
+
lines.push(import_picocolors50.default.dim("No MCP servers configured — nothing to check."));
|
|
78083
78475
|
return lines.join(`
|
|
78084
78476
|
`) + `
|
|
78085
78477
|
`;
|
|
78086
78478
|
}
|
|
78087
78479
|
for (const s3 of report2.servers) {
|
|
78088
|
-
const mark = s3.status === "ok" ?
|
|
78089
|
-
const detail = s3.status === "ok" ?
|
|
78480
|
+
const mark = s3.status === "ok" ? import_picocolors50.default.green("✓") : s3.status === "auth_failed" ? import_picocolors50.default.red("✗") : import_picocolors50.default.yellow("⚠");
|
|
78481
|
+
const detail = s3.status === "ok" ? import_picocolors50.default.dim(`${s3.tool_count} tool${s3.tool_count === 1 ? "" : "s"}`) : import_picocolors50.default.dim(s3.status + (s3.error ? ` — ${s3.error}` : ""));
|
|
78090
78482
|
lines.push(` ${mark} ${s3.name} ${detail}`);
|
|
78091
78483
|
}
|
|
78092
|
-
const summary = report2.check_status === "ok" ?
|
|
78484
|
+
const summary = report2.check_status === "ok" ? import_picocolors50.default.green("All MCP servers connected.") : import_picocolors50.default.yellow("Some MCP servers are unhealthy.");
|
|
78093
78485
|
lines.push("", summary);
|
|
78094
78486
|
return lines.join(`
|
|
78095
78487
|
`) + `
|
|
@@ -78185,12 +78577,12 @@ function isUnhealthy(server) {
|
|
|
78185
78577
|
}
|
|
78186
78578
|
function renderServerList(servers) {
|
|
78187
78579
|
if (servers.length === 0) {
|
|
78188
|
-
return
|
|
78580
|
+
return import_picocolors50.default.dim("No MCP servers configured for this agent.") + `
|
|
78189
78581
|
`;
|
|
78190
78582
|
}
|
|
78191
78583
|
const lines = [""];
|
|
78192
78584
|
for (const s3 of servers) {
|
|
78193
|
-
const mark = s3.auth === "oauth_expired" ?
|
|
78585
|
+
const mark = s3.auth === "oauth_expired" ? import_picocolors50.default.red("✗") : s3.auth === "oauth_required" || isUnhealthy(s3) ? import_picocolors50.default.yellow("!") : !s3.is_enabled ? import_picocolors50.default.dim("·") : import_picocolors50.default.green("✓");
|
|
78194
78586
|
const bits = [s3.transport];
|
|
78195
78587
|
if (!s3.is_enabled)
|
|
78196
78588
|
bits.push("disabled");
|
|
@@ -78203,10 +78595,10 @@ function renderServerList(servers) {
|
|
|
78203
78595
|
const expiry = describeExpiry(s3);
|
|
78204
78596
|
if (expiry)
|
|
78205
78597
|
bits.push(expiry);
|
|
78206
|
-
lines.push(` ${mark} ${
|
|
78598
|
+
lines.push(` ${mark} ${import_picocolors50.default.bold(s3.name)} ${import_picocolors50.default.dim(bits.join(" · "))}`);
|
|
78207
78599
|
}
|
|
78208
78600
|
if (servers.some((s3) => s3.auth === "oauth_required" || s3.auth === "oauth_expired")) {
|
|
78209
|
-
lines.push("",
|
|
78601
|
+
lines.push("", import_picocolors50.default.dim("Authorize OAuth-backed servers in the web app; the CLI cannot run that flow yet."));
|
|
78210
78602
|
}
|
|
78211
78603
|
lines.push("");
|
|
78212
78604
|
return lines.join(`
|
|
@@ -78249,7 +78641,7 @@ async function runMcp(cwd2, sub, _argv, options) {
|
|
|
78249
78641
|
}
|
|
78250
78642
|
|
|
78251
78643
|
// src/cli/task.ts
|
|
78252
|
-
var
|
|
78644
|
+
var import_picocolors51 = __toESM(require_picocolors(), 1);
|
|
78253
78645
|
|
|
78254
78646
|
// src/cli/task-create.ts
|
|
78255
78647
|
import { randomUUID as randomUUID2 } from "node:crypto";
|
|
@@ -78435,25 +78827,25 @@ async function runTask(cwd2, sub, args) {
|
|
|
78435
78827
|
function printHelp4() {
|
|
78436
78828
|
const out = [];
|
|
78437
78829
|
out.push("");
|
|
78438
|
-
out.push(` ${
|
|
78830
|
+
out.push(` ${import_picocolors51.default.bold("brainbase task")} ${import_picocolors51.default.dim("<sub> [options]")}`);
|
|
78439
78831
|
out.push("");
|
|
78440
|
-
out.push(` ${
|
|
78832
|
+
out.push(` ${import_picocolors51.default.cyan("create")} ${import_picocolors51.default.dim("--message <text>")} ${import_picocolors51.default.dim("create a task and start its first run")}`);
|
|
78441
78833
|
out.push("");
|
|
78442
|
-
out.push(` ${
|
|
78443
|
-
out.push(` ${
|
|
78444
|
-
out.push(` ${
|
|
78445
|
-
out.push(` ${
|
|
78446
|
-
out.push(` ${
|
|
78447
|
-
out.push(` ${
|
|
78834
|
+
out.push(` ${import_picocolors51.default.bold("create flags")}`);
|
|
78835
|
+
out.push(` ${import_picocolors51.default.dim("--message <text>")} required first user message`);
|
|
78836
|
+
out.push(` ${import_picocolors51.default.dim("--agent <id>")} override the claimed agent in brainbase.agent.yaml`);
|
|
78837
|
+
out.push(` ${import_picocolors51.default.dim("--title <text>")} optional task title`);
|
|
78838
|
+
out.push(` ${import_picocolors51.default.dim("--model <id>")} optional model override`);
|
|
78839
|
+
out.push(` ${import_picocolors51.default.dim("--json")} print task_id, agent_id, and status as JSON`);
|
|
78448
78840
|
out.push("");
|
|
78449
|
-
out.push(` ${
|
|
78841
|
+
out.push(` ${import_picocolors51.default.dim("Flag-like values:")} use ${import_picocolors51.default.cyan("--flag=value")} or ${import_picocolors51.default.cyan("--flag -- <value>")}`);
|
|
78450
78842
|
out.push("");
|
|
78451
78843
|
console.log(out.join(`
|
|
78452
78844
|
`));
|
|
78453
78845
|
}
|
|
78454
78846
|
|
|
78455
78847
|
// src/cli/benchmark.ts
|
|
78456
|
-
var
|
|
78848
|
+
var import_picocolors52 = __toESM(require_picocolors(), 1);
|
|
78457
78849
|
import {
|
|
78458
78850
|
execFileSync as execFileSync3,
|
|
78459
78851
|
spawn as spawn5
|
|
@@ -78461,7 +78853,7 @@ import {
|
|
|
78461
78853
|
import crypto7 from "node:crypto";
|
|
78462
78854
|
import fs82 from "node:fs";
|
|
78463
78855
|
import os17 from "node:os";
|
|
78464
|
-
import
|
|
78856
|
+
import path90 from "node:path";
|
|
78465
78857
|
|
|
78466
78858
|
// src/core/benchmark-phase.ts
|
|
78467
78859
|
import {
|
|
@@ -78471,7 +78863,7 @@ import {
|
|
|
78471
78863
|
import crypto6 from "node:crypto";
|
|
78472
78864
|
import fs81 from "node:fs";
|
|
78473
78865
|
import os16 from "node:os";
|
|
78474
|
-
import
|
|
78866
|
+
import path89 from "node:path";
|
|
78475
78867
|
import { Readable, Transform as Transform2 } from "node:stream";
|
|
78476
78868
|
import { pipeline as pipeline2 } from "node:stream/promises";
|
|
78477
78869
|
import { createGunzip, createInflateRaw } from "node:zlib";
|
|
@@ -78485,6 +78877,8 @@ var MAX_TRAJECTORY_BYTES = 100 * 1024 * 1024;
|
|
|
78485
78877
|
var MAX_REMOTE_INPUT_BYTES = 2 * 1024 * 1024 * 1024;
|
|
78486
78878
|
var MAX_ARCHIVE_EXTRACTED_BYTES = 2 * 1024 * 1024 * 1024;
|
|
78487
78879
|
var MAX_ARCHIVE_SCAN_BYTES = 2 * 1024 * 1024 * 1024;
|
|
78880
|
+
var MAX_HYDRATE_COMMANDS = 150;
|
|
78881
|
+
var MAX_PHASE_RESULT_BYTES = 32 * 1024 * 1024;
|
|
78488
78882
|
var MAX_SANDBOX_COMMANDS = 20;
|
|
78489
78883
|
var MAX_CRITERIA_PER_EVALUATOR = 200;
|
|
78490
78884
|
var MAX_CRITERIA_RESULT_BYTES = 24 * 1024 * 1024;
|
|
@@ -78496,6 +78890,7 @@ var MAX_ALLOWED_EVIDENCE_IDS = 1e4;
|
|
|
78496
78890
|
var COMMAND_PROCESS_MARKER_ENV = "BRAINBASE_BENCHMARK_COMMAND_MARKER";
|
|
78497
78891
|
var COMMAND_PROCESS_POLL_MS = 10;
|
|
78498
78892
|
var COMMAND_PROCESS_CLEANUP_MS = 500;
|
|
78893
|
+
var JUDGE_ERROR_PREFIX = "BRAINBASE_BENCHMARK_JUDGE_ERROR_V1:";
|
|
78499
78894
|
var RESERVED_WORKSPACE_PATHS = new Set([
|
|
78500
78895
|
".brainbase",
|
|
78501
78896
|
".git",
|
|
@@ -78512,7 +78907,7 @@ var BASE_ENV_NAMES = [
|
|
|
78512
78907
|
"USER"
|
|
78513
78908
|
];
|
|
78514
78909
|
var SENSITIVE_ENV_NAME_RE = /(?:^|_)(?:TOKEN|SECRET|PASSWORD|PASSWD|API_KEY|PRIVATE_KEY|ACCESS_KEY|PAT|CREDENTIAL)(?:$|_)|^(?:PGPASSWORD|DATABASE_URL|REDIS_URL|MONGODB_URI)$/i;
|
|
78515
|
-
var AbsolutePathSchema = exports_external.string().min(1).refine(
|
|
78910
|
+
var AbsolutePathSchema = exports_external.string().min(1).refine(path89.isAbsolute, {
|
|
78516
78911
|
message: "must be an absolute path"
|
|
78517
78912
|
});
|
|
78518
78913
|
var Sha256Schema = exports_external.string().regex(SHA256_RE).transform((value) => value.toLowerCase());
|
|
@@ -78662,7 +79057,7 @@ var TrajectoryEvidenceSchema = EvidenceFileSchema.extend({
|
|
|
78662
79057
|
var HydrateSpecSchema = BaseSpecSchema.extend({
|
|
78663
79058
|
phase: exports_external.literal("hydrate"),
|
|
78664
79059
|
materials: exports_external.array(MaterialSchema).max(1e4).default([]),
|
|
78665
|
-
setup_commands: exports_external.array(CommandSchema).max(
|
|
79060
|
+
setup_commands: exports_external.array(CommandSchema).max(MAX_HYDRATE_COMMANDS).default([])
|
|
78666
79061
|
}).strict();
|
|
78667
79062
|
var CandidateOutputSchema = exports_external.object({
|
|
78668
79063
|
id: IdSchema,
|
|
@@ -78803,12 +79198,12 @@ var BenchmarkSpecSchema = exports_external.discriminatedUnion("phase", [
|
|
|
78803
79198
|
{ items: value.candidate_outputs, path: "candidate_outputs" }
|
|
78804
79199
|
];
|
|
78805
79200
|
for (const { items, path: issuePath } of uniqueLists) {
|
|
78806
|
-
const ids = items.map((item) => item.id);
|
|
79201
|
+
const ids = items.map((item) => issuePath === "candidate_outputs" ? item.id.toLowerCase() : item.id);
|
|
78807
79202
|
if (new Set(ids).size !== ids.length) {
|
|
78808
79203
|
context.addIssue({
|
|
78809
79204
|
code: exports_external.ZodIssueCode.custom,
|
|
78810
79205
|
path: [issuePath],
|
|
78811
|
-
message: `${issuePath} ids must be unique`
|
|
79206
|
+
message: `${issuePath} ids must be unique${issuePath === "candidate_outputs" ? " ignoring case" : ""}`
|
|
78812
79207
|
});
|
|
78813
79208
|
}
|
|
78814
79209
|
}
|
|
@@ -78871,6 +79266,7 @@ var BENCHMARK_CAPABILITIES = {
|
|
|
78871
79266
|
"remote_input_references_v1",
|
|
78872
79267
|
"archive_file_materials_v1",
|
|
78873
79268
|
"structured_criterion_results_v1",
|
|
79269
|
+
"structured_judge_errors_v1",
|
|
78874
79270
|
"multiple_sandbox_commands_v1",
|
|
78875
79271
|
"sandbox_command_workspace_modes_v1",
|
|
78876
79272
|
"candidate_outputs_v1",
|
|
@@ -78884,6 +79280,8 @@ var BENCHMARK_CAPABILITIES = {
|
|
|
78884
79280
|
],
|
|
78885
79281
|
limits: {
|
|
78886
79282
|
max_secret_bindings: 100,
|
|
79283
|
+
max_hydrate_commands: MAX_HYDRATE_COMMANDS,
|
|
79284
|
+
max_phase_result_bytes: MAX_PHASE_RESULT_BYTES,
|
|
78887
79285
|
max_evaluators: 1000,
|
|
78888
79286
|
max_sandbox_commands: MAX_SANDBOX_COMMANDS,
|
|
78889
79287
|
max_criteria_per_evaluator: MAX_CRITERIA_PER_EVALUATOR
|
|
@@ -78927,35 +79325,35 @@ function normalizedRootRelative(input) {
|
|
|
78927
79325
|
return safeRelPath(input);
|
|
78928
79326
|
}
|
|
78929
79327
|
function isWithin(root, candidate) {
|
|
78930
|
-
const relative =
|
|
78931
|
-
return relative === "" || !relative.startsWith("..") && !
|
|
79328
|
+
const relative = path89.relative(path89.resolve(root), path89.resolve(candidate));
|
|
79329
|
+
return relative === "" || !relative.startsWith("..") && !path89.isAbsolute(relative);
|
|
78932
79330
|
}
|
|
78933
79331
|
function canonicalFuturePath(input) {
|
|
78934
|
-
const resolved =
|
|
79332
|
+
const resolved = path89.resolve(input);
|
|
78935
79333
|
const suffix = [];
|
|
78936
79334
|
let current = resolved;
|
|
78937
79335
|
while (!fs81.existsSync(current)) {
|
|
78938
|
-
const parent =
|
|
79336
|
+
const parent = path89.dirname(current);
|
|
78939
79337
|
if (parent === current)
|
|
78940
79338
|
break;
|
|
78941
|
-
suffix.unshift(
|
|
79339
|
+
suffix.unshift(path89.basename(current));
|
|
78942
79340
|
current = parent;
|
|
78943
79341
|
}
|
|
78944
79342
|
const canonicalBase = fs81.realpathSync(current);
|
|
78945
|
-
return
|
|
79343
|
+
return path89.join(canonicalBase, ...suffix);
|
|
78946
79344
|
}
|
|
78947
79345
|
function validateRoots(spec) {
|
|
78948
|
-
const workspace =
|
|
79346
|
+
const workspace = path89.resolve(spec.workspace_root);
|
|
78949
79347
|
if (!fs81.existsSync(workspace) || fs81.lstatSync(workspace).isSymbolicLink() || !fs81.lstatSync(workspace).isDirectory()) {
|
|
78950
79348
|
throw new BenchmarkPhaseError("invalid_workspace_root", "workspace_root must be an existing real directory");
|
|
78951
79349
|
}
|
|
78952
79350
|
const canonicalWorkspace = canonicalFuturePath(workspace);
|
|
78953
|
-
const staging =
|
|
78954
|
-
const expectedStaging =
|
|
79351
|
+
const staging = path89.resolve(spec.staging_root);
|
|
79352
|
+
const expectedStaging = path89.join(workspace, ".brainbase", "benchmark", spec.attempt_id, "incoming");
|
|
78955
79353
|
if (staging !== expectedStaging) {
|
|
78956
79354
|
throw new BenchmarkPhaseError("invalid_staging_root", `staging_root must be ${expectedStaging}`);
|
|
78957
79355
|
}
|
|
78958
|
-
if (!fs81.existsSync(staging) || fs81.lstatSync(staging).isSymbolicLink() || !fs81.lstatSync(staging).isDirectory() || fs81.realpathSync(staging) !==
|
|
79356
|
+
if (!fs81.existsSync(staging) || fs81.lstatSync(staging).isSymbolicLink() || !fs81.lstatSync(staging).isDirectory() || fs81.realpathSync(staging) !== path89.join(canonicalWorkspace, ".brainbase", "benchmark", spec.attempt_id, "incoming")) {
|
|
78959
79357
|
throw new BenchmarkPhaseError("invalid_staging_root", "staging_root must be a real directory under workspace_root");
|
|
78960
79358
|
}
|
|
78961
79359
|
const canonicalLogs = validateExternalRoot("logs_root", spec.logs_root, canonicalWorkspace);
|
|
@@ -78967,8 +79365,8 @@ function validateRoots(spec) {
|
|
|
78967
79365
|
}
|
|
78968
79366
|
}
|
|
78969
79367
|
function validateExternalRoot(label, input, canonicalWorkspace) {
|
|
78970
|
-
const candidate =
|
|
78971
|
-
if (candidate ===
|
|
79368
|
+
const candidate = path89.resolve(input);
|
|
79369
|
+
if (candidate === path89.parse(candidate).root) {
|
|
78972
79370
|
throw new BenchmarkPhaseError(`invalid_${label}`, `${label} cannot be a filesystem root`);
|
|
78973
79371
|
}
|
|
78974
79372
|
if (fs81.existsSync(candidate) && fs81.lstatSync(candidate).isSymbolicLink()) {
|
|
@@ -78998,9 +79396,9 @@ function assertNoSymlinkTraversal(root, relative) {
|
|
|
78998
79396
|
const rel = normalizedRootRelative(relative);
|
|
78999
79397
|
if (rel === ".")
|
|
79000
79398
|
return;
|
|
79001
|
-
let current =
|
|
79399
|
+
let current = path89.resolve(root);
|
|
79002
79400
|
for (const segment of rel.split("/").slice(0, -1)) {
|
|
79003
|
-
current =
|
|
79401
|
+
current = path89.join(current, segment);
|
|
79004
79402
|
if (!fs81.existsSync(current))
|
|
79005
79403
|
continue;
|
|
79006
79404
|
if (fs81.lstatSync(current).isSymbolicLink()) {
|
|
@@ -79069,10 +79467,10 @@ function assertWritableDestination(root, relative) {
|
|
|
79069
79467
|
const rel = normalizedRootRelative(relative);
|
|
79070
79468
|
if (rel === ".")
|
|
79071
79469
|
return;
|
|
79072
|
-
let current =
|
|
79470
|
+
let current = path89.resolve(root);
|
|
79073
79471
|
const segments = rel.split("/");
|
|
79074
79472
|
for (const segment of segments.slice(0, -1)) {
|
|
79075
|
-
current =
|
|
79473
|
+
current = path89.join(current, segment);
|
|
79076
79474
|
if (!fs81.existsSync(current))
|
|
79077
79475
|
continue;
|
|
79078
79476
|
const stat = fs81.lstatSync(current);
|
|
@@ -79083,7 +79481,7 @@ function assertWritableDestination(root, relative) {
|
|
|
79083
79481
|
throw new BenchmarkPhaseError("destination_conflict", `destination parent is not a directory: ${relative}`);
|
|
79084
79482
|
}
|
|
79085
79483
|
}
|
|
79086
|
-
const destination =
|
|
79484
|
+
const destination = path89.resolve(root, rel);
|
|
79087
79485
|
if (fs81.existsSync(destination) && fs81.lstatSync(destination).isDirectory()) {
|
|
79088
79486
|
throw new BenchmarkPhaseError("destination_conflict", `file destination is an existing directory: ${relative}`);
|
|
79089
79487
|
}
|
|
@@ -79109,7 +79507,7 @@ function validateDestinationGraph(paths) {
|
|
|
79109
79507
|
}
|
|
79110
79508
|
function sourcePath(stagingRoot, relative) {
|
|
79111
79509
|
const rel = safeRelPath(relative);
|
|
79112
|
-
const source =
|
|
79510
|
+
const source = path89.resolve(stagingRoot, rel);
|
|
79113
79511
|
if (!isWithin(stagingRoot, source)) {
|
|
79114
79512
|
throw new BenchmarkPhaseError("unsafe_path", `source escapes staging root: ${relative}`);
|
|
79115
79513
|
}
|
|
@@ -79144,7 +79542,7 @@ async function verifyRecordsUnchanged(records, spec) {
|
|
|
79144
79542
|
}
|
|
79145
79543
|
const relative = safeRelPath(record3.path);
|
|
79146
79544
|
assertNoSymlinkTraversal(root, relative);
|
|
79147
|
-
const candidate =
|
|
79545
|
+
const candidate = path89.resolve(root, relative);
|
|
79148
79546
|
if (!isWithin(root, candidate)) {
|
|
79149
79547
|
throw new BenchmarkPhaseError("evidence_tampered", `evidence was removed during evaluation: ${record3.root}:${record3.path}`);
|
|
79150
79548
|
}
|
|
@@ -79214,7 +79612,7 @@ async function cachedVerifiedInput(stagingRoot, input, context) {
|
|
|
79214
79612
|
function stagedInputRecord(stagingRoot, verified) {
|
|
79215
79613
|
return {
|
|
79216
79614
|
root: "staging",
|
|
79217
|
-
path:
|
|
79615
|
+
path: path89.relative(stagingRoot, verified.source).replace(/\\/g, "/"),
|
|
79218
79616
|
sha256: verified.sha256,
|
|
79219
79617
|
size: verified.size,
|
|
79220
79618
|
mode: verified.mode,
|
|
@@ -79235,7 +79633,7 @@ function removeRemoteHydrationInputs(spec) {
|
|
|
79235
79633
|
if (!material.download_url_env || removedSources.has(material.source))
|
|
79236
79634
|
continue;
|
|
79237
79635
|
const relative = safeRelPath(material.source);
|
|
79238
|
-
const source =
|
|
79636
|
+
const source = path89.resolve(spec.staging_root, relative);
|
|
79239
79637
|
if (!isWithin(spec.staging_root, source)) {
|
|
79240
79638
|
throw new BenchmarkPhaseError("unsafe_path", `source escapes staging root: ${material.source}`);
|
|
79241
79639
|
}
|
|
@@ -79267,7 +79665,7 @@ async function downloadInputReference(stagingRoot, input, context) {
|
|
|
79267
79665
|
return await cachedVerifiedInput(stagingRoot, input, context);
|
|
79268
79666
|
}
|
|
79269
79667
|
const relative = safeRelPath(input.source);
|
|
79270
|
-
const destination =
|
|
79668
|
+
const destination = path89.resolve(stagingRoot, relative);
|
|
79271
79669
|
if (!isWithin(stagingRoot, destination)) {
|
|
79272
79670
|
throw new BenchmarkPhaseError("unsafe_path", `source escapes staging root: ${input.source}`);
|
|
79273
79671
|
}
|
|
@@ -79296,7 +79694,7 @@ async function downloadInputReference(stagingRoot, input, context) {
|
|
|
79296
79694
|
if (remainingMs <= 0) {
|
|
79297
79695
|
throw new BenchmarkPhaseError("phase_timeout", "phase budget expired");
|
|
79298
79696
|
}
|
|
79299
|
-
fs81.mkdirSync(
|
|
79697
|
+
fs81.mkdirSync(path89.dirname(destination), { recursive: true, mode: 448 });
|
|
79300
79698
|
assertNoSymlinkTraversal(stagingRoot, relative);
|
|
79301
79699
|
assertWritableDestination(stagingRoot, relative);
|
|
79302
79700
|
const temporary = `${destination}.${process.pid}.${crypto6.randomBytes(6).toString("hex")}.download`;
|
|
@@ -79515,7 +79913,7 @@ function findZipMembers(archivePath, requested, context) {
|
|
|
79515
79913
|
}
|
|
79516
79914
|
}
|
|
79517
79915
|
async function writeVerifiedArchiveMember(source, destination, material, context) {
|
|
79518
|
-
fs81.mkdirSync(
|
|
79916
|
+
fs81.mkdirSync(path89.dirname(destination), { recursive: true, mode: 448 });
|
|
79519
79917
|
const temporary = `${destination}.${process.pid}.${crypto6.randomBytes(6).toString("hex")}.tmp`;
|
|
79520
79918
|
const descriptor = fs81.openSync(temporary, "wx", 384);
|
|
79521
79919
|
const hash = crypto6.createHash("sha256");
|
|
@@ -79630,7 +80028,7 @@ async function extractArchiveMembers(archivePath, outputRoot, materials, context
|
|
|
79630
80028
|
const indexed = findZipMembers(archivePath, requested, context);
|
|
79631
80029
|
for (const [memberPath, material] of requested) {
|
|
79632
80030
|
assertBudget(context);
|
|
79633
|
-
const destination =
|
|
80031
|
+
const destination = path89.resolve(outputRoot, memberPath);
|
|
79634
80032
|
if (!isWithin(outputRoot, destination)) {
|
|
79635
80033
|
throw new BenchmarkPhaseError("unsafe_path", `archive member escapes output root: ${memberPath}`);
|
|
79636
80034
|
}
|
|
@@ -79706,7 +80104,7 @@ async function extractArchiveMembers(archivePath, outputRoot, materials, context
|
|
|
79706
80104
|
return extracted;
|
|
79707
80105
|
}
|
|
79708
80106
|
async function atomicCopy(source, destination, mode, sourceRoot) {
|
|
79709
|
-
fs81.mkdirSync(
|
|
80107
|
+
fs81.mkdirSync(path89.dirname(destination), { recursive: true });
|
|
79710
80108
|
const temporary = `${destination}.${process.pid}.${crypto6.randomBytes(6).toString("hex")}.tmp`;
|
|
79711
80109
|
const opened = openRegularFileNoFollow(source, `copy source ${source}`, sourceRoot);
|
|
79712
80110
|
try {
|
|
@@ -79726,7 +80124,7 @@ async function atomicCopy(source, destination, mode, sourceRoot) {
|
|
|
79726
80124
|
}
|
|
79727
80125
|
}
|
|
79728
80126
|
async function recordFile(root, filePath, rootName, kind = "file") {
|
|
79729
|
-
const relative =
|
|
80127
|
+
const relative = path89.relative(root, filePath).replace(/\\/g, "/");
|
|
79730
80128
|
if (kind === "symlink") {
|
|
79731
80129
|
const stat = fs81.lstatSync(filePath);
|
|
79732
80130
|
const target = fs81.readlinkSync(filePath);
|
|
@@ -79767,11 +80165,11 @@ async function copyMaterial(material, sourceRoot, destinationRoot, destinationRo
|
|
|
79767
80165
|
throw new BenchmarkPhaseError("unsafe_path", "file destination cannot be a directory root");
|
|
79768
80166
|
}
|
|
79769
80167
|
assertWritableDestination(destinationRoot, destinationRel);
|
|
79770
|
-
const destination =
|
|
80168
|
+
const destination = path89.resolve(destinationRoot, destinationRel);
|
|
79771
80169
|
if (material.kind === "file") {
|
|
79772
80170
|
await atomicCopy(source, destination, material.mode ?? verifiedSource?.mode, sourceRoot);
|
|
79773
80171
|
} else {
|
|
79774
|
-
await atomicCopy(source, destination, material.mode,
|
|
80172
|
+
await atomicCopy(source, destination, material.mode, path89.dirname(source));
|
|
79775
80173
|
}
|
|
79776
80174
|
const record3 = await recordFile(destinationRoot, destination, destinationRootName);
|
|
79777
80175
|
const expectedSha256 = material.kind === "archive_file" ? material.file_sha256 : material.sha256;
|
|
@@ -79781,15 +80179,15 @@ async function copyMaterial(material, sourceRoot, destinationRoot, destinationRo
|
|
|
79781
80179
|
}
|
|
79782
80180
|
return [record3];
|
|
79783
80181
|
}
|
|
79784
|
-
const temporary = fs81.mkdtempSync(
|
|
80182
|
+
const temporary = fs81.mkdtempSync(path89.join(os16.tmpdir(), "brainbase-benchmark-"));
|
|
79785
80183
|
try {
|
|
79786
|
-
const verifiedArchive =
|
|
80184
|
+
const verifiedArchive = path89.join(temporary, "material.tar.gz");
|
|
79787
80185
|
await atomicCopy(source, verifiedArchive, 384, sourceRoot);
|
|
79788
80186
|
const archiveRecord = await recordFile(temporary, verifiedArchive, "staging");
|
|
79789
80187
|
if (archiveRecord.sha256 !== material.sha256 || archiveRecord.size !== material.size_bytes) {
|
|
79790
80188
|
throw new BenchmarkPhaseError("evidence_tampered", `material changed while it was copied: ${material.source}`);
|
|
79791
80189
|
}
|
|
79792
|
-
const extractedRoot =
|
|
80190
|
+
const extractedRoot = path89.join(temporary, "extracted");
|
|
79793
80191
|
const extracted = await extract({
|
|
79794
80192
|
tarFile: verifiedArchive,
|
|
79795
80193
|
outDir: extractedRoot,
|
|
@@ -79798,17 +80196,17 @@ async function copyMaterial(material, sourceRoot, destinationRoot, destinationRo
|
|
|
79798
80196
|
});
|
|
79799
80197
|
const outputs = [];
|
|
79800
80198
|
for (const extractedRel of extracted.sort()) {
|
|
79801
|
-
const sourceFile =
|
|
80199
|
+
const sourceFile = path89.resolve(extractedRoot, safeRelPath(extractedRel));
|
|
79802
80200
|
const stat = fs81.lstatSync(sourceFile);
|
|
79803
80201
|
if (!stat.isFile())
|
|
79804
80202
|
continue;
|
|
79805
|
-
const combined = destinationRel === "." ? safeRelPath(extractedRel) : safeRelPath(
|
|
80203
|
+
const combined = destinationRel === "." ? safeRelPath(extractedRel) : safeRelPath(path89.posix.join(destinationRel, extractedRel));
|
|
79806
80204
|
const checked = protectWorkspace ? workspaceRel(combined) : combined;
|
|
79807
80205
|
if (!protectWorkspace && checked.toLowerCase() === ".brainbase-benchmark-owner.json") {
|
|
79808
80206
|
throw new BenchmarkPhaseError("reserved_path", "benchmark input cannot replace the phase ownership marker");
|
|
79809
80207
|
}
|
|
79810
80208
|
assertWritableDestination(destinationRoot, checked);
|
|
79811
|
-
const destination =
|
|
80209
|
+
const destination = path89.resolve(destinationRoot, checked);
|
|
79812
80210
|
await atomicCopy(sourceFile, destination, material.mode, extractedRoot);
|
|
79813
80211
|
outputs.push(await recordFile(destinationRoot, destination, destinationRootName));
|
|
79814
80212
|
}
|
|
@@ -79832,7 +80230,7 @@ async function preflightMaterial(material, materials, sourceRoot, destinationRoo
|
|
|
79832
80230
|
const cacheKey = archiveMemberCacheKey(material);
|
|
79833
80231
|
let extracted = context.preparedArchiveFiles.get(cacheKey);
|
|
79834
80232
|
if (!extracted) {
|
|
79835
|
-
const temporary2 = fs81.mkdtempSync(
|
|
80233
|
+
const temporary2 = fs81.mkdtempSync(path89.join(os16.tmpdir(), "brainbase-benchmark-member-"));
|
|
79836
80234
|
context.temporaryRoots.add(temporary2);
|
|
79837
80235
|
const archiveKey = archiveSourceCacheKey(material);
|
|
79838
80236
|
const related = materials.filter((candidate) => candidate.kind === "archive_file" && archiveSourceCacheKey(candidate) === archiveKey);
|
|
@@ -79852,15 +80250,15 @@ async function preflightMaterial(material, materials, sourceRoot, destinationRoo
|
|
|
79852
80250
|
}
|
|
79853
80251
|
return [destinationRel];
|
|
79854
80252
|
}
|
|
79855
|
-
const temporary = fs81.mkdtempSync(
|
|
80253
|
+
const temporary = fs81.mkdtempSync(path89.join(os16.tmpdir(), "brainbase-benchmark-preflight-"));
|
|
79856
80254
|
try {
|
|
79857
|
-
const verifiedArchive =
|
|
80255
|
+
const verifiedArchive = path89.join(temporary, "material.tar.gz");
|
|
79858
80256
|
await atomicCopy(source, verifiedArchive, 384, sourceRoot);
|
|
79859
80257
|
const archiveRecord = await recordFile(temporary, verifiedArchive, "staging");
|
|
79860
80258
|
if (archiveRecord.sha256 !== material.sha256 || archiveRecord.size !== material.size_bytes) {
|
|
79861
80259
|
throw new BenchmarkPhaseError("evidence_tampered", `material changed while it was copied: ${material.source}`);
|
|
79862
80260
|
}
|
|
79863
|
-
const extractedRoot =
|
|
80261
|
+
const extractedRoot = path89.join(temporary, "extracted");
|
|
79864
80262
|
const extracted = await extract({
|
|
79865
80263
|
tarFile: verifiedArchive,
|
|
79866
80264
|
outDir: extractedRoot,
|
|
@@ -79869,7 +80267,7 @@ async function preflightMaterial(material, materials, sourceRoot, destinationRoo
|
|
|
79869
80267
|
});
|
|
79870
80268
|
const planned = [];
|
|
79871
80269
|
for (const extractedRel of extracted) {
|
|
79872
|
-
const combined = destinationRel === "." ? safeRelPath(extractedRel) : safeRelPath(
|
|
80270
|
+
const combined = destinationRel === "." ? safeRelPath(extractedRel) : safeRelPath(path89.posix.join(destinationRel, extractedRel));
|
|
79873
80271
|
const checked = protectWorkspace ? workspaceRel(combined) : combined;
|
|
79874
80272
|
if (!protectWorkspace && checked.toLowerCase() === ".brainbase-benchmark-owner.json") {
|
|
79875
80273
|
throw new BenchmarkPhaseError("reserved_path", "benchmark input cannot replace the phase ownership marker");
|
|
@@ -79883,7 +80281,7 @@ async function preflightMaterial(material, materials, sourceRoot, destinationRoo
|
|
|
79883
80281
|
}
|
|
79884
80282
|
}
|
|
79885
80283
|
function ownerMarker(root) {
|
|
79886
|
-
return
|
|
80284
|
+
return path89.join(root, ".brainbase-benchmark-owner.json");
|
|
79887
80285
|
}
|
|
79888
80286
|
function verifyOwnedDirectory(root, role, spec) {
|
|
79889
80287
|
if (!fs81.existsSync(root) || fs81.lstatSync(root).isSymbolicLink())
|
|
@@ -80021,7 +80419,7 @@ function markedProcessPids(marker) {
|
|
|
80021
80419
|
if (pid === process.pid)
|
|
80022
80420
|
continue;
|
|
80023
80421
|
try {
|
|
80024
|
-
const environment = fs81.readFileSync(
|
|
80422
|
+
const environment = fs81.readFileSync(path89.join("/proc", entry, "environ"), "utf8");
|
|
80025
80423
|
if (environment.split("\x00").includes(assignment))
|
|
80026
80424
|
matches2.push(pid);
|
|
80027
80425
|
} catch {}
|
|
@@ -80055,7 +80453,7 @@ function markedProcessPids(marker) {
|
|
|
80055
80453
|
function processExists(pid) {
|
|
80056
80454
|
if (process.platform === "linux") {
|
|
80057
80455
|
try {
|
|
80058
|
-
const stat = fs81.readFileSync(
|
|
80456
|
+
const stat = fs81.readFileSync(path89.join("/proc", String(pid), "stat"), "utf8");
|
|
80059
80457
|
const commandEnd = stat.lastIndexOf(")");
|
|
80060
80458
|
const state = commandEnd >= 0 ? stat.slice(commandEnd + 2, commandEnd + 3) : "";
|
|
80061
80459
|
if (state === "Z" || state === "X")
|
|
@@ -80099,7 +80497,7 @@ async function terminateCommandProcesses(child, marker, observedDescendants) {
|
|
|
80099
80497
|
async function runCommand(command, root, spec, context, options = {}) {
|
|
80100
80498
|
const cwdRel = normalizedRootRelative(command.cwd);
|
|
80101
80499
|
assertNoSymlinkTraversal(root, cwdRel);
|
|
80102
|
-
const cwd2 =
|
|
80500
|
+
const cwd2 = path89.resolve(root, cwdRel);
|
|
80103
80501
|
let cwdStat;
|
|
80104
80502
|
try {
|
|
80105
80503
|
cwdStat = fs81.lstatSync(cwd2);
|
|
@@ -80222,8 +80620,8 @@ async function runCommand(command, root, spec, context, options = {}) {
|
|
|
80222
80620
|
});
|
|
80223
80621
|
}
|
|
80224
80622
|
async function writeLog(root, name, data, spec) {
|
|
80225
|
-
const destination =
|
|
80226
|
-
fs81.mkdirSync(
|
|
80623
|
+
const destination = path89.join(root, name);
|
|
80624
|
+
fs81.mkdirSync(path89.dirname(destination), { recursive: true });
|
|
80227
80625
|
const temporary = `${destination}.${process.pid}.${crypto6.randomBytes(6).toString("hex")}.tmp`;
|
|
80228
80626
|
try {
|
|
80229
80627
|
fs81.writeFileSync(temporary, redactCommandOutput(data, spec), {
|
|
@@ -80237,7 +80635,7 @@ async function writeLog(root, name, data, spec) {
|
|
|
80237
80635
|
return await recordFile(root, destination, "logs");
|
|
80238
80636
|
}
|
|
80239
80637
|
function writeBufferAtomic(destination, data) {
|
|
80240
|
-
fs81.mkdirSync(
|
|
80638
|
+
fs81.mkdirSync(path89.dirname(destination), { recursive: true });
|
|
80241
80639
|
const temporary = `${destination}.${process.pid}.${crypto6.randomBytes(6).toString("hex")}.tmp`;
|
|
80242
80640
|
try {
|
|
80243
80641
|
fs81.writeFileSync(temporary, data, { flag: "wx", mode: 384 });
|
|
@@ -80337,7 +80735,7 @@ async function executeHydrate(spec, context) {
|
|
|
80337
80735
|
finalOutputs.push(output);
|
|
80338
80736
|
continue;
|
|
80339
80737
|
}
|
|
80340
|
-
const candidate =
|
|
80738
|
+
const candidate = path89.resolve(spec.workspace_root, safeRelPath(output.path));
|
|
80341
80739
|
assertNoSymlinkTraversal(spec.workspace_root, output.path);
|
|
80342
80740
|
if (!fs81.existsSync(candidate))
|
|
80343
80741
|
continue;
|
|
@@ -80368,7 +80766,7 @@ async function readEvidence(stagingRoot, evidence) {
|
|
|
80368
80766
|
buffer,
|
|
80369
80767
|
record: {
|
|
80370
80768
|
root: "staging",
|
|
80371
|
-
path:
|
|
80769
|
+
path: path89.relative(stagingRoot, filePath).replace(/\\/g, "/"),
|
|
80372
80770
|
sha256: evidence.sha256,
|
|
80373
80771
|
size: opened.stat.size,
|
|
80374
80772
|
mode: opened.stat.mode & 511
|
|
@@ -80381,14 +80779,14 @@ async function readEvidence(stagingRoot, evidence) {
|
|
|
80381
80779
|
async function workspaceManifest(spec, context) {
|
|
80382
80780
|
const records = [];
|
|
80383
80781
|
let totalBytes = 0;
|
|
80384
|
-
const stack = [
|
|
80782
|
+
const stack = [path89.resolve(spec.workspace_root)];
|
|
80385
80783
|
while (stack.length > 0) {
|
|
80386
80784
|
const directory = stack.pop();
|
|
80387
80785
|
const entries = fs81.readdirSync(directory, { withFileTypes: true }).sort((a3, b4) => a3.name.localeCompare(b4.name));
|
|
80388
80786
|
for (const entry of entries) {
|
|
80389
80787
|
assertBudget(context);
|
|
80390
|
-
const full =
|
|
80391
|
-
const relative =
|
|
80788
|
+
const full = path89.join(directory, entry.name);
|
|
80789
|
+
const relative = path89.relative(spec.workspace_root, full).replace(/\\/g, "/");
|
|
80392
80790
|
if (relative === ".brainbase" || relative.startsWith(".brainbase/"))
|
|
80393
80791
|
continue;
|
|
80394
80792
|
if (relative === ".git" || relative.startsWith(".git/"))
|
|
@@ -80421,13 +80819,13 @@ async function verifyWorkspaceManifestUnchanged(expected, spec, context) {
|
|
|
80421
80819
|
}
|
|
80422
80820
|
function treeBytes(root, context) {
|
|
80423
80821
|
let totalBytes = 0;
|
|
80424
|
-
const stack = [
|
|
80822
|
+
const stack = [path89.resolve(root)];
|
|
80425
80823
|
while (stack.length > 0) {
|
|
80426
80824
|
const directory = stack.pop();
|
|
80427
80825
|
const entries = fs81.readdirSync(directory, { withFileTypes: true });
|
|
80428
80826
|
for (const entry of entries) {
|
|
80429
80827
|
assertBudget(context);
|
|
80430
|
-
const candidate =
|
|
80828
|
+
const candidate = path89.join(directory, entry.name);
|
|
80431
80829
|
const stat = fs81.lstatSync(candidate);
|
|
80432
80830
|
if (stat.isDirectory()) {
|
|
80433
80831
|
stack.push(candidate);
|
|
@@ -80441,7 +80839,7 @@ function treeBytes(root, context) {
|
|
|
80441
80839
|
totalBytes += Buffer.byteLength(fs81.readlinkSync(candidate));
|
|
80442
80840
|
continue;
|
|
80443
80841
|
}
|
|
80444
|
-
throw new BenchmarkPhaseError("unsafe_path", `evaluate output contains an unsupported filesystem entry: ${
|
|
80842
|
+
throw new BenchmarkPhaseError("unsafe_path", `evaluate output contains an unsupported filesystem entry: ${path89.relative(root, candidate)}`);
|
|
80445
80843
|
}
|
|
80446
80844
|
}
|
|
80447
80845
|
return totalBytes;
|
|
@@ -80487,11 +80885,11 @@ function manifestDirectories(manifest, context) {
|
|
|
80487
80885
|
assertBudget(context);
|
|
80488
80886
|
if (entry.kind === "symlink")
|
|
80489
80887
|
continue;
|
|
80490
|
-
let current =
|
|
80888
|
+
let current = path89.posix.dirname(entry.path);
|
|
80491
80889
|
while (current !== ".") {
|
|
80492
80890
|
assertBudget(context);
|
|
80493
80891
|
directories.add(current);
|
|
80494
|
-
current =
|
|
80892
|
+
current = path89.posix.dirname(current);
|
|
80495
80893
|
}
|
|
80496
80894
|
}
|
|
80497
80895
|
return [...directories].sort();
|
|
@@ -80560,8 +80958,8 @@ async function copyCandidateOutput(output, manifest, spec, context) {
|
|
|
80560
80958
|
const copied = [];
|
|
80561
80959
|
for (const frozenFile of selected.files) {
|
|
80562
80960
|
assertBudget(context);
|
|
80563
|
-
const source =
|
|
80564
|
-
const destination =
|
|
80961
|
+
const source = path89.resolve(spec.workspace_root, safeRelPath(frozenFile.path));
|
|
80962
|
+
const destination = path89.resolve(spec.logs_root, "candidate-outputs", output.id, safeRelPath(frozenFile.path));
|
|
80565
80963
|
if (fs81.existsSync(destination)) {
|
|
80566
80964
|
throw new BenchmarkPhaseError("destination_conflict", `candidate output destination already exists: ${output.id}/${frozenFile.path}`);
|
|
80567
80965
|
}
|
|
@@ -80575,24 +80973,24 @@ async function copyCandidateOutput(output, manifest, spec, context) {
|
|
|
80575
80973
|
return copied;
|
|
80576
80974
|
}
|
|
80577
80975
|
async function copyFrozenWorkspace(manifest, spec, context, sourceRoot = spec.workspace_root, symlinkPolicy = "preserve") {
|
|
80578
|
-
const destinationRoot = fs81.mkdtempSync(
|
|
80976
|
+
const destinationRoot = fs81.mkdtempSync(path89.join(os16.tmpdir(), "brainbase-benchmark-workspace-"));
|
|
80579
80977
|
fs81.chmodSync(destinationRoot, 448);
|
|
80580
80978
|
context.temporaryRoots.add(destinationRoot);
|
|
80581
80979
|
for (const frozenFile of manifest) {
|
|
80582
80980
|
assertBudget(context);
|
|
80583
|
-
const source =
|
|
80584
|
-
const destination =
|
|
80981
|
+
const source = path89.resolve(sourceRoot, safeRelPath(frozenFile.path));
|
|
80982
|
+
const destination = path89.resolve(destinationRoot, safeRelPath(frozenFile.path));
|
|
80585
80983
|
if (frozenFile.kind === "symlink") {
|
|
80586
80984
|
const stat = fs81.lstatSync(source);
|
|
80587
80985
|
const target = stat.isSymbolicLink() ? fs81.readlinkSync(source) : null;
|
|
80588
80986
|
if (target === null || Buffer.byteLength(target) !== frozenFile.size || sha256(target) !== frozenFile.sha256) {
|
|
80589
80987
|
throw new BenchmarkPhaseError("evidence_tampered", `workspace changed after it was frozen: ${frozenFile.path}`);
|
|
80590
80988
|
}
|
|
80591
|
-
const resolvedTarget =
|
|
80592
|
-
if (symlinkPolicy === "contained_relative_only" && (
|
|
80989
|
+
const resolvedTarget = path89.resolve(path89.dirname(source), target);
|
|
80990
|
+
if (symlinkPolicy === "contained_relative_only" && (path89.isAbsolute(target) || !isWithin(sourceRoot, resolvedTarget))) {
|
|
80593
80991
|
continue;
|
|
80594
80992
|
}
|
|
80595
|
-
fs81.mkdirSync(
|
|
80993
|
+
fs81.mkdirSync(path89.dirname(destination), { recursive: true, mode: 448 });
|
|
80596
80994
|
fs81.symlinkSync(target, destination);
|
|
80597
80995
|
continue;
|
|
80598
80996
|
}
|
|
@@ -80605,12 +81003,12 @@ async function copyFrozenWorkspace(manifest, spec, context, sourceRoot = spec.wo
|
|
|
80605
81003
|
return destinationRoot;
|
|
80606
81004
|
}
|
|
80607
81005
|
async function copyEvaluatorTests(spec, evaluator, context) {
|
|
80608
|
-
const destinationRoot = fs81.mkdtempSync(
|
|
81006
|
+
const destinationRoot = fs81.mkdtempSync(path89.join(os16.tmpdir(), "brainbase-benchmark-tests-"));
|
|
80609
81007
|
fs81.chmodSync(destinationRoot, 448);
|
|
80610
81008
|
context.temporaryRoots.add(destinationRoot);
|
|
80611
81009
|
const sourceRoot = evaluatorTestsPath(evaluator, spec.tests_root);
|
|
80612
81010
|
const relativeRoot = evaluator.tests_path ? normalizedRootRelative(evaluator.tests_path) : ".";
|
|
80613
|
-
const destinationStart = relativeRoot === "." ? destinationRoot :
|
|
81011
|
+
const destinationStart = relativeRoot === "." ? destinationRoot : path89.resolve(destinationRoot, relativeRoot);
|
|
80614
81012
|
fs81.mkdirSync(destinationStart, { recursive: true, mode: 448 });
|
|
80615
81013
|
const stack = [{ source: sourceRoot, destination: destinationStart }];
|
|
80616
81014
|
while (stack.length > 0) {
|
|
@@ -80619,11 +81017,11 @@ async function copyEvaluatorTests(spec, evaluator, context) {
|
|
|
80619
81017
|
const entries = fs81.readdirSync(current.source, { withFileTypes: true }).sort((left, right) => left.name.localeCompare(right.name));
|
|
80620
81018
|
for (const entry of entries) {
|
|
80621
81019
|
assertBudget(context);
|
|
80622
|
-
const source =
|
|
80623
|
-
const destination =
|
|
81020
|
+
const source = path89.join(current.source, entry.name);
|
|
81021
|
+
const destination = path89.join(current.destination, entry.name);
|
|
80624
81022
|
const stat = fs81.lstatSync(source);
|
|
80625
81023
|
if (stat.isSymbolicLink()) {
|
|
80626
|
-
throw new BenchmarkPhaseError("unsafe_path", `evaluator reference tree contains a symlink: ${
|
|
81024
|
+
throw new BenchmarkPhaseError("unsafe_path", `evaluator reference tree contains a symlink: ${path89.relative(spec.tests_root, source)}`);
|
|
80627
81025
|
}
|
|
80628
81026
|
if (stat.isDirectory()) {
|
|
80629
81027
|
fs81.mkdirSync(destination, { recursive: true, mode: stat.mode & 511 });
|
|
@@ -80631,7 +81029,7 @@ async function copyEvaluatorTests(spec, evaluator, context) {
|
|
|
80631
81029
|
continue;
|
|
80632
81030
|
}
|
|
80633
81031
|
if (!stat.isFile()) {
|
|
80634
|
-
throw new BenchmarkPhaseError("unsafe_path", `evaluator reference tree contains an unsupported filesystem entry: ${
|
|
81032
|
+
throw new BenchmarkPhaseError("unsafe_path", `evaluator reference tree contains an unsupported filesystem entry: ${path89.relative(spec.tests_root, source)}`);
|
|
80635
81033
|
}
|
|
80636
81034
|
await atomicCopy(source, destination, stat.mode & 511, spec.tests_root);
|
|
80637
81035
|
const sourceRecord = await recordFile(spec.tests_root, source, "tests");
|
|
@@ -80648,7 +81046,7 @@ function evaluatorTestsPath(evaluator, testsRoot) {
|
|
|
80648
81046
|
return testsRoot;
|
|
80649
81047
|
const relative = normalizedRootRelative(evaluator.tests_path);
|
|
80650
81048
|
assertNoSymlinkTraversal(testsRoot, relative);
|
|
80651
|
-
const candidate =
|
|
81049
|
+
const candidate = path89.resolve(testsRoot, relative);
|
|
80652
81050
|
if (!isWithin(testsRoot, candidate) || !fs81.existsSync(candidate)) {
|
|
80653
81051
|
throw new BenchmarkPhaseError("invalid_tests_path", `evaluator tests_path does not exist: ${evaluator.tests_path}`);
|
|
80654
81052
|
}
|
|
@@ -80683,10 +81081,33 @@ var CriteriaResultFileSchema = exports_external.object({
|
|
|
80683
81081
|
});
|
|
80684
81082
|
}
|
|
80685
81083
|
});
|
|
81084
|
+
var JudgeErrorSchema = exports_external.object({
|
|
81085
|
+
code: exports_external.enum([
|
|
81086
|
+
"judge_provider_quota_exhausted",
|
|
81087
|
+
"judge_rate_limited",
|
|
81088
|
+
"judge_provider_authentication_failed",
|
|
81089
|
+
"judge_provider_unavailable",
|
|
81090
|
+
"judge_request_failed"
|
|
81091
|
+
]),
|
|
81092
|
+
message: exports_external.string().min(1).max(500)
|
|
81093
|
+
}).strict();
|
|
81094
|
+
function structuredJudgeError(stderr) {
|
|
81095
|
+
for (const line of stderr.toString("utf8").split(/\r?\n/).reverse()) {
|
|
81096
|
+
const marker = line.indexOf(JUDGE_ERROR_PREFIX);
|
|
81097
|
+
if (marker < 0)
|
|
81098
|
+
continue;
|
|
81099
|
+
try {
|
|
81100
|
+
const parsed = JudgeErrorSchema.safeParse(JSON.parse(line.slice(marker + JUDGE_ERROR_PREFIX.length)));
|
|
81101
|
+
if (parsed.success)
|
|
81102
|
+
return parsed.data;
|
|
81103
|
+
} catch {}
|
|
81104
|
+
}
|
|
81105
|
+
return null;
|
|
81106
|
+
}
|
|
80686
81107
|
function readCriterionResults(resultPath, criterionKeys, allowedEvidenceIds, spec, additionalSecrets = []) {
|
|
80687
81108
|
let opened;
|
|
80688
81109
|
try {
|
|
80689
|
-
opened = openRegularFileNoFollow(resultPath, "criterion result",
|
|
81110
|
+
opened = openRegularFileNoFollow(resultPath, "criterion result", path89.dirname(resultPath));
|
|
80690
81111
|
} catch (error2) {
|
|
80691
81112
|
if (error2.code === "ENOENT") {
|
|
80692
81113
|
throw new BenchmarkPhaseError("missing_criterion_result", "sandbox evaluator did not write its criterion result");
|
|
@@ -80833,7 +81254,7 @@ async function evaluateOne(evaluator, spec, manifest, frozenWorkspaceRoot, final
|
|
|
80833
81254
|
if (evaluator.type === "workspace_assertion") {
|
|
80834
81255
|
const relative = workspaceRel(evaluator.path);
|
|
80835
81256
|
assertNoSymlinkTraversal(frozenWorkspaceRoot, relative);
|
|
80836
|
-
const candidate =
|
|
81257
|
+
const candidate = path89.resolve(frozenWorkspaceRoot, relative);
|
|
80837
81258
|
let stat = null;
|
|
80838
81259
|
try {
|
|
80839
81260
|
stat = fs81.lstatSync(candidate);
|
|
@@ -80913,10 +81334,10 @@ async function evaluateOne(evaluator, spec, manifest, frozenWorkspaceRoot, final
|
|
|
80913
81334
|
};
|
|
80914
81335
|
let criterionResultPath;
|
|
80915
81336
|
if (evaluator.criterion_keys) {
|
|
80916
|
-
privateResultRoot = fs81.mkdtempSync(
|
|
81337
|
+
privateResultRoot = fs81.mkdtempSync(path89.join(os16.tmpdir(), "brainbase-benchmark-criteria-"));
|
|
80917
81338
|
fs81.chmodSync(privateResultRoot, 448);
|
|
80918
81339
|
context.temporaryRoots.add(privateResultRoot);
|
|
80919
|
-
criterionResultPath =
|
|
81340
|
+
criterionResultPath = path89.join(privateResultRoot, "result.json");
|
|
80920
81341
|
environment.BRAINBASE_BENCHMARK_CRITERIA_RESULT = criterionResultPath;
|
|
80921
81342
|
}
|
|
80922
81343
|
const result2 = await runCommand(command, commandRoot, spec, context, {
|
|
@@ -80929,7 +81350,13 @@ async function evaluateOne(evaluator, spec, manifest, frozenWorkspaceRoot, final
|
|
|
80929
81350
|
try {
|
|
80930
81351
|
criterionResults = evaluator.criterion_keys && criterionResultPath ? readCriterionResults(criterionResultPath, evaluator.criterion_keys, evaluator.allowed_evidence_ids ?? [], spec, result2.redactions) : undefined;
|
|
80931
81352
|
} catch (error2) {
|
|
80932
|
-
|
|
81353
|
+
let normalized = stableError(error2);
|
|
81354
|
+
if (normalized?.code === "missing_criterion_result" && result2.exitCode !== 0) {
|
|
81355
|
+
normalized = structuredJudgeError(result2.stderr) ?? {
|
|
81356
|
+
code: "command_terminated",
|
|
81357
|
+
message: "sandbox evaluator terminated before writing its criterion result"
|
|
81358
|
+
};
|
|
81359
|
+
}
|
|
80933
81360
|
return {
|
|
80934
81361
|
...base2,
|
|
80935
81362
|
status: "errored",
|
|
@@ -81001,8 +81428,8 @@ async function executeEvaluate(spec, context) {
|
|
|
81001
81428
|
context.logsOwned = true;
|
|
81002
81429
|
validateRoots(spec);
|
|
81003
81430
|
const outputs = [];
|
|
81004
|
-
const finalOutputPath =
|
|
81005
|
-
const trajectoryPath =
|
|
81431
|
+
const finalOutputPath = path89.join(spec.logs_root, "candidate-evidence", "final-output");
|
|
81432
|
+
const trajectoryPath = path89.join(spec.logs_root, "candidate-evidence", "trajectory.json");
|
|
81006
81433
|
writeBufferAtomic(finalOutputPath, finalOutput.buffer);
|
|
81007
81434
|
writeBufferAtomic(trajectoryPath, trajectoryEvidence.buffer);
|
|
81008
81435
|
const frozenEvidenceRecords = [
|
|
@@ -81014,7 +81441,7 @@ async function executeEvaluate(spec, context) {
|
|
|
81014
81441
|
assertEvaluateOutputBudget(spec, context);
|
|
81015
81442
|
assertBudget(context);
|
|
81016
81443
|
const manifest = await workspaceManifest(spec, context);
|
|
81017
|
-
const manifestPath2 =
|
|
81444
|
+
const manifestPath2 = path89.join(spec.logs_root, "candidate-workspace-manifest.json");
|
|
81018
81445
|
writeJsonAtomic(manifestPath2, {
|
|
81019
81446
|
schema_version: SCHEMA_VERSION,
|
|
81020
81447
|
attempt_id: spec.attempt_id,
|
|
@@ -81028,12 +81455,12 @@ async function executeEvaluate(spec, context) {
|
|
|
81028
81455
|
for (const artifactRelInput of spec.candidate_artifacts) {
|
|
81029
81456
|
const artifactRel = workspaceRel(artifactRelInput);
|
|
81030
81457
|
assertNoSymlinkTraversal(spec.workspace_root, artifactRel);
|
|
81031
|
-
const source =
|
|
81458
|
+
const source = path89.resolve(spec.workspace_root, artifactRel);
|
|
81032
81459
|
const frozenArtifact = manifest.find((entry) => entry.path === artifactRel && entry.kind !== "symlink");
|
|
81033
81460
|
if (!frozenArtifact || !fs81.existsSync(source) || !fs81.lstatSync(source).isFile()) {
|
|
81034
81461
|
throw new BenchmarkPhaseError("missing_artifact", `candidate artifact is missing: ${artifactRel}`);
|
|
81035
81462
|
}
|
|
81036
|
-
const destination =
|
|
81463
|
+
const destination = path89.resolve(spec.logs_root, "candidate-artifacts", artifactRel);
|
|
81037
81464
|
await atomicCopy(source, destination, undefined, spec.workspace_root);
|
|
81038
81465
|
const artifact = await recordFile(spec.logs_root, destination, "logs");
|
|
81039
81466
|
if (artifact.sha256 !== frozenArtifact.sha256 || artifact.size !== frozenArtifact.size || artifact.mode !== frozenArtifact.mode) {
|
|
@@ -81051,7 +81478,7 @@ async function executeEvaluate(spec, context) {
|
|
|
81051
81478
|
assertEvaluateOutputBudget(spec, context);
|
|
81052
81479
|
if (spec.capture_workspace_archive) {
|
|
81053
81480
|
const regularFiles = manifest.filter((entry) => entry.kind !== "symlink").map((entry) => entry.path);
|
|
81054
|
-
const archive =
|
|
81481
|
+
const archive = path89.join(spec.logs_root, "candidate-workspace.tar.gz");
|
|
81055
81482
|
const temporary = `${archive}.${process.pid}.${crypto6.randomBytes(6).toString("hex")}.tmp`;
|
|
81056
81483
|
try {
|
|
81057
81484
|
await pack({ rootDir: spec.workspace_root, outFile: temporary, files: regularFiles });
|
|
@@ -81165,6 +81592,67 @@ function stableError(error2) {
|
|
|
81165
81592
|
message: error2 instanceof Error ? error2.message : "unknown benchmark phase failure"
|
|
81166
81593
|
};
|
|
81167
81594
|
}
|
|
81595
|
+
function compactOversizedResult(result2) {
|
|
81596
|
+
const actualBytes = Buffer.byteLength(`${JSON.stringify(result2, null, 2)}
|
|
81597
|
+
`);
|
|
81598
|
+
if (actualBytes <= MAX_PHASE_RESULT_BYTES)
|
|
81599
|
+
return result2;
|
|
81600
|
+
return {
|
|
81601
|
+
schema_version: result2.schema_version,
|
|
81602
|
+
cli_version: result2.cli_version,
|
|
81603
|
+
phase: result2.phase,
|
|
81604
|
+
attempt_id: result2.attempt_id,
|
|
81605
|
+
phase_id: result2.phase_id,
|
|
81606
|
+
spec_digest: result2.spec_digest,
|
|
81607
|
+
status: "failed",
|
|
81608
|
+
started_at: result2.started_at,
|
|
81609
|
+
completed_at: result2.completed_at,
|
|
81610
|
+
duration_ms: result2.duration_ms,
|
|
81611
|
+
steps: [],
|
|
81612
|
+
inputs: [],
|
|
81613
|
+
outputs: [],
|
|
81614
|
+
error: {
|
|
81615
|
+
code: "result_too_large",
|
|
81616
|
+
message: "benchmark phase result exceeds the 32 MiB contract limit",
|
|
81617
|
+
details: {
|
|
81618
|
+
actual_bytes: actualBytes,
|
|
81619
|
+
max_bytes: MAX_PHASE_RESULT_BYTES,
|
|
81620
|
+
step_count: result2.steps.length,
|
|
81621
|
+
input_count: result2.inputs.length,
|
|
81622
|
+
output_count: result2.outputs.length,
|
|
81623
|
+
evaluator_count: result2.evaluators?.length ?? 0
|
|
81624
|
+
}
|
|
81625
|
+
}
|
|
81626
|
+
};
|
|
81627
|
+
}
|
|
81628
|
+
function readCachedPhaseResult(resultPath) {
|
|
81629
|
+
let opened;
|
|
81630
|
+
try {
|
|
81631
|
+
opened = openRegularFileNoFollow(resultPath, "cached benchmark phase result");
|
|
81632
|
+
} catch {
|
|
81633
|
+
return;
|
|
81634
|
+
}
|
|
81635
|
+
try {
|
|
81636
|
+
if (opened.stat.size > MAX_PHASE_RESULT_BYTES)
|
|
81637
|
+
return;
|
|
81638
|
+
const chunks = [];
|
|
81639
|
+
let offset = 0;
|
|
81640
|
+
while (offset <= MAX_PHASE_RESULT_BYTES) {
|
|
81641
|
+
const buffer = Buffer.alloc(Math.min(64 * 1024, MAX_PHASE_RESULT_BYTES + 1 - offset));
|
|
81642
|
+
const bytesRead = fs81.readSync(opened.fd, buffer, 0, buffer.length, offset);
|
|
81643
|
+
if (bytesRead === 0) {
|
|
81644
|
+
return JSON.parse(Buffer.concat(chunks, offset).toString("utf8"));
|
|
81645
|
+
}
|
|
81646
|
+
chunks.push(buffer.subarray(0, bytesRead));
|
|
81647
|
+
offset += bytesRead;
|
|
81648
|
+
}
|
|
81649
|
+
return;
|
|
81650
|
+
} catch {
|
|
81651
|
+
return;
|
|
81652
|
+
} finally {
|
|
81653
|
+
fs81.closeSync(opened.fd);
|
|
81654
|
+
}
|
|
81655
|
+
}
|
|
81168
81656
|
function rawIdentity(value) {
|
|
81169
81657
|
if (!value || typeof value !== "object") {
|
|
81170
81658
|
return { phase: "unknown", attemptId: null, phaseId: null };
|
|
@@ -81177,7 +81665,7 @@ function rawIdentity(value) {
|
|
|
81177
81665
|
};
|
|
81178
81666
|
}
|
|
81179
81667
|
function readSpecBytes(specPathInput) {
|
|
81180
|
-
const specPath =
|
|
81668
|
+
const specPath = path89.resolve(specPathInput);
|
|
81181
81669
|
const noFollow = typeof fs81.constants.O_NOFOLLOW === "number" ? fs81.constants.O_NOFOLLOW : 0;
|
|
81182
81670
|
let fd;
|
|
81183
81671
|
try {
|
|
@@ -81208,8 +81696,8 @@ function validateBenchmarkInvocationBytes(bytes, resultPathInput, expectedPhase)
|
|
|
81208
81696
|
throw new BenchmarkPhaseError("phase_mismatch", `the ${expectedPhase} command cannot execute a ${spec.phase} spec`);
|
|
81209
81697
|
}
|
|
81210
81698
|
validateRoots(spec);
|
|
81211
|
-
const resultPath =
|
|
81212
|
-
const expectedResultPath =
|
|
81699
|
+
const resultPath = path89.resolve(resultPathInput);
|
|
81700
|
+
const expectedResultPath = path89.join(path89.resolve(spec.logs_root), "result.json");
|
|
81213
81701
|
if (resultPath !== expectedResultPath) {
|
|
81214
81702
|
throw new BenchmarkPhaseError("invalid_result_path", `result path must be ${expectedResultPath}`);
|
|
81215
81703
|
}
|
|
@@ -81237,13 +81725,9 @@ function prepareBenchmarkPhaseInvocation(specPathInput, resultPathInput, expecte
|
|
|
81237
81725
|
timeout_ms: spec.budget.timeout_ms
|
|
81238
81726
|
};
|
|
81239
81727
|
let cachedResult;
|
|
81240
|
-
|
|
81241
|
-
|
|
81242
|
-
|
|
81243
|
-
if (cached2.schema_version === SCHEMA_VERSION && cached2.phase === spec.phase && cached2.attempt_id === spec.attempt_id && cached2.phase_id === spec.phase_id && cached2.spec_digest === digest && cached2.status === "succeeded") {
|
|
81244
|
-
cachedResult = cached2;
|
|
81245
|
-
}
|
|
81246
|
-
} catch {}
|
|
81728
|
+
const cached2 = readCachedPhaseResult(resultPath);
|
|
81729
|
+
if (cached2?.schema_version === SCHEMA_VERSION && cached2.phase === spec.phase && cached2.attempt_id === spec.attempt_id && cached2.phase_id === spec.phase_id && cached2.spec_digest === digest && cached2.status === "succeeded") {
|
|
81730
|
+
cachedResult = cached2;
|
|
81247
81731
|
}
|
|
81248
81732
|
if (cachedResult) {
|
|
81249
81733
|
if (spec.phase === "hydrate") {
|
|
@@ -81260,7 +81744,7 @@ function prepareBenchmarkPhaseInvocation(specPathInput, resultPathInput, expecte
|
|
|
81260
81744
|
} catch (error2) {
|
|
81261
81745
|
return {
|
|
81262
81746
|
ok: false,
|
|
81263
|
-
result: {
|
|
81747
|
+
result: compactOversizedResult({
|
|
81264
81748
|
schema_version: SCHEMA_VERSION,
|
|
81265
81749
|
cli_version: VERSION,
|
|
81266
81750
|
phase: identity2.phase === "unknown" ? expectedPhase : identity2.phase,
|
|
@@ -81275,7 +81759,7 @@ function prepareBenchmarkPhaseInvocation(specPathInput, resultPathInput, expecte
|
|
|
81275
81759
|
inputs: [],
|
|
81276
81760
|
outputs: [],
|
|
81277
81761
|
error: stableError(error2)
|
|
81278
|
-
}
|
|
81762
|
+
})
|
|
81279
81763
|
};
|
|
81280
81764
|
}
|
|
81281
81765
|
}
|
|
@@ -81313,7 +81797,7 @@ function writeBenchmarkPhaseTimeoutResult(specBytes, resultPathInput, expectedPh
|
|
|
81313
81797
|
async function runBenchmarkPhase(specPathInput, resultPathInput, expectedPhase, immutableSpecBytes) {
|
|
81314
81798
|
const startedAt = nowIso();
|
|
81315
81799
|
const started = Date.now();
|
|
81316
|
-
const resultPath =
|
|
81800
|
+
const resultPath = path89.resolve(resultPathInput);
|
|
81317
81801
|
let raw = undefined;
|
|
81318
81802
|
let digest = null;
|
|
81319
81803
|
let identity2 = rawIdentity(raw);
|
|
@@ -81349,19 +81833,15 @@ async function runBenchmarkPhase(specPathInput, resultPathInput, expectedPhase,
|
|
|
81349
81833
|
throw new BenchmarkPhaseError("phase_mismatch", `the ${expectedPhase} command cannot execute a ${spec.phase} spec`);
|
|
81350
81834
|
}
|
|
81351
81835
|
validateRoots(spec);
|
|
81352
|
-
const expectedResultPath =
|
|
81836
|
+
const expectedResultPath = path89.join(path89.resolve(spec.logs_root), "result.json");
|
|
81353
81837
|
if (resultPath !== expectedResultPath) {
|
|
81354
81838
|
throw new BenchmarkPhaseError("invalid_result_path", `result path must be ${expectedResultPath}`);
|
|
81355
81839
|
}
|
|
81356
81840
|
resultPathValidated = true;
|
|
81357
81841
|
let cachedResult;
|
|
81358
|
-
|
|
81359
|
-
|
|
81360
|
-
|
|
81361
|
-
if (cached2.schema_version === SCHEMA_VERSION && cached2.phase === spec.phase && cached2.attempt_id === spec.attempt_id && cached2.phase_id === spec.phase_id && cached2.spec_digest === digest && cached2.status === "succeeded") {
|
|
81362
|
-
cachedResult = cached2;
|
|
81363
|
-
}
|
|
81364
|
-
} catch {}
|
|
81842
|
+
const cached2 = readCachedPhaseResult(resultPath);
|
|
81843
|
+
if (cached2?.schema_version === SCHEMA_VERSION && cached2.phase === spec.phase && cached2.attempt_id === spec.attempt_id && cached2.phase_id === spec.phase_id && cached2.spec_digest === digest && cached2.status === "succeeded") {
|
|
81844
|
+
cachedResult = cached2;
|
|
81365
81845
|
}
|
|
81366
81846
|
if (cachedResult) {
|
|
81367
81847
|
if (spec.phase === "hydrate") {
|
|
@@ -81404,7 +81884,7 @@ async function runBenchmarkPhase(specPathInput, resultPathInput, expectedPhase,
|
|
|
81404
81884
|
fs81.rmSync(temporary, { recursive: true, force: true });
|
|
81405
81885
|
}
|
|
81406
81886
|
}
|
|
81407
|
-
|
|
81887
|
+
let result2 = {
|
|
81408
81888
|
schema_version: SCHEMA_VERSION,
|
|
81409
81889
|
cli_version: VERSION,
|
|
81410
81890
|
phase: identity2.phase === "unknown" && expectedPhase ? expectedPhase : identity2.phase,
|
|
@@ -81422,6 +81902,7 @@ async function runBenchmarkPhase(specPathInput, resultPathInput, expectedPhase,
|
|
|
81422
81902
|
...error2 ? { error: error2 } : {}
|
|
81423
81903
|
};
|
|
81424
81904
|
if (!resultPathValidated || !context?.logsOwned) {
|
|
81905
|
+
result2 = compactOversizedResult(result2);
|
|
81425
81906
|
return { exitCode: status === "succeeded" ? 0 : 1, result: result2 };
|
|
81426
81907
|
}
|
|
81427
81908
|
if (status === "succeeded" && validatedSpec?.phase === "evaluate") {
|
|
@@ -81435,6 +81916,8 @@ async function runBenchmarkPhase(specPathInput, resultPathInput, expectedPhase,
|
|
|
81435
81916
|
result2.error = stableError(budgetError);
|
|
81436
81917
|
}
|
|
81437
81918
|
}
|
|
81919
|
+
result2 = compactOversizedResult(result2);
|
|
81920
|
+
status = result2.status;
|
|
81438
81921
|
try {
|
|
81439
81922
|
writeJsonAtomic(resultPath, result2);
|
|
81440
81923
|
} catch (writeError) {
|
|
@@ -81578,7 +82061,7 @@ function terminatePhase(child) {
|
|
|
81578
82061
|
}
|
|
81579
82062
|
}
|
|
81580
82063
|
function createAnonymousSpecFd(bytes) {
|
|
81581
|
-
const temporary =
|
|
82064
|
+
const temporary = path90.join(os17.tmpdir(), `brainbase-benchmark-spec-${process.pid}-${crypto7.randomBytes(12).toString("hex")}`);
|
|
81582
82065
|
fs82.writeFileSync(temporary, bytes, { flag: "wx", mode: 384 });
|
|
81583
82066
|
try {
|
|
81584
82067
|
const fd = fs82.openSync(temporary, "r");
|
|
@@ -81782,13 +82265,13 @@ async function runBenchmark(sub, args, write = (value) => process.stdout.write(v
|
|
|
81782
82265
|
function printHelp5() {
|
|
81783
82266
|
const out = [];
|
|
81784
82267
|
out.push("");
|
|
81785
|
-
out.push(` ${
|
|
82268
|
+
out.push(` ${import_picocolors52.default.bold("brainbase benchmark")} ${import_picocolors52.default.dim("<sub> [options]")}`);
|
|
81786
82269
|
out.push("");
|
|
81787
|
-
out.push(` ${
|
|
81788
|
-
out.push(` ${
|
|
81789
|
-
out.push(` ${
|
|
82270
|
+
out.push(` ${import_picocolors52.default.cyan("hydrate")} ${import_picocolors52.default.dim("--spec <path> --result <path> --json")}`);
|
|
82271
|
+
out.push(` ${import_picocolors52.default.cyan("evaluate")} ${import_picocolors52.default.dim("--spec <path> --result <path> --json")}`);
|
|
82272
|
+
out.push(` ${import_picocolors52.default.cyan("capabilities")} ${import_picocolors52.default.dim("--json")}`);
|
|
81790
82273
|
out.push("");
|
|
81791
|
-
out.push(` ${
|
|
82274
|
+
out.push(` ${import_picocolors52.default.dim("These machine-only commands execute versioned benchmark phase specs inside a task sandbox.")}`);
|
|
81792
82275
|
out.push("");
|
|
81793
82276
|
console.log(out.join(`
|
|
81794
82277
|
`));
|
|
@@ -81815,137 +82298,140 @@ var SUBCOMMAND_OWNED_FLAGS = {
|
|
|
81815
82298
|
function help() {
|
|
81816
82299
|
const out = [];
|
|
81817
82300
|
out.push("");
|
|
81818
|
-
out.push(` ${brandTint("◆")} ${
|
|
81819
|
-
out.push(` ${
|
|
82301
|
+
out.push(` ${brandTint("◆")} ${import_picocolors53.default.bold("brainbase")} ${import_picocolors53.default.dim(`v${VERSION}`)}`);
|
|
82302
|
+
out.push(` ${import_picocolors53.default.dim("connect your local agent to the brainbase platform")}`);
|
|
81820
82303
|
out.push("");
|
|
81821
82304
|
out.push(divider("USAGE"));
|
|
81822
82305
|
out.push("");
|
|
81823
|
-
out.push(` ${
|
|
82306
|
+
out.push(` ${import_picocolors53.default.bold("brainbase")} ${import_picocolors53.default.dim("<command> [options]")}`);
|
|
81824
82307
|
out.push("");
|
|
81825
82308
|
out.push(divider("AUTH"));
|
|
81826
82309
|
out.push("");
|
|
81827
|
-
out.push(` ${
|
|
81828
|
-
out.push(` ${
|
|
81829
|
-
out.push(` ${
|
|
82310
|
+
out.push(` ${import_picocolors53.default.cyan("login")} ${import_picocolors53.default.dim(" open the web app and connect this device")}`);
|
|
82311
|
+
out.push(` ${import_picocolors53.default.cyan("logout")} ${import_picocolors53.default.dim(" clear the local session")}`);
|
|
82312
|
+
out.push(` ${import_picocolors53.default.cyan("whoami")} ${import_picocolors53.default.dim("[--json]")} ${import_picocolors53.default.dim(" show which credential is in use and what it covers")}`);
|
|
81830
82313
|
out.push("");
|
|
81831
82314
|
out.push(divider("DISCOVERY"));
|
|
81832
82315
|
out.push("");
|
|
81833
|
-
out.push(` ${
|
|
81834
|
-
out.push(` ${
|
|
82316
|
+
out.push(` ${import_picocolors53.default.cyan("team list")} ${import_picocolors53.default.dim("show the teams you can create agents in")}`);
|
|
82317
|
+
out.push(` ${import_picocolors53.default.cyan("agent list")} ${import_picocolors53.default.dim("show a team's agents and their ids")}`);
|
|
81835
82318
|
out.push("");
|
|
81836
82319
|
out.push(divider("LINKED AGENT"));
|
|
81837
82320
|
out.push("");
|
|
81838
|
-
out.push(` ${
|
|
81839
|
-
out.push(` ${
|
|
81840
|
-
out.push(` ${
|
|
81841
|
-
out.push(` ${
|
|
81842
|
-
out.push(` ${
|
|
81843
|
-
out.push(` ${
|
|
81844
|
-
out.push(` ${
|
|
81845
|
-
out.push(` ${
|
|
81846
|
-
out.push(` ${
|
|
81847
|
-
out.push(` ${
|
|
81848
|
-
out.push(` ${
|
|
81849
|
-
out.push(` ${
|
|
81850
|
-
out.push(` ${
|
|
82321
|
+
out.push(` ${import_picocolors53.default.cyan("agent init")} ${import_picocolors53.default.dim("write a starter brainbase.agent.yaml here — offline, no login needed")}`);
|
|
82322
|
+
out.push(` ${import_picocolors53.default.cyan("agent create")} ${import_picocolors53.default.dim("claim an unclaimed brainbase.agent.yaml and create the cloud agent")}`);
|
|
82323
|
+
out.push(` ${import_picocolors53.default.cyan("agent pull")} ${import_picocolors53.default.dim("[<id>]")} ${import_picocolors53.default.dim("bring cloud changes into this folder (--force to override; --run-entrypoint to also execute the agent entrypoint)")}`);
|
|
82324
|
+
out.push(` ${import_picocolors53.default.cyan("agent push")} ${import_picocolors53.default.dim("send local changes to the cloud (--force to overwrite cloud-side conflicts with local)")}`);
|
|
82325
|
+
out.push(` ${import_picocolors53.default.cyan("agent unpack")} ${import_picocolors53.default.dim("install the claimed agent into a harness layout")}`);
|
|
82326
|
+
out.push(` ${import_picocolors53.default.cyan("link")} ${import_picocolors53.default.dim("attach this folder to an existing agent")}`);
|
|
82327
|
+
out.push(` ${import_picocolors53.default.cyan("agent status")} ${import_picocolors53.default.dim("show what would pull and what would push")}`);
|
|
82328
|
+
out.push(` ${import_picocolors53.default.cyan("agent connections")} ${import_picocolors53.default.dim("show which integrations this agent is wired to (--json for CI)")}`);
|
|
82329
|
+
out.push(` ${import_picocolors53.default.cyan("agent connect")} ${import_picocolors53.default.dim("<name>")} ${import_picocolors53.default.dim("connect slack or meeting from the terminal")}`);
|
|
82330
|
+
out.push(` ${import_picocolors53.default.cyan("agent disconnect")} ${import_picocolors53.default.dim("<name>")} ${import_picocolors53.default.dim("revoke a slack or meeting install")}`);
|
|
82331
|
+
out.push(` ${import_picocolors53.default.cyan("agent env")} ${import_picocolors53.default.dim("print export lines for `eval $(brainbase agent env)`")}`);
|
|
82332
|
+
out.push(` ${import_picocolors53.default.cyan("run")} ${import_picocolors53.default.dim("<cmd> [args...]")} ${import_picocolors53.default.dim("run <cmd> with secrets.env loaded into env")}`);
|
|
82333
|
+
out.push(` ${import_picocolors53.default.cyan("status")} ${import_picocolors53.default.dim("show what this folder is linked to")}`);
|
|
82334
|
+
out.push(` ${import_picocolors53.default.cyan("unlink")} ${import_picocolors53.default.dim("disconnect this folder")}`);
|
|
81851
82335
|
out.push("");
|
|
81852
82336
|
out.push(divider("TASKS"));
|
|
81853
82337
|
out.push("");
|
|
81854
|
-
out.push(` ${
|
|
82338
|
+
out.push(` ${import_picocolors53.default.cyan("task create")} ${import_picocolors53.default.dim("--message <text>")} ${import_picocolors53.default.dim("create a managed task and start its first run")}`);
|
|
81855
82339
|
out.push("");
|
|
81856
82340
|
out.push(divider("BENCHMARK RUNTIME"));
|
|
81857
82341
|
out.push("");
|
|
81858
|
-
out.push(` ${
|
|
81859
|
-
out.push(` ${
|
|
81860
|
-
out.push(` ${
|
|
82342
|
+
out.push(` ${import_picocolors53.default.cyan("benchmark hydrate")} ${import_picocolors53.default.dim("--spec <path> --result <path> --json")}`);
|
|
82343
|
+
out.push(` ${import_picocolors53.default.cyan("benchmark evaluate")} ${import_picocolors53.default.dim("--spec <path> --result <path> --json")}`);
|
|
82344
|
+
out.push(` ${import_picocolors53.default.cyan("benchmark capabilities")} ${import_picocolors53.default.dim("--json")}`);
|
|
81861
82345
|
out.push("");
|
|
81862
82346
|
out.push(divider("ORCHESTRATIONS"));
|
|
81863
82347
|
out.push("");
|
|
81864
|
-
out.push(` ${
|
|
81865
|
-
out.push(` ${
|
|
81866
|
-
out.push(` ${
|
|
81867
|
-
out.push(` ${
|
|
81868
|
-
out.push(` ${
|
|
82348
|
+
out.push(` ${import_picocolors53.default.cyan("orchestration create")} ${import_picocolors53.default.dim("claim a local orchestration manifest and create it in the cloud")}`);
|
|
82349
|
+
out.push(` ${import_picocolors53.default.cyan("orchestration list")} ${import_picocolors53.default.dim("list orchestrations under a team")}`);
|
|
82350
|
+
out.push(` ${import_picocolors53.default.cyan("orchestration pull")} ${import_picocolors53.default.dim("<id>")} ${import_picocolors53.default.dim("recursively fetch an orchestration + every member agent")}`);
|
|
82351
|
+
out.push(` ${import_picocolors53.default.cyan("orchestration push")} ${import_picocolors53.default.dim("recursively push each member, then update the graph")}`);
|
|
82352
|
+
out.push(` ${import_picocolors53.default.cyan("orchestration status")} ${import_picocolors53.default.dim("show what would push and what would pull")}`);
|
|
81869
82353
|
out.push("");
|
|
81870
82354
|
out.push(divider("TEMPLATES"));
|
|
81871
82355
|
out.push("");
|
|
81872
|
-
out.push(` ${
|
|
81873
|
-
out.push(` ${
|
|
81874
|
-
out.push(` ${
|
|
81875
|
-
out.push(` ${
|
|
81876
|
-
out.push(` ${
|
|
81877
|
-
out.push(` ${
|
|
81878
|
-
out.push(` ${
|
|
82356
|
+
out.push(` ${import_picocolors53.default.cyan("template pack")} ${import_picocolors53.default.dim("bundle the current agent into a template")}`);
|
|
82357
|
+
out.push(` ${import_picocolors53.default.cyan("template publish")} ${import_picocolors53.default.dim("upload a template to the registry")}`);
|
|
82358
|
+
out.push(` ${import_picocolors53.default.cyan("template search")} ${import_picocolors53.default.dim("[query]")} ${import_picocolors53.default.dim("search the registry")}`);
|
|
82359
|
+
out.push(` ${import_picocolors53.default.cyan("template info")} ${import_picocolors53.default.dim("<creator/slug>")} ${import_picocolors53.default.dim("show registry details for a template")}`);
|
|
82360
|
+
out.push(` ${import_picocolors53.default.cyan("template onboard")} ${import_picocolors53.default.dim("<creator/slug>")} ${import_picocolors53.default.dim("install (or refresh) a template")}`);
|
|
82361
|
+
out.push(` ${import_picocolors53.default.cyan("template list")} ${import_picocolors53.default.dim("show installed templates")}`);
|
|
82362
|
+
out.push(` ${import_picocolors53.default.cyan("template remove")} ${import_picocolors53.default.dim("<creator/slug>")} ${import_picocolors53.default.dim("uninstall a template")}`);
|
|
81879
82363
|
out.push("");
|
|
81880
82364
|
out.push(divider("SKILLS"));
|
|
81881
82365
|
out.push("");
|
|
81882
|
-
out.push(` ${
|
|
81883
|
-
out.push(` ${
|
|
81884
|
-
out.push(` ${
|
|
81885
|
-
out.push(` ${
|
|
81886
|
-
out.push(` ${
|
|
81887
|
-
out.push(` ${
|
|
81888
|
-
out.push(` ${
|
|
82366
|
+
out.push(` ${import_picocolors53.default.cyan("skill add")} ${import_picocolors53.default.dim("<source>")} ${import_picocolors53.default.dim("install a skill (github / git / brainbase)")}`);
|
|
82367
|
+
out.push(` ${import_picocolors53.default.cyan("skill list")} ${import_picocolors53.default.dim("show locally installed skills + their source")}`);
|
|
82368
|
+
out.push(` ${import_picocolors53.default.cyan("skill update")} ${import_picocolors53.default.dim("<slug>")} ${import_picocolors53.default.dim("re-fetch a skill from its recorded source")}`);
|
|
82369
|
+
out.push(` ${import_picocolors53.default.cyan("skill remove")} ${import_picocolors53.default.dim("<slug>")} ${import_picocolors53.default.dim("uninstall a skill")}`);
|
|
82370
|
+
out.push(` ${import_picocolors53.default.cyan("skill search")} ${import_picocolors53.default.dim("[query]")} ${import_picocolors53.default.dim("search the brainbase skill registry")}`);
|
|
82371
|
+
out.push(` ${import_picocolors53.default.cyan("skill info")} ${import_picocolors53.default.dim("<creator/slug>")} ${import_picocolors53.default.dim("show registry details for a skill")}`);
|
|
82372
|
+
out.push(` ${import_picocolors53.default.cyan("skill publish")} ${import_picocolors53.default.dim("[dir]")} ${import_picocolors53.default.dim("publish a SKILL.md folder (defaults to .)")}`);
|
|
81889
82373
|
out.push("");
|
|
81890
82374
|
out.push(divider("CLI TOKENS"));
|
|
81891
82375
|
out.push("");
|
|
81892
|
-
out.push(` ${
|
|
81893
|
-
out.push(` ${
|
|
81894
|
-
out.push(` ${
|
|
81895
|
-
out.push(` ${
|
|
82376
|
+
out.push(` ${import_picocolors53.default.cyan("token create")} ${import_picocolors53.default.dim("issue a long-lived CLI key for CI / scripts")}`);
|
|
82377
|
+
out.push(` ${import_picocolors53.default.cyan("token list")} ${import_picocolors53.default.dim("show your tokens")}`);
|
|
82378
|
+
out.push(` ${import_picocolors53.default.cyan("token rename")} ${import_picocolors53.default.dim("<id>")} ${import_picocolors53.default.dim("relabel a token")}`);
|
|
82379
|
+
out.push(` ${import_picocolors53.default.cyan("token revoke")} ${import_picocolors53.default.dim("<id>")} ${import_picocolors53.default.dim("revoke a token")}`);
|
|
81896
82380
|
out.push("");
|
|
81897
82381
|
out.push(divider("MCP"));
|
|
81898
82382
|
out.push("");
|
|
81899
|
-
out.push(` ${
|
|
81900
|
-
out.push(` ${
|
|
82383
|
+
out.push(` ${import_picocolors53.default.cyan("mcp check")} ${import_picocolors53.default.dim("[--json]")} ${import_picocolors53.default.dim("verify MCP server connectivity through the brainbase proxy (runs at sandbox bootstrap)")}`);
|
|
82384
|
+
out.push(` ${import_picocolors53.default.cyan("mcp list")} ${import_picocolors53.default.dim("[--json]")} ${import_picocolors53.default.dim("show configured servers with OAuth state and expiry")}`);
|
|
81901
82385
|
out.push("");
|
|
81902
82386
|
out.push(divider("FLAGS"));
|
|
81903
82387
|
out.push("");
|
|
81904
|
-
out.push(` ${
|
|
81905
|
-
out.push(` ${
|
|
81906
|
-
out.push(` ${
|
|
81907
|
-
out.push(` ${
|
|
81908
|
-
out.push(` ${
|
|
81909
|
-
out.push(` ${
|
|
81910
|
-
out.push(` ${
|
|
81911
|
-
out.push(` ${
|
|
81912
|
-
out.push(` ${
|
|
81913
|
-
out.push(` ${
|
|
81914
|
-
out.push(` ${
|
|
81915
|
-
out.push(` ${
|
|
81916
|
-
out.push(` ${
|
|
81917
|
-
out.push(` ${
|
|
81918
|
-
out.push(` ${
|
|
81919
|
-
out.push(` ${
|
|
81920
|
-
out.push(` ${
|
|
81921
|
-
out.push(` ${
|
|
82388
|
+
out.push(` ${import_picocolors53.default.dim("--harness <id>")} force harness for onboard / sync (e.g. claude-code)`);
|
|
82389
|
+
out.push(` ${import_picocolors53.default.dim("--scope <s>")} force scope: global | project`);
|
|
82390
|
+
out.push(` ${import_picocolors53.default.dim("--yes, -y")} skip confirmations / auto-overwrite`);
|
|
82391
|
+
out.push(` ${import_picocolors53.default.dim("--agent <id>")} for link/task create: use this agent id explicitly`);
|
|
82392
|
+
out.push(` ${import_picocolors53.default.dim("--message <text>")} for task create: required first user message`);
|
|
82393
|
+
out.push(` ${import_picocolors53.default.dim("--title <text>")} for task create: optional task title`);
|
|
82394
|
+
out.push(` ${import_picocolors53.default.dim("--model <id>")} for task create: optional model override`);
|
|
82395
|
+
out.push(` ${import_picocolors53.default.dim("--org <id-or-slug>")} pick the organization (team/agent list, agent create, orchestration create/list)`);
|
|
82396
|
+
out.push(` ${import_picocolors53.default.dim("--team <id>")} pick the team, same commands (works without --org)`);
|
|
82397
|
+
out.push(` ${import_picocolors53.default.dim("--json")} machine-readable output for supported commands`);
|
|
82398
|
+
out.push(` ${import_picocolors53.default.dim("--no-tracking")} for link: skip routing LLM traffic through brainbase`);
|
|
82399
|
+
out.push(` ${import_picocolors53.default.dim("--track")} for agent create: enable tracking non-interactively (off without a TTY)`);
|
|
82400
|
+
out.push(` ${import_picocolors53.default.dim("--shell <sh|fish>")} for agent env: pick output format (auto-detected from $SHELL)`);
|
|
82401
|
+
out.push(` ${import_picocolors53.default.dim("--bot-token <t>")} for agent connect slack (or BRAINBASE_SLACK_BOT_TOKEN, or stdin)`);
|
|
82402
|
+
out.push(` ${import_picocolors53.default.dim("--signing-secret <s>")} for agent connect slack (or BRAINBASE_SLACK_SIGNING_SECRET, or stdin)`);
|
|
82403
|
+
out.push(` ${import_picocolors53.default.dim("--bot-name <name>")} for agent connect meeting: the bot's display name`);
|
|
82404
|
+
out.push(` ${import_picocolors53.default.dim("--full")} for agent init: write a commented template covering every block`);
|
|
82405
|
+
out.push(` ${import_picocolors53.default.dim("--minimal")} for agent init: write the starter manifest (the default)`);
|
|
82406
|
+
out.push(` ${import_picocolors53.default.dim("--all")} for template list: include installs from other folders`);
|
|
82407
|
+
out.push(` ${import_picocolors53.default.dim("--web <url>")} for login: web app URL (default https://app.brainbaselabs.com)`);
|
|
81922
82408
|
out.push("");
|
|
81923
82409
|
out.push(divider("ENV"));
|
|
81924
82410
|
out.push("");
|
|
81925
|
-
out.push(` ${
|
|
81926
|
-
out.push(` ${
|
|
81927
|
-
out.push(` ${
|
|
81928
|
-
out.push(` ${
|
|
81929
|
-
out.push(` ${
|
|
81930
|
-
out.push(` ${
|
|
81931
|
-
out.push(` ${
|
|
81932
|
-
out.push(` ${
|
|
81933
|
-
out.push(` ${
|
|
81934
|
-
out.push(` ${
|
|
81935
|
-
out.push(` ${
|
|
82411
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_HOME")} override the local config dir (default ~/.brainbase)`);
|
|
82412
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_DEBUG")} print full stack traces on error (any value; unset to disable)`);
|
|
82413
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_WEB_URL")} override the web app URL used by login`);
|
|
82414
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_CONTROL_PLANE_URL")} override the MAS host (/v2/cli; task create uses /v2/tasks)`);
|
|
82415
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_API_URL")} legacy KLS host override (uses /api/cli; proxy/registry fallback)`);
|
|
82416
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_PROXY_URL")} override the model-proxy URL used by harness traffic (default https://api.v1.brainbaselabs.com)`);
|
|
82417
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_REGISTRY_URL")} override the registry API URL (default https://api.v1.brainbaselabs.com)`);
|
|
82418
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_TOKEN")} long-lived CLI PAT; the only PAT control-plane commands accept (token.json is not read there)`);
|
|
82419
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_SKIP_AUTH")} bypass the auth gate for development`);
|
|
82420
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_NON_INTERACTIVE")} force non-interactive mode — skip/auto-default prompts (CI & agents)`);
|
|
82421
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_RUN_ENTRYPOINT")} =1 → agent pull executes the agent entrypoint (sandbox boots; or pass --run-entrypoint)`);
|
|
81936
82422
|
out.push("");
|
|
81937
|
-
out.push(` ${
|
|
81938
|
-
out.push(` ${
|
|
81939
|
-
out.push(` ${
|
|
81940
|
-
out.push(` ${
|
|
81941
|
-
out.push(` ${
|
|
81942
|
-
out.push(` ${
|
|
82423
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_MEMORY_MCP_URL")} override the built-in memory MCP host`);
|
|
82424
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_BROWSER_MCP_URL")} override the built-in browser MCP host`);
|
|
82425
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_SLACK_MCP_URL")} override the built-in Slack MCP host`);
|
|
82426
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_MEETING_MCP_URL")} override the built-in meeting MCP host`);
|
|
82427
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_GITHUB_MCP_URL")} override the built-in GitHub MCP host`);
|
|
82428
|
+
out.push(` ${import_picocolors53.default.dim("BRAINBASE_ORCHESTRATION_MCP_URL")} override the built-in orchestration MCP host`);
|
|
81943
82429
|
out.push("");
|
|
81944
82430
|
out.push(divider("HARNESSES"));
|
|
81945
82431
|
out.push("");
|
|
81946
|
-
out.push(` ${
|
|
81947
|
-
out.push(` ${
|
|
81948
|
-
out.push(` ${
|
|
82432
|
+
out.push(` ${import_picocolors53.default.dim("•")} ${import_picocolors53.default.bold("claude-code")} ${import_picocolors53.default.dim("skills, mcps, agents, commands, playbooks, instructions, files")}`);
|
|
82433
|
+
out.push(` ${import_picocolors53.default.dim("•")} ${import_picocolors53.default.bold("codex")} ${import_picocolors53.default.dim("skills, mcps, commands, playbooks, instructions, files")}`);
|
|
82434
|
+
out.push(` ${import_picocolors53.default.dim("•")} ${import_picocolors53.default.bold("kafka")} ${import_picocolors53.default.dim("skills, mcps, agents, commands, playbooks, instructions, files")}`);
|
|
81949
82435
|
out.push("");
|
|
81950
82436
|
console.log(out.join(`
|
|
81951
82437
|
`));
|
|
@@ -82097,13 +82583,13 @@ async function requireAuth(cmd) {
|
|
|
82097
82583
|
if (STORED_PAT_COMMANDS.has(cmd) && readToken())
|
|
82098
82584
|
return;
|
|
82099
82585
|
console.error("");
|
|
82100
|
-
console.error(` ${brandTint("◆")} ${
|
|
82586
|
+
console.error(` ${brandTint("◆")} ${import_picocolors53.default.bold("brainbase")}`);
|
|
82101
82587
|
console.error("");
|
|
82102
|
-
console.error(` ${
|
|
82588
|
+
console.error(` ${import_picocolors53.default.red("✗")} You need to sign in to use ${import_picocolors53.default.bold("brainbase " + cmd)}.`);
|
|
82103
82589
|
if (status.reason)
|
|
82104
|
-
console.error(` ${
|
|
82590
|
+
console.error(` ${import_picocolors53.default.dim(status.reason)}`);
|
|
82105
82591
|
console.error("");
|
|
82106
|
-
console.error(` Run ${
|
|
82592
|
+
console.error(` Run ${import_picocolors53.default.cyan("brainbase login")} to connect this device.`);
|
|
82107
82593
|
console.error("");
|
|
82108
82594
|
process14.exit(1);
|
|
82109
82595
|
}
|
|
@@ -82148,6 +82634,8 @@ async function main() {
|
|
|
82148
82634
|
const noTracking = hasFlag2(sharedArgs, "--no-tracking");
|
|
82149
82635
|
const track = hasFlag2(sharedArgs, "--track");
|
|
82150
82636
|
const forceFlag = hasFlag2(sharedArgs, "--force");
|
|
82637
|
+
const minimalFlag = hasFlag2(sharedArgs, "--minimal");
|
|
82638
|
+
const fullFlag = hasFlag2(sharedArgs, "--full");
|
|
82151
82639
|
const runEntrypointFlag = hasFlag2(sharedArgs, "--run-entrypoint");
|
|
82152
82640
|
const graphOnlyFlag = hasFlag2(sharedArgs, "--graph-only");
|
|
82153
82641
|
const nameFlag = takeFlag("--name");
|
|
@@ -82243,6 +82731,8 @@ async function main() {
|
|
|
82243
82731
|
scope: scopeFlag,
|
|
82244
82732
|
shell: shellFlag,
|
|
82245
82733
|
harness,
|
|
82734
|
+
minimal: minimalFlag,
|
|
82735
|
+
full: fullFlag,
|
|
82246
82736
|
name: nameFlag,
|
|
82247
82737
|
tagline: taglineFlag,
|
|
82248
82738
|
orgId: orgIdFlag,
|
|
@@ -82316,10 +82806,10 @@ async function main() {
|
|
|
82316
82806
|
process14.exit(1);
|
|
82317
82807
|
}
|
|
82318
82808
|
} catch (err) {
|
|
82319
|
-
console.error(
|
|
82809
|
+
console.error(import_picocolors53.default.red(`
|
|
82320
82810
|
${err.message}`));
|
|
82321
82811
|
if (err instanceof ApiError && err.status === 401) {
|
|
82322
|
-
console.error(` Run ${
|
|
82812
|
+
console.error(` Run ${import_picocolors53.default.cyan("brainbase login")} to connect this device.`);
|
|
82323
82813
|
}
|
|
82324
82814
|
if (process14.env.BRAINBASE_DEBUG)
|
|
82325
82815
|
console.error(err.stack);
|