@pellux/goodvibes-agent 1.0.3 → 1.0.5
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/CHANGELOG.md +12 -0
- package/README.md +2 -2
- package/dist/package/main.js +831 -199
- package/docs/README.md +2 -2
- package/docs/getting-started.md +2 -2
- package/docs/tools-and-commands.md +7 -3
- package/package.json +1 -1
- package/src/tools/agent-harness-keybinding-metadata.ts +262 -0
- package/src/tools/agent-harness-tool-schema.ts +127 -0
- package/src/tools/agent-harness-tool.ts +47 -144
- package/src/tools/agent-harness-ui-surface-metadata.ts +343 -0
- package/src/version.ts +1 -1
package/dist/package/main.js
CHANGED
|
@@ -816566,7 +816566,7 @@ var createStyledCell = (char, overrides = {}) => ({
|
|
|
816566
816566
|
// src/version.ts
|
|
816567
816567
|
import { readFileSync } from "fs";
|
|
816568
816568
|
import { join } from "path";
|
|
816569
|
-
var _version = "1.0.
|
|
816569
|
+
var _version = "1.0.5";
|
|
816570
816570
|
var _sdkVersion = "0.33.35";
|
|
816571
816571
|
try {
|
|
816572
816572
|
const pkg = JSON.parse(readFileSync(join(import.meta.dir, "..", "package.json"), "utf-8"));
|
|
@@ -821197,7 +821197,7 @@ var INBOUND_EVENT_SURFACE_KINDS = new Set([
|
|
|
821197
821197
|
]);
|
|
821198
821198
|
// src/runtime/onboarding/apply.ts
|
|
821199
821199
|
init_config8();
|
|
821200
|
-
import { existsSync as
|
|
821200
|
+
import { existsSync as existsSync85, readFileSync as readFileSync91, rmSync as rmSync10 } from "fs";
|
|
821201
821201
|
|
|
821202
821202
|
// src/agent/runtime-profile.ts
|
|
821203
821203
|
import { existsSync as existsSync43, mkdirSync as mkdirSync32, readFileSync as readFileSync48, readdirSync as readdirSync15, rmSync as rmSync5, statSync as statSync13, writeFileSync as writeFileSync29 } from "fs";
|
|
@@ -847775,13 +847775,13 @@ init_state3();
|
|
|
847775
847775
|
|
|
847776
847776
|
// src/input/commands/recall-shared.ts
|
|
847777
847777
|
var VALID_CLASSES = ["decision", "constraint", "incident", "pattern", "fact", "risk", "runbook", "architecture", "ownership"];
|
|
847778
|
-
var
|
|
847778
|
+
var VALID_SCOPES2 = ["session", "project", "team"];
|
|
847779
847779
|
var VALID_REVIEW_STATES = ["fresh", "reviewed", "stale", "contradicted"];
|
|
847780
847780
|
function isValidClass(s4) {
|
|
847781
847781
|
return VALID_CLASSES.includes(s4);
|
|
847782
847782
|
}
|
|
847783
847783
|
function isValidScope(s4) {
|
|
847784
|
-
return
|
|
847784
|
+
return VALID_SCOPES2.includes(s4);
|
|
847785
847785
|
}
|
|
847786
847786
|
function isValidReviewState(s4) {
|
|
847787
847787
|
return VALID_REVIEW_STATES.includes(s4);
|
|
@@ -847824,7 +847824,7 @@ function handleRecallSearch(args2, context) {
|
|
|
847824
847824
|
if (isValidScope(scope))
|
|
847825
847825
|
filter.scope = scope;
|
|
847826
847826
|
else {
|
|
847827
|
-
context.print(`[memory] Unknown scope "${scope}". Valid values ${
|
|
847827
|
+
context.print(`[memory] Unknown scope "${scope}". Valid values ${VALID_SCOPES2.join(", ")}.`);
|
|
847828
847828
|
return;
|
|
847829
847829
|
}
|
|
847830
847830
|
}
|
|
@@ -847999,7 +847999,7 @@ function handleRecallList(args2, context) {
|
|
|
847999
847999
|
if (scopeIdx !== -1 && args2[scopeIdx + 1]) {
|
|
848000
848000
|
const scope = args2[scopeIdx + 1];
|
|
848001
848001
|
if (!isValidScope(scope)) {
|
|
848002
|
-
context.print(`[memory] Unknown scope "${scope}". Valid values ${
|
|
848002
|
+
context.print(`[memory] Unknown scope "${scope}". Valid values ${VALID_SCOPES2.join(", ")}.`);
|
|
848003
848003
|
return;
|
|
848004
848004
|
}
|
|
848005
848005
|
filter.scope = scope;
|
|
@@ -848049,7 +848049,7 @@ async function handleRecallAdd(args2, context) {
|
|
|
848049
848049
|
const tags = tagsRaw ? tagsRaw.split(",").map((token) => token.trim()).filter(Boolean) : [];
|
|
848050
848050
|
const scope = scopeRaw && isValidScope(scopeRaw) ? scopeRaw : "project";
|
|
848051
848051
|
if (scopeRaw && !isValidScope(scopeRaw)) {
|
|
848052
|
-
context.print(`[memory] Invalid scope "${scopeRaw}". Valid values ${
|
|
848052
|
+
context.print(`[memory] Invalid scope "${scopeRaw}". Valid values ${VALID_SCOPES2.join(", ")}.`);
|
|
848053
848053
|
return;
|
|
848054
848054
|
}
|
|
848055
848055
|
const provenance = [];
|
|
@@ -848183,7 +848183,7 @@ function handleRecallExport(args2, context) {
|
|
|
848183
848183
|
if (scopeIdx !== -1 && commandArgs[scopeIdx + 1]) {
|
|
848184
848184
|
const scope = commandArgs[scopeIdx + 1];
|
|
848185
848185
|
if (!isValidScope(scope)) {
|
|
848186
|
-
context.print(`[memory] Unknown scope "${scope}". Valid values ${
|
|
848186
|
+
context.print(`[memory] Unknown scope "${scope}". Valid values ${VALID_SCOPES2.join(", ")}.`);
|
|
848187
848187
|
return;
|
|
848188
848188
|
}
|
|
848189
848189
|
filter.scope = scope;
|
|
@@ -848262,7 +848262,7 @@ function handleRecallHandoffExport(args2, context) {
|
|
|
848262
848262
|
const scopeIdx = commandArgs.indexOf("--scope");
|
|
848263
848263
|
const scopeRaw = scopeIdx !== -1 ? commandArgs[scopeIdx + 1] : "team";
|
|
848264
848264
|
if (!scopeRaw || !isValidScope(scopeRaw)) {
|
|
848265
|
-
context.print(`[memory] Unknown scope "${scopeRaw ?? ""}". Valid values ${
|
|
848265
|
+
context.print(`[memory] Unknown scope "${scopeRaw ?? ""}". Valid values ${VALID_SCOPES2.join(", ")}.`);
|
|
848266
848266
|
return;
|
|
848267
848267
|
}
|
|
848268
848268
|
const bundle = memory.exportBundle({ scope: scopeRaw });
|
|
@@ -848378,7 +848378,7 @@ function handleRecallPromote(args2, context) {
|
|
|
848378
848378
|
const id = parsed.rest[0];
|
|
848379
848379
|
const scope = parsed.rest[1];
|
|
848380
848380
|
if (!id || !scope || !isValidScope(scope)) {
|
|
848381
|
-
context.print(`[memory] Usage: /memory promote <id> <${
|
|
848381
|
+
context.print(`[memory] Usage: /memory promote <id> <${VALID_SCOPES2.join("|")}> --yes`);
|
|
848382
848382
|
return;
|
|
848383
848383
|
}
|
|
848384
848384
|
if (!parsed.yes) {
|
|
@@ -862154,7 +862154,7 @@ import { mkdirSync as mkdirSync64, readFileSync as readFileSync86, writeFileSync
|
|
|
862154
862154
|
import { dirname as dirname63, resolve as resolve39 } from "path";
|
|
862155
862155
|
init_state3();
|
|
862156
862156
|
var VALID_CLASSES2 = ["decision", "constraint", "incident", "pattern", "fact", "risk", "runbook", "architecture", "ownership"];
|
|
862157
|
-
var
|
|
862157
|
+
var VALID_SCOPES4 = ["session", "project", "team"];
|
|
862158
862158
|
var VALID_REVIEW_STATES3 = ["fresh", "reviewed", "stale", "contradicted"];
|
|
862159
862159
|
var VALID_PROVENANCE_KINDS = ["session", "turn", "task", "event", "file"];
|
|
862160
862160
|
var VALUE_OPTIONS = new Set([
|
|
@@ -862254,7 +862254,7 @@ function isMemoryClass2(value) {
|
|
|
862254
862254
|
return VALID_CLASSES2.includes(value);
|
|
862255
862255
|
}
|
|
862256
862256
|
function isMemoryScope2(value) {
|
|
862257
|
-
return
|
|
862257
|
+
return VALID_SCOPES4.includes(value);
|
|
862258
862258
|
}
|
|
862259
862259
|
function isReviewState(value) {
|
|
862260
862260
|
return VALID_REVIEW_STATES3.includes(value);
|
|
@@ -862269,7 +862269,7 @@ function requireClass(value) {
|
|
|
862269
862269
|
}
|
|
862270
862270
|
function requireScope(value) {
|
|
862271
862271
|
if (!value || !isMemoryScope2(value))
|
|
862272
|
-
throw new Error(`Invalid memory scope "${value ?? ""}". Valid values ${
|
|
862272
|
+
throw new Error(`Invalid memory scope "${value ?? ""}". Valid values ${VALID_SCOPES4.join(", ")}`);
|
|
862273
862273
|
return value;
|
|
862274
862274
|
}
|
|
862275
862275
|
function optionalScope(value) {
|
|
@@ -879718,7 +879718,19 @@ function describeHarnessCliCommand(args2) {
|
|
|
879718
879718
|
};
|
|
879719
879719
|
}
|
|
879720
879720
|
|
|
879721
|
-
// src/tools/agent-harness-
|
|
879721
|
+
// src/tools/agent-harness-keybinding-metadata.ts
|
|
879722
|
+
import { existsSync as existsSync82, mkdirSync as mkdirSync67, readFileSync as readFileSync89, writeFileSync as writeFileSync58 } from "fs";
|
|
879723
|
+
import { dirname as dirname66 } from "path";
|
|
879724
|
+
var FIXED_SHORTCUTS = [
|
|
879725
|
+
{ key: "Enter", description: "Send prompt" },
|
|
879726
|
+
{ key: "Shift+Enter / Ctrl+J", description: "Insert newline" },
|
|
879727
|
+
{ key: "Up / Down", description: "Navigate input history, lists, and scrollable overlays" },
|
|
879728
|
+
{ key: "Tab", description: "Autocomplete slash command or file mention" },
|
|
879729
|
+
{ key: "Esc", description: "Close overlays, pickers, and transient input modes" },
|
|
879730
|
+
{ key: "? / F1", description: "Toggle help overlay" },
|
|
879731
|
+
{ key: "F2 / /shortcuts", description: "Open keyboard shortcut reference" },
|
|
879732
|
+
{ key: "/keybindings", description: "List configurable keybindings and config path" }
|
|
879733
|
+
];
|
|
879722
879734
|
function readString51(value) {
|
|
879723
879735
|
return typeof value === "string" ? value.trim() : "";
|
|
879724
879736
|
}
|
|
@@ -879728,6 +879740,237 @@ function readLimit6(value, fallback) {
|
|
|
879728
879740
|
return fallback;
|
|
879729
879741
|
return Math.max(1, Math.min(500, Math.trunc(parsed)));
|
|
879730
879742
|
}
|
|
879743
|
+
function readFieldMap(value) {
|
|
879744
|
+
if (typeof value !== "object" || value === null || Array.isArray(value))
|
|
879745
|
+
return {};
|
|
879746
|
+
return Object.fromEntries(Object.entries(value).map(([key, entry]) => [key, typeof entry === "string" ? entry : String(entry)]));
|
|
879747
|
+
}
|
|
879748
|
+
function requireKeybindingsManager2(context) {
|
|
879749
|
+
const manager5 = context.workspace.keybindingsManager;
|
|
879750
|
+
if (!manager5)
|
|
879751
|
+
throw new Error("workspace.keybindingsManager is unavailable in this Agent runtime");
|
|
879752
|
+
return manager5;
|
|
879753
|
+
}
|
|
879754
|
+
function isKeyAction2(action2) {
|
|
879755
|
+
return Object.hasOwn(ACTION_DESCRIPTIONS, action2);
|
|
879756
|
+
}
|
|
879757
|
+
function actionFromArgs(args2) {
|
|
879758
|
+
const action2 = readString51(args2.actionId || args2.key || args2.query);
|
|
879759
|
+
return action2 && isKeyAction2(action2) ? action2 : null;
|
|
879760
|
+
}
|
|
879761
|
+
function readBoolean15(value) {
|
|
879762
|
+
if (typeof value === "boolean")
|
|
879763
|
+
return value;
|
|
879764
|
+
if (typeof value !== "string")
|
|
879765
|
+
return;
|
|
879766
|
+
const normalized = value.trim().toLowerCase();
|
|
879767
|
+
if (["true", "yes", "y", "1", "on"].includes(normalized))
|
|
879768
|
+
return true;
|
|
879769
|
+
if (["false", "no", "n", "0", "off"].includes(normalized))
|
|
879770
|
+
return false;
|
|
879771
|
+
return;
|
|
879772
|
+
}
|
|
879773
|
+
function normalizeCombo(value) {
|
|
879774
|
+
if (typeof value !== "object" || value === null || Array.isArray(value))
|
|
879775
|
+
return null;
|
|
879776
|
+
const raw = value;
|
|
879777
|
+
const key = readString51(raw.key);
|
|
879778
|
+
if (!key)
|
|
879779
|
+
return null;
|
|
879780
|
+
const combo = { key };
|
|
879781
|
+
const ctrl = readBoolean15(raw.ctrl);
|
|
879782
|
+
const shift = readBoolean15(raw.shift);
|
|
879783
|
+
const alt = readBoolean15(raw.alt);
|
|
879784
|
+
if (ctrl !== undefined)
|
|
879785
|
+
combo.ctrl = ctrl;
|
|
879786
|
+
if (shift !== undefined)
|
|
879787
|
+
combo.shift = shift;
|
|
879788
|
+
if (alt !== undefined)
|
|
879789
|
+
combo.alt = alt;
|
|
879790
|
+
return combo;
|
|
879791
|
+
}
|
|
879792
|
+
function parseComboLabel(value) {
|
|
879793
|
+
const parts2 = value.split("+").map((part) => part.trim()).filter(Boolean);
|
|
879794
|
+
if (parts2.length === 0)
|
|
879795
|
+
return null;
|
|
879796
|
+
const key = parts2.at(-1);
|
|
879797
|
+
if (!key)
|
|
879798
|
+
return null;
|
|
879799
|
+
const combo = { key: key.length === 1 ? key.toLowerCase() : key.toLowerCase() };
|
|
879800
|
+
for (const part of parts2.slice(0, -1)) {
|
|
879801
|
+
const normalized = part.toLowerCase();
|
|
879802
|
+
if (normalized === "ctrl" || normalized === "control")
|
|
879803
|
+
combo.ctrl = true;
|
|
879804
|
+
else if (normalized === "shift")
|
|
879805
|
+
combo.shift = true;
|
|
879806
|
+
else if (normalized === "alt" || normalized === "option")
|
|
879807
|
+
combo.alt = true;
|
|
879808
|
+
else
|
|
879809
|
+
return null;
|
|
879810
|
+
}
|
|
879811
|
+
return combo;
|
|
879812
|
+
}
|
|
879813
|
+
function combosFromArgs(args2) {
|
|
879814
|
+
if (Array.isArray(args2.combos)) {
|
|
879815
|
+
const combos = args2.combos.map(normalizeCombo);
|
|
879816
|
+
if (combos.every((combo2) => combo2 !== null))
|
|
879817
|
+
return combos;
|
|
879818
|
+
throw new Error("set_keybinding combos must be objects with key and optional boolean ctrl/shift/alt fields.");
|
|
879819
|
+
}
|
|
879820
|
+
const combo = normalizeCombo(args2.combo);
|
|
879821
|
+
if (combo)
|
|
879822
|
+
return [combo];
|
|
879823
|
+
const fields = readFieldMap(args2.fields);
|
|
879824
|
+
const fieldCombo = normalizeCombo(fields);
|
|
879825
|
+
if (fieldCombo)
|
|
879826
|
+
return [fieldCombo];
|
|
879827
|
+
const labelCombo = parseComboLabel(readString51(args2.value));
|
|
879828
|
+
if (labelCombo)
|
|
879829
|
+
return [labelCombo];
|
|
879830
|
+
throw new Error('set_keybinding requires combo, combos, fields.key, or a value such as "Ctrl+G".');
|
|
879831
|
+
}
|
|
879832
|
+
function comboFingerprint(combo) {
|
|
879833
|
+
return `${combo.key}:${combo.ctrl ? 1 : 0}:${combo.shift ? 1 : 0}:${combo.alt ? 1 : 0}`;
|
|
879834
|
+
}
|
|
879835
|
+
function combosEqual(left, right) {
|
|
879836
|
+
if (left.length !== right.length)
|
|
879837
|
+
return false;
|
|
879838
|
+
return left.every((combo, index) => comboFingerprint(combo) === comboFingerprint(right[index]));
|
|
879839
|
+
}
|
|
879840
|
+
function describeCombo(manager5, combo) {
|
|
879841
|
+
return {
|
|
879842
|
+
key: combo.key,
|
|
879843
|
+
ctrl: combo.ctrl === true,
|
|
879844
|
+
shift: combo.shift === true,
|
|
879845
|
+
alt: combo.alt === true,
|
|
879846
|
+
label: manager5.formatCombo(combo)
|
|
879847
|
+
};
|
|
879848
|
+
}
|
|
879849
|
+
function bindingMatches(entry, query2) {
|
|
879850
|
+
if (!query2)
|
|
879851
|
+
return true;
|
|
879852
|
+
const haystack = [
|
|
879853
|
+
entry.action,
|
|
879854
|
+
entry.description,
|
|
879855
|
+
...entry.combos.map((combo) => comboFingerprint(combo))
|
|
879856
|
+
].join(`
|
|
879857
|
+
`).toLowerCase();
|
|
879858
|
+
return haystack.includes(query2.toLowerCase());
|
|
879859
|
+
}
|
|
879860
|
+
function describeBinding(manager5, action2, combos) {
|
|
879861
|
+
const defaults3 = DEFAULT_KEYBINDINGS[action2];
|
|
879862
|
+
const customized = !combosEqual(combos, defaults3);
|
|
879863
|
+
return {
|
|
879864
|
+
action: action2,
|
|
879865
|
+
description: ACTION_DESCRIPTIONS[action2],
|
|
879866
|
+
bindings: combos.map((combo) => describeCombo(manager5, combo)),
|
|
879867
|
+
labels: combos.map((combo) => manager5.formatCombo(combo)),
|
|
879868
|
+
defaultBindings: defaults3.map((combo) => describeCombo(manager5, combo)),
|
|
879869
|
+
customized,
|
|
879870
|
+
source: customized ? "custom" : "default"
|
|
879871
|
+
};
|
|
879872
|
+
}
|
|
879873
|
+
function readOverrideFile(configPath) {
|
|
879874
|
+
if (!existsSync82(configPath))
|
|
879875
|
+
return {};
|
|
879876
|
+
const parsed = JSON.parse(readFileSync89(configPath, "utf-8"));
|
|
879877
|
+
if (typeof parsed !== "object" || parsed === null || Array.isArray(parsed)) {
|
|
879878
|
+
throw new Error(`Keybindings config ${configPath} must contain a JSON object.`);
|
|
879879
|
+
}
|
|
879880
|
+
return parsed;
|
|
879881
|
+
}
|
|
879882
|
+
function writeOverrideFile(configPath, overrides) {
|
|
879883
|
+
mkdirSync67(dirname66(configPath), { recursive: true });
|
|
879884
|
+
writeFileSync58(configPath, `${JSON.stringify(overrides, null, 2)}
|
|
879885
|
+
`, "utf-8");
|
|
879886
|
+
}
|
|
879887
|
+
function totalHarnessKeybindings(context) {
|
|
879888
|
+
return context.workspace.keybindingsManager?.getAll().length ?? 0;
|
|
879889
|
+
}
|
|
879890
|
+
function totalHarnessShortcuts(context) {
|
|
879891
|
+
return totalHarnessKeybindings(context) + FIXED_SHORTCUTS.length;
|
|
879892
|
+
}
|
|
879893
|
+
function listHarnessShortcuts(context, args2) {
|
|
879894
|
+
const keybindings = listHarnessKeybindings(context, args2);
|
|
879895
|
+
const query2 = readString51(args2.query).toLowerCase();
|
|
879896
|
+
const fixed = FIXED_SHORTCUTS.filter((shortcut) => !query2 || `${shortcut.key}
|
|
879897
|
+
${shortcut.description}`.toLowerCase().includes(query2)).slice(0, readLimit6(args2.limit, 200)).map((shortcut) => ({ ...shortcut, source: "fixed", userEditable: false }));
|
|
879898
|
+
return {
|
|
879899
|
+
configPath: keybindings.configPath,
|
|
879900
|
+
fixedShortcuts: fixed,
|
|
879901
|
+
configurableKeybindings: keybindings.keybindings,
|
|
879902
|
+
returned: fixed.length + Number(keybindings.returned ?? 0),
|
|
879903
|
+
total: totalHarnessShortcuts(context),
|
|
879904
|
+
policy: "Fixed shortcuts are runtime/editor controls. Configurable keybindings can be changed with set_keybinding/reset_keybinding."
|
|
879905
|
+
};
|
|
879906
|
+
}
|
|
879907
|
+
function listHarnessKeybindings(context, args2) {
|
|
879908
|
+
const manager5 = requireKeybindingsManager2(context);
|
|
879909
|
+
const query2 = readString51(args2.query);
|
|
879910
|
+
const entries = manager5.getAll().filter((entry) => bindingMatches(entry, query2)).slice(0, readLimit6(args2.limit, 200)).map((entry) => describeBinding(manager5, entry.action, entry.combos));
|
|
879911
|
+
return {
|
|
879912
|
+
configPath: manager5.getConfigPath(),
|
|
879913
|
+
keybindings: entries,
|
|
879914
|
+
returned: entries.length,
|
|
879915
|
+
total: manager5.getAll().length,
|
|
879916
|
+
policy: "Reads the live resolved keybindings. set_keybinding/reset_keybinding write the same keybindings.json file the user can edit and reload the runtime manager."
|
|
879917
|
+
};
|
|
879918
|
+
}
|
|
879919
|
+
function describeHarnessKeybinding(context, args2) {
|
|
879920
|
+
const manager5 = requireKeybindingsManager2(context);
|
|
879921
|
+
const action2 = actionFromArgs(args2);
|
|
879922
|
+
if (!action2)
|
|
879923
|
+
return null;
|
|
879924
|
+
const entry = manager5.getAll().find((candidate) => candidate.action === action2);
|
|
879925
|
+
return entry ? {
|
|
879926
|
+
configPath: manager5.getConfigPath(),
|
|
879927
|
+
...describeBinding(manager5, entry.action, entry.combos)
|
|
879928
|
+
} : null;
|
|
879929
|
+
}
|
|
879930
|
+
function setHarnessKeybinding(context, args2) {
|
|
879931
|
+
const manager5 = requireKeybindingsManager2(context);
|
|
879932
|
+
const action2 = actionFromArgs(args2);
|
|
879933
|
+
if (!action2)
|
|
879934
|
+
throw new Error("set_keybinding requires a valid keybinding action id.");
|
|
879935
|
+
const combos = combosFromArgs(args2);
|
|
879936
|
+
const configPath = manager5.getConfigPath();
|
|
879937
|
+
const overrides = readOverrideFile(configPath);
|
|
879938
|
+
overrides[action2] = combos.length === 1 ? combos[0] : combos;
|
|
879939
|
+
writeOverrideFile(configPath, overrides);
|
|
879940
|
+
manager5.loadFromDisk();
|
|
879941
|
+
return {
|
|
879942
|
+
status: "updated",
|
|
879943
|
+
configPath,
|
|
879944
|
+
keybinding: describeHarnessKeybinding(context, { actionId: action2 })
|
|
879945
|
+
};
|
|
879946
|
+
}
|
|
879947
|
+
function resetHarnessKeybinding(context, args2) {
|
|
879948
|
+
const manager5 = requireKeybindingsManager2(context);
|
|
879949
|
+
const action2 = actionFromArgs(args2);
|
|
879950
|
+
if (!action2)
|
|
879951
|
+
throw new Error("reset_keybinding requires a valid keybinding action id.");
|
|
879952
|
+
const configPath = manager5.getConfigPath();
|
|
879953
|
+
const overrides = readOverrideFile(configPath);
|
|
879954
|
+
delete overrides[action2];
|
|
879955
|
+
writeOverrideFile(configPath, overrides);
|
|
879956
|
+
manager5.loadFromDisk();
|
|
879957
|
+
return {
|
|
879958
|
+
status: "reset",
|
|
879959
|
+
configPath,
|
|
879960
|
+
keybinding: describeHarnessKeybinding(context, { actionId: action2 })
|
|
879961
|
+
};
|
|
879962
|
+
}
|
|
879963
|
+
|
|
879964
|
+
// src/tools/agent-harness-panel-metadata.ts
|
|
879965
|
+
function readString52(value) {
|
|
879966
|
+
return typeof value === "string" ? value.trim() : "";
|
|
879967
|
+
}
|
|
879968
|
+
function readLimit7(value, fallback) {
|
|
879969
|
+
const parsed = typeof value === "string" && value.trim() ? Number(value) : value;
|
|
879970
|
+
if (typeof parsed !== "number" || !Number.isFinite(parsed))
|
|
879971
|
+
return fallback;
|
|
879972
|
+
return Math.max(1, Math.min(500, Math.trunc(parsed)));
|
|
879973
|
+
}
|
|
879731
879974
|
function panelManager(context) {
|
|
879732
879975
|
return context.workspace.panelManager ?? null;
|
|
879733
879976
|
}
|
|
@@ -879777,16 +880020,16 @@ function listHarnessPanels(context, args2) {
|
|
|
879777
880020
|
const manager5 = panelManager(context);
|
|
879778
880021
|
if (!manager5)
|
|
879779
880022
|
return [];
|
|
879780
|
-
const query2 =
|
|
879781
|
-
const category =
|
|
879782
|
-
const limit3 =
|
|
880023
|
+
const query2 = readString52(args2.query);
|
|
880024
|
+
const category = readString52(args2.category);
|
|
880025
|
+
const limit3 = readLimit7(args2.limit, 200);
|
|
879783
880026
|
return manager5.getRegisteredTypes().map((registration) => describePanelRegistration(context, registration)).filter((panel) => !category || panel.category === category).filter((panel) => panelMatches(panel, query2)).sort((a4, b3) => String(a4.id).localeCompare(String(b3.id))).slice(0, limit3);
|
|
879784
880027
|
}
|
|
879785
880028
|
function describeHarnessPanel(context, args2) {
|
|
879786
880029
|
const manager5 = panelManager(context);
|
|
879787
880030
|
if (!manager5)
|
|
879788
880031
|
return null;
|
|
879789
|
-
const panelId =
|
|
880032
|
+
const panelId = readString52(args2.panelId || args2.query);
|
|
879790
880033
|
if (!panelId)
|
|
879791
880034
|
return null;
|
|
879792
880035
|
const registration = manager5.getRegisteredTypes().find((panel) => panel.id === panelId || panel.name.toLowerCase() === panelId.toLowerCase());
|
|
@@ -879797,11 +880040,11 @@ function openHarnessPanel(context, args2) {
|
|
|
879797
880040
|
if (!panel) {
|
|
879798
880041
|
return {
|
|
879799
880042
|
status: "unknown_panel",
|
|
879800
|
-
panelId:
|
|
880043
|
+
panelId: readString52(args2.panelId || args2.query) || "<missing>",
|
|
879801
880044
|
availablePanels: listHarnessPanels(context, { limit: 50 }).map((entry) => entry.id)
|
|
879802
880045
|
};
|
|
879803
880046
|
}
|
|
879804
|
-
const requestedPane =
|
|
880047
|
+
const requestedPane = readString52(args2.pane);
|
|
879805
880048
|
const pane = requestedPane === "bottom" || requestedPane === "top" ? requestedPane : undefined;
|
|
879806
880049
|
if (!context.showPanel) {
|
|
879807
880050
|
return {
|
|
@@ -879826,10 +880069,10 @@ function output6(value) {
|
|
|
879826
880069
|
function error51(message) {
|
|
879827
880070
|
return { success: false, error: message };
|
|
879828
880071
|
}
|
|
879829
|
-
function
|
|
880072
|
+
function readString53(value) {
|
|
879830
880073
|
return typeof value === "string" ? value.trim() : "";
|
|
879831
880074
|
}
|
|
879832
|
-
function
|
|
880075
|
+
function readFieldMap2(value) {
|
|
879833
880076
|
if (typeof value !== "object" || value === null || Array.isArray(value))
|
|
879834
880077
|
return {};
|
|
879835
880078
|
return Object.fromEntries(Object.entries(value).map(([key, entry]) => [key, typeof entry === "string" ? entry : String(entry)]));
|
|
@@ -879852,11 +880095,11 @@ function describeEditor(editor) {
|
|
|
879852
880095
|
};
|
|
879853
880096
|
}
|
|
879854
880097
|
function readRecordId(args2) {
|
|
879855
|
-
const fields =
|
|
879856
|
-
return
|
|
880098
|
+
const fields = readFieldMap2(args2.fields);
|
|
880099
|
+
return readString53(args2.recordId ?? args2.id ?? fields.recordId ?? fields.id);
|
|
879857
880100
|
}
|
|
879858
880101
|
function requireConfirmed(args2, label) {
|
|
879859
|
-
if (!
|
|
880102
|
+
if (!readString53(args2.explicitUserRequest))
|
|
879860
880103
|
return `${label} requires explicitUserRequest with the user's exact request or a short faithful summary.`;
|
|
879861
880104
|
if (args2.confirm !== true)
|
|
879862
880105
|
return `${label} requires confirm:true after an explicit user request.`;
|
|
@@ -879866,7 +880109,7 @@ function fieldReader(editor, fields) {
|
|
|
879866
880109
|
return (id) => fields[id] ?? editor.fields.find((field) => field.id === id)?.value ?? "";
|
|
879867
880110
|
}
|
|
879868
880111
|
function hasExecutionFields(args2) {
|
|
879869
|
-
return Object.keys(
|
|
880112
|
+
return Object.keys(readFieldMap2(args2.fields)).some((key) => key !== "id" && key !== "recordId");
|
|
879870
880113
|
}
|
|
879871
880114
|
function missingRequiredFields(editor, fields) {
|
|
879872
880115
|
const read = fieldReader(editor, fields);
|
|
@@ -879977,14 +880220,14 @@ function localRegistryArgsFromEditor(editor, fields, id) {
|
|
|
879977
880220
|
return { domain: "routine", action: editor.mode === "update" ? "update" : "create", id, name: read("name"), description: read("description"), steps: read("steps"), tags: splitList5(read("tags")), triggers: splitList5(read("triggers")), requiresEnv: splitList5(read("requiresEnv")), requiresCommands: splitList5(read("requiresCommands")), enabled: isAffirmative15(read("enabled")), provenance: editor.recordId ? "agent-harness-local-operation" : "agent-harness-note-promotion" };
|
|
879978
880221
|
}
|
|
879979
880222
|
function localRegistryArgsForTarget(target, args2, recordId) {
|
|
879980
|
-
const fields =
|
|
880223
|
+
const fields = readFieldMap2(args2.fields);
|
|
879981
880224
|
const base2 = { domain: target.domain, action: target.action, ...recordId ? { id: recordId } : {} };
|
|
879982
880225
|
const edit = target.action === "update" ? localRegistryArgsFromEditor({ kind: target.domain, mode: "update", recordId, title: "", selectedFieldIndex: 0, message: "", fields: [] }, fields, recordId) : {};
|
|
879983
880226
|
return {
|
|
879984
880227
|
...base2,
|
|
879985
880228
|
...edit,
|
|
879986
880229
|
...target.action === "stale" && fields.reason ? { reason: fields.reason } : {},
|
|
879987
|
-
...target.action === "delete" ? { confirm: args2.confirm, explicitUserRequest:
|
|
880230
|
+
...target.action === "delete" ? { confirm: args2.confirm, explicitUserRequest: readString53(args2.explicitUserRequest) } : {}
|
|
879988
880231
|
};
|
|
879989
880232
|
}
|
|
879990
880233
|
async function executeTool(toolRegistry, name51, toolArgs) {
|
|
@@ -880024,12 +880267,12 @@ async function runLocalWorkspaceAction(deps, action2, args2) {
|
|
|
880024
880267
|
if (confirmationError2)
|
|
880025
880268
|
return error51(confirmationError2);
|
|
880026
880269
|
if (editor) {
|
|
880027
|
-
const fields =
|
|
880270
|
+
const fields = readFieldMap2(args2.fields);
|
|
880028
880271
|
const missing = missingRequiredFields(editor, fields);
|
|
880029
880272
|
if (missing.length > 0)
|
|
880030
880273
|
return output6({ status: "missing_required_fields", missing, action: action2.id, editor: describeEditor(editor) });
|
|
880031
880274
|
if (editor.kind === "knowledge-url")
|
|
880032
|
-
return executeTool(deps.toolRegistry, "agent_knowledge_ingest", { sourceKind: "url", url: fieldReader(editor, fields)("url"), tags: splitList5(fieldReader(editor, fields)("tags")), folderPath: fieldReader(editor, fields)("folder"), confirm: args2.confirm, explicitUserRequest:
|
|
880275
|
+
return executeTool(deps.toolRegistry, "agent_knowledge_ingest", { sourceKind: "url", url: fieldReader(editor, fields)("url"), tags: splitList5(fieldReader(editor, fields)("tags")), folderPath: fieldReader(editor, fields)("folder"), confirm: args2.confirm, explicitUserRequest: readString53(args2.explicitUserRequest) });
|
|
880033
880276
|
return executeTool(deps.toolRegistry, "agent_local_registry", localRegistryArgsFromEditor(editor, fields, recordId));
|
|
880034
880277
|
}
|
|
880035
880278
|
if (!target)
|
|
@@ -880038,19 +880281,19 @@ async function runLocalWorkspaceAction(deps, action2, args2) {
|
|
|
880038
880281
|
}
|
|
880039
880282
|
|
|
880040
880283
|
// src/tools/agent-harness-model-tool-catalog.ts
|
|
880041
|
-
function
|
|
880284
|
+
function readString54(value) {
|
|
880042
880285
|
return typeof value === "string" ? value.trim() : "";
|
|
880043
880286
|
}
|
|
880044
|
-
function
|
|
880287
|
+
function readLimit8(value, fallback) {
|
|
880045
880288
|
const parsed = typeof value === "string" && value.trim() ? Number(value) : value;
|
|
880046
880289
|
if (typeof parsed !== "number" || !Number.isFinite(parsed))
|
|
880047
880290
|
return fallback;
|
|
880048
880291
|
return Math.max(1, Math.min(500, Math.trunc(parsed)));
|
|
880049
880292
|
}
|
|
880050
880293
|
function listHarnessModelTools(toolRegistry, args2) {
|
|
880051
|
-
const query2 =
|
|
880294
|
+
const query2 = readString54(args2.query).toLowerCase();
|
|
880052
880295
|
const includeParameters = args2.includeParameters === true;
|
|
880053
|
-
const limit3 =
|
|
880296
|
+
const limit3 = readLimit8(args2.limit, 200);
|
|
880054
880297
|
return toolRegistry.getToolDefinitions().filter((tool2) => !query2 || [tool2.name, tool2.description, ...tool2.sideEffects ?? []].join(`
|
|
880055
880298
|
`).toLowerCase().includes(query2)).sort((a4, b3) => a4.name.localeCompare(b3.name)).slice(0, limit3).map((tool2) => ({
|
|
880056
880299
|
name: tool2.name,
|
|
@@ -880063,14 +880306,22 @@ function listHarnessModelTools(toolRegistry, args2) {
|
|
|
880063
880306
|
}));
|
|
880064
880307
|
}
|
|
880065
880308
|
|
|
880066
|
-
// src/tools/agent-harness-tool.ts
|
|
880067
|
-
var
|
|
880309
|
+
// src/tools/agent-harness-tool-schema.ts
|
|
880310
|
+
var AGENT_HARNESS_MODES = [
|
|
880068
880311
|
"summary",
|
|
880069
880312
|
"cli_commands",
|
|
880070
880313
|
"cli_command",
|
|
880071
880314
|
"panels",
|
|
880072
880315
|
"panel",
|
|
880073
880316
|
"open_panel",
|
|
880317
|
+
"ui_surfaces",
|
|
880318
|
+
"ui_surface",
|
|
880319
|
+
"open_ui_surface",
|
|
880320
|
+
"shortcuts",
|
|
880321
|
+
"keybindings",
|
|
880322
|
+
"keybinding",
|
|
880323
|
+
"set_keybinding",
|
|
880324
|
+
"reset_keybinding",
|
|
880074
880325
|
"commands",
|
|
880075
880326
|
"command",
|
|
880076
880327
|
"run_command",
|
|
@@ -880086,13 +880337,448 @@ var MODES = [
|
|
|
880086
880337
|
"tools",
|
|
880087
880338
|
"connected_host"
|
|
880088
880339
|
];
|
|
880340
|
+
var KEY_COMBO_PARAMETER_SCHEMA = {
|
|
880341
|
+
type: "object",
|
|
880342
|
+
properties: { key: { type: "string" }, ctrl: { type: "boolean" }, shift: { type: "boolean" }, alt: { type: "boolean" } },
|
|
880343
|
+
required: ["key"],
|
|
880344
|
+
additionalProperties: false
|
|
880345
|
+
};
|
|
880346
|
+
var AGENT_HARNESS_PARAMETER_PROPERTIES = {
|
|
880347
|
+
mode: {
|
|
880348
|
+
type: "string",
|
|
880349
|
+
enum: AGENT_HARNESS_MODES,
|
|
880350
|
+
description: "Harness operation to perform."
|
|
880351
|
+
},
|
|
880352
|
+
query: {
|
|
880353
|
+
type: "string",
|
|
880354
|
+
description: "Search text for command, setting, tool, or UI surface catalogs."
|
|
880355
|
+
},
|
|
880356
|
+
command: {
|
|
880357
|
+
type: "string",
|
|
880358
|
+
description: 'Full slash command string for mode run_command, for example "/settings get provider.model". In cli_command mode this may also hold a top-level CLI string such as "goodvibes-agent status --json".'
|
|
880359
|
+
},
|
|
880360
|
+
cliCommand: {
|
|
880361
|
+
type: "string",
|
|
880362
|
+
description: 'Top-level CLI command string for mode cli_command, for example "goodvibes-agent status --json" or "profiles list". This mode is read-only metadata/parse inspection.'
|
|
880363
|
+
},
|
|
880364
|
+
commandName: {
|
|
880365
|
+
type: "string",
|
|
880366
|
+
description: "Slash command root without the leading slash for mode command or run_command, or a top-level CLI command token for cli_command."
|
|
880367
|
+
},
|
|
880368
|
+
args: {
|
|
880369
|
+
type: "array",
|
|
880370
|
+
items: { type: "string" },
|
|
880371
|
+
description: "Slash command argument tokens for mode run_command when commandName is used."
|
|
880372
|
+
},
|
|
880373
|
+
categoryId: {
|
|
880374
|
+
type: "string",
|
|
880375
|
+
description: "Agent workspace category id for workspace action filtering or ui surface routing."
|
|
880376
|
+
},
|
|
880377
|
+
surfaceId: {
|
|
880378
|
+
type: "string",
|
|
880379
|
+
description: "UI surface id for ui_surface or open_ui_surface modes."
|
|
880380
|
+
},
|
|
880381
|
+
panelId: {
|
|
880382
|
+
type: "string",
|
|
880383
|
+
description: "Built-in panel id for panel or open_panel modes."
|
|
880384
|
+
},
|
|
880385
|
+
actionId: {
|
|
880386
|
+
type: "string",
|
|
880387
|
+
description: "Agent workspace action id for workspace_action or run_workspace_action, or keybinding action id for keybinding/set_keybinding/reset_keybinding."
|
|
880388
|
+
},
|
|
880389
|
+
fields: {
|
|
880390
|
+
type: "object",
|
|
880391
|
+
additionalProperties: { type: "string" },
|
|
880392
|
+
description: "Field values for run_workspace_action when the workspace action opens an editor form."
|
|
880393
|
+
},
|
|
880394
|
+
combo: {
|
|
880395
|
+
...KEY_COMBO_PARAMETER_SCHEMA,
|
|
880396
|
+
description: 'Single key combo for set_keybinding, for example { "key": "g", "ctrl": true }.'
|
|
880397
|
+
},
|
|
880398
|
+
combos: {
|
|
880399
|
+
type: "array",
|
|
880400
|
+
items: KEY_COMBO_PARAMETER_SCHEMA,
|
|
880401
|
+
description: "Multiple key combos for set_keybinding."
|
|
880402
|
+
},
|
|
880403
|
+
recordId: {
|
|
880404
|
+
type: "string",
|
|
880405
|
+
description: "Selected Agent-local record id for selection-based local workspace operations."
|
|
880406
|
+
},
|
|
880407
|
+
key: {
|
|
880408
|
+
type: "string",
|
|
880409
|
+
description: "Agent setting key for get_setting, set_setting, or reset_setting."
|
|
880410
|
+
},
|
|
880411
|
+
value: {
|
|
880412
|
+
anyOf: [
|
|
880413
|
+
{ type: "string" },
|
|
880414
|
+
{ type: "number" },
|
|
880415
|
+
{ type: "boolean" }
|
|
880416
|
+
],
|
|
880417
|
+
description: "Setting value for set_setting. Strings, booleans, numbers, and enum strings are accepted."
|
|
880418
|
+
},
|
|
880419
|
+
target: {
|
|
880420
|
+
type: "string",
|
|
880421
|
+
description: "Optional UI target, such as a model-picker target or settings target key."
|
|
880422
|
+
},
|
|
880423
|
+
category: {
|
|
880424
|
+
type: "string",
|
|
880425
|
+
description: "Setting category filter such as provider, behavior, tools, ui, tts, permissions, automation, or surfaces."
|
|
880426
|
+
},
|
|
880427
|
+
prefix: {
|
|
880428
|
+
type: "string",
|
|
880429
|
+
description: "Setting key prefix filter such as surfaces.slack."
|
|
880430
|
+
},
|
|
880431
|
+
includeHidden: {
|
|
880432
|
+
type: "boolean",
|
|
880433
|
+
description: "Include settings hidden from the Agent workspace because they are host-owned or non-Agent lifecycle settings."
|
|
880434
|
+
},
|
|
880435
|
+
includeParameters: {
|
|
880436
|
+
type: "boolean",
|
|
880437
|
+
description: "Include model tool JSON schemas in tools mode, or workspace editor field schemas in workspace_actions mode."
|
|
880438
|
+
},
|
|
880439
|
+
limit: {
|
|
880440
|
+
type: "number",
|
|
880441
|
+
description: "Maximum catalog entries to return."
|
|
880442
|
+
},
|
|
880443
|
+
pane: {
|
|
880444
|
+
type: "string",
|
|
880445
|
+
enum: ["top", "bottom"],
|
|
880446
|
+
description: "Preferred panel pane for open_panel when the current shell supports panel routing."
|
|
880447
|
+
},
|
|
880448
|
+
confirm: {
|
|
880449
|
+
type: "boolean",
|
|
880450
|
+
description: "Required true for set_setting, reset_setting, run_command, open_panel, open_ui_surface, and mutating run_workspace_action calls after an explicit user request."
|
|
880451
|
+
},
|
|
880452
|
+
explicitUserRequest: {
|
|
880453
|
+
type: "string",
|
|
880454
|
+
description: "Exact user request or faithful short summary authorizing a setting mutation or harness UI/command invocation."
|
|
880455
|
+
}
|
|
880456
|
+
};
|
|
880457
|
+
|
|
880458
|
+
// src/tools/agent-harness-ui-surface-metadata.ts
|
|
880459
|
+
function readString55(value) {
|
|
880460
|
+
return typeof value === "string" ? value.trim() : "";
|
|
880461
|
+
}
|
|
880462
|
+
function readLimit9(value, fallback) {
|
|
880463
|
+
const parsed = typeof value === "string" && value.trim() ? Number(value) : value;
|
|
880464
|
+
if (typeof parsed !== "number" || !Number.isFinite(parsed))
|
|
880465
|
+
return fallback;
|
|
880466
|
+
return Math.max(1, Math.min(500, Math.trunc(parsed)));
|
|
880467
|
+
}
|
|
880468
|
+
function routeUnavailable(surface) {
|
|
880469
|
+
return {
|
|
880470
|
+
status: "route_unavailable",
|
|
880471
|
+
surface: surface.id,
|
|
880472
|
+
note: "The current runtime did not provide the shell opener for this UI surface."
|
|
880473
|
+
};
|
|
880474
|
+
}
|
|
880475
|
+
function opened(surface, extra = {}) {
|
|
880476
|
+
return {
|
|
880477
|
+
status: "opened",
|
|
880478
|
+
surface: surface.id,
|
|
880479
|
+
kind: surface.kind,
|
|
880480
|
+
...extra,
|
|
880481
|
+
note: "UI routing was handed to the current Agent shell bridge."
|
|
880482
|
+
};
|
|
880483
|
+
}
|
|
880484
|
+
function optionalModelTarget(args2) {
|
|
880485
|
+
const target = readString55(args2.target);
|
|
880486
|
+
return target === "main" || target === "helper" || target === "tool" || target === "tts" ? target : undefined;
|
|
880487
|
+
}
|
|
880488
|
+
function optionalOnboardingMode(args2) {
|
|
880489
|
+
const target = readString55(args2.target);
|
|
880490
|
+
return target === "new" || target === "edit" || target === "reopen" ? target : undefined;
|
|
880491
|
+
}
|
|
880492
|
+
function workspaceCategory(args2) {
|
|
880493
|
+
return readString55(args2.categoryId || args2.category || args2.target) || undefined;
|
|
880494
|
+
}
|
|
880495
|
+
function settingsTarget(args2) {
|
|
880496
|
+
return readString55(args2.target || args2.key || args2.prefix) || undefined;
|
|
880497
|
+
}
|
|
880498
|
+
var UI_SURFACES = [
|
|
880499
|
+
{
|
|
880500
|
+
id: "agent-workspace",
|
|
880501
|
+
label: "Agent Workspace",
|
|
880502
|
+
kind: "workspace",
|
|
880503
|
+
summary: "Fullscreen operator workspace with setup, knowledge, local state, channels, automation, and delegation routes.",
|
|
880504
|
+
command: "/agent",
|
|
880505
|
+
preferredModelRoute: "Use workspace_actions/workspace_action/run_workspace_action for model operation; use open_ui_surface only to visibly navigate.",
|
|
880506
|
+
parameters: ["categoryId"],
|
|
880507
|
+
available: (context) => typeof context.openAgentWorkspace === "function",
|
|
880508
|
+
open: (context, args2) => {
|
|
880509
|
+
const surface = findSurfaceById("agent-workspace");
|
|
880510
|
+
if (!context.openAgentWorkspace)
|
|
880511
|
+
return routeUnavailable(surface);
|
|
880512
|
+
const categoryId = workspaceCategory(args2);
|
|
880513
|
+
context.openAgentWorkspace(categoryId);
|
|
880514
|
+
return opened(surface, { categoryId: categoryId ?? "default" });
|
|
880515
|
+
}
|
|
880516
|
+
},
|
|
880517
|
+
{
|
|
880518
|
+
id: "settings",
|
|
880519
|
+
label: "Settings",
|
|
880520
|
+
kind: "modal",
|
|
880521
|
+
summary: "Fullscreen settings workspace for Agent-owned configuration, subscriptions, secrets, MCP, tools, and surface settings.",
|
|
880522
|
+
command: "/settings",
|
|
880523
|
+
preferredModelRoute: "Use settings/get_setting/set_setting/reset_setting for model operation; use open_ui_surface only to visibly navigate.",
|
|
880524
|
+
parameters: ["target", "key", "prefix"],
|
|
880525
|
+
available: (context) => typeof context.openSettingsModal === "function",
|
|
880526
|
+
open: (context, args2) => {
|
|
880527
|
+
const surface = findSurfaceById("settings");
|
|
880528
|
+
if (!context.openSettingsModal)
|
|
880529
|
+
return routeUnavailable(surface);
|
|
880530
|
+
const target = settingsTarget(args2);
|
|
880531
|
+
context.openSettingsModal(target);
|
|
880532
|
+
return opened(surface, { target: target ?? "default" });
|
|
880533
|
+
}
|
|
880534
|
+
},
|
|
880535
|
+
{
|
|
880536
|
+
id: "mcp-workspace",
|
|
880537
|
+
label: "MCP Workspace",
|
|
880538
|
+
kind: "workspace",
|
|
880539
|
+
summary: "MCP server setup, trust posture, and tool inventory workspace.",
|
|
880540
|
+
command: "/mcp",
|
|
880541
|
+
preferredModelRoute: "Use workspace_actions, tools, and settings modes for model operation.",
|
|
880542
|
+
available: (context) => typeof context.openMcpWorkspace === "function",
|
|
880543
|
+
open: (context) => {
|
|
880544
|
+
const surface = findSurfaceById("mcp-workspace");
|
|
880545
|
+
if (!context.openMcpWorkspace)
|
|
880546
|
+
return routeUnavailable(surface);
|
|
880547
|
+
context.openMcpWorkspace();
|
|
880548
|
+
return opened(surface);
|
|
880549
|
+
}
|
|
880550
|
+
},
|
|
880551
|
+
{
|
|
880552
|
+
id: "model-picker",
|
|
880553
|
+
label: "Model Picker",
|
|
880554
|
+
kind: "picker",
|
|
880555
|
+
summary: "Interactive model picker for main, helper, tool, and TTS model routes.",
|
|
880556
|
+
command: "/model",
|
|
880557
|
+
preferredModelRoute: "Use settings mode for direct provider.model changes, or run_command /model with confirmation when a concrete model id is known.",
|
|
880558
|
+
parameters: ["target"],
|
|
880559
|
+
available: (context) => typeof context.openModelPicker === "function" || typeof context.openModelPickerWithTarget === "function",
|
|
880560
|
+
open: (context, args2) => {
|
|
880561
|
+
const surface = findSurfaceById("model-picker");
|
|
880562
|
+
const target = optionalModelTarget(args2);
|
|
880563
|
+
if (target && context.openModelPickerWithTarget) {
|
|
880564
|
+
const openedForTarget = context.openModelPickerWithTarget(target);
|
|
880565
|
+
return opened(surface, { target, openedForTarget });
|
|
880566
|
+
}
|
|
880567
|
+
if (!context.openModelPicker)
|
|
880568
|
+
return routeUnavailable(surface);
|
|
880569
|
+
context.openModelPicker();
|
|
880570
|
+
return opened(surface, { target: "main" });
|
|
880571
|
+
}
|
|
880572
|
+
},
|
|
880573
|
+
{
|
|
880574
|
+
id: "provider-picker",
|
|
880575
|
+
label: "Provider Picker",
|
|
880576
|
+
kind: "picker",
|
|
880577
|
+
summary: "Interactive provider picker for model route setup.",
|
|
880578
|
+
command: "/provider",
|
|
880579
|
+
preferredModelRoute: "Use settings mode for direct provider routing changes, or run confirmed slash-command mirrors for concrete provider changes.",
|
|
880580
|
+
parameters: ["target"],
|
|
880581
|
+
available: (context) => typeof context.openProviderPicker === "function" || typeof context.openProviderModelPickerWithTarget === "function",
|
|
880582
|
+
open: (context, args2) => {
|
|
880583
|
+
const surface = findSurfaceById("provider-picker");
|
|
880584
|
+
const target = optionalModelTarget(args2);
|
|
880585
|
+
if (target && context.openProviderModelPickerWithTarget) {
|
|
880586
|
+
context.openProviderModelPickerWithTarget(target);
|
|
880587
|
+
return opened(surface, { target });
|
|
880588
|
+
}
|
|
880589
|
+
if (!context.openProviderPicker)
|
|
880590
|
+
return routeUnavailable(surface);
|
|
880591
|
+
context.openProviderPicker();
|
|
880592
|
+
return opened(surface, { target: "main" });
|
|
880593
|
+
}
|
|
880594
|
+
},
|
|
880595
|
+
{
|
|
880596
|
+
id: "session-picker",
|
|
880597
|
+
label: "Session Picker",
|
|
880598
|
+
kind: "picker",
|
|
880599
|
+
summary: "Saved session browser and loader.",
|
|
880600
|
+
command: "/sessions",
|
|
880601
|
+
preferredModelRoute: "Use session slash-command mirrors with confirmation for concrete save/load/export actions.",
|
|
880602
|
+
available: (context) => typeof context.openSessionPicker === "function",
|
|
880603
|
+
open: (context) => {
|
|
880604
|
+
const surface = findSurfaceById("session-picker");
|
|
880605
|
+
if (!context.openSessionPicker)
|
|
880606
|
+
return routeUnavailable(surface);
|
|
880607
|
+
context.openSessionPicker();
|
|
880608
|
+
return opened(surface);
|
|
880609
|
+
}
|
|
880610
|
+
},
|
|
880611
|
+
{
|
|
880612
|
+
id: "profile-picker",
|
|
880613
|
+
label: "Profile Picker",
|
|
880614
|
+
kind: "picker",
|
|
880615
|
+
summary: "Agent profile picker for local isolated profile selection.",
|
|
880616
|
+
command: "/agent-profile",
|
|
880617
|
+
preferredModelRoute: "Use workspace profile actions or profile slash-command mirrors for concrete model operation.",
|
|
880618
|
+
available: (context) => typeof context.openProfilePicker === "function",
|
|
880619
|
+
open: (context) => {
|
|
880620
|
+
const surface = findSurfaceById("profile-picker");
|
|
880621
|
+
if (!context.openProfilePicker)
|
|
880622
|
+
return routeUnavailable(surface);
|
|
880623
|
+
context.openProfilePicker();
|
|
880624
|
+
return opened(surface);
|
|
880625
|
+
}
|
|
880626
|
+
},
|
|
880627
|
+
{
|
|
880628
|
+
id: "bookmark-modal",
|
|
880629
|
+
label: "Bookmarks",
|
|
880630
|
+
kind: "modal",
|
|
880631
|
+
summary: "Transcript bookmark browser.",
|
|
880632
|
+
command: "/bookmarks",
|
|
880633
|
+
preferredModelRoute: "Use slash-command mirrors for concrete bookmark inspection; opening is visible navigation only.",
|
|
880634
|
+
available: (context) => typeof context.openBookmarkModal === "function",
|
|
880635
|
+
open: (context) => {
|
|
880636
|
+
const surface = findSurfaceById("bookmark-modal");
|
|
880637
|
+
if (!context.openBookmarkModal)
|
|
880638
|
+
return routeUnavailable(surface);
|
|
880639
|
+
context.openBookmarkModal();
|
|
880640
|
+
return opened(surface);
|
|
880641
|
+
}
|
|
880642
|
+
},
|
|
880643
|
+
{
|
|
880644
|
+
id: "context-inspector",
|
|
880645
|
+
label: "Context Inspector",
|
|
880646
|
+
kind: "modal",
|
|
880647
|
+
summary: "Context-window usage and token breakdown inspector.",
|
|
880648
|
+
command: "/context",
|
|
880649
|
+
preferredModelRoute: "Use slash-command mirrors for text output; opening is visible navigation only.",
|
|
880650
|
+
available: (context) => typeof context.openContextInspector === "function",
|
|
880651
|
+
open: (context) => {
|
|
880652
|
+
const surface = findSurfaceById("context-inspector");
|
|
880653
|
+
if (!context.openContextInspector)
|
|
880654
|
+
return routeUnavailable(surface);
|
|
880655
|
+
context.openContextInspector();
|
|
880656
|
+
return opened(surface);
|
|
880657
|
+
}
|
|
880658
|
+
},
|
|
880659
|
+
{
|
|
880660
|
+
id: "help-overlay",
|
|
880661
|
+
label: "Help Overlay",
|
|
880662
|
+
kind: "overlay",
|
|
880663
|
+
summary: "Registry-driven command and shortcut help overlay.",
|
|
880664
|
+
command: "/help",
|
|
880665
|
+
preferredModelRoute: "Use commands/command and shortcuts modes for model-readable discovery.",
|
|
880666
|
+
available: (context) => typeof context.openHelpOverlay === "function",
|
|
880667
|
+
open: (context) => {
|
|
880668
|
+
const surface = findSurfaceById("help-overlay");
|
|
880669
|
+
if (!context.openHelpOverlay)
|
|
880670
|
+
return routeUnavailable(surface);
|
|
880671
|
+
context.openHelpOverlay();
|
|
880672
|
+
return opened(surface);
|
|
880673
|
+
}
|
|
880674
|
+
},
|
|
880675
|
+
{
|
|
880676
|
+
id: "shortcuts-overlay",
|
|
880677
|
+
label: "Shortcuts Overlay",
|
|
880678
|
+
kind: "overlay",
|
|
880679
|
+
summary: "Keyboard shortcut reference overlay.",
|
|
880680
|
+
command: "/shortcuts",
|
|
880681
|
+
preferredModelRoute: "Use shortcuts/keybindings modes for model-readable discovery and confirmed keybinding edits.",
|
|
880682
|
+
available: (context) => typeof context.openShortcutsOverlay === "function",
|
|
880683
|
+
open: (context) => {
|
|
880684
|
+
const surface = findSurfaceById("shortcuts-overlay");
|
|
880685
|
+
if (!context.openShortcutsOverlay)
|
|
880686
|
+
return routeUnavailable(surface);
|
|
880687
|
+
context.openShortcutsOverlay();
|
|
880688
|
+
return opened(surface);
|
|
880689
|
+
}
|
|
880690
|
+
},
|
|
880691
|
+
{
|
|
880692
|
+
id: "onboarding",
|
|
880693
|
+
label: "Onboarding Wizard",
|
|
880694
|
+
kind: "modal",
|
|
880695
|
+
summary: "First-run and setup review wizard for Agent readiness.",
|
|
880696
|
+
command: "/setup",
|
|
880697
|
+
preferredModelRoute: "Use workspace setup actions and settings modes for concrete model operation.",
|
|
880698
|
+
parameters: ["target=new|edit|reopen"],
|
|
880699
|
+
available: (context) => typeof context.openOnboardingWizard === "function",
|
|
880700
|
+
open: (context, args2) => {
|
|
880701
|
+
const surface = findSurfaceById("onboarding");
|
|
880702
|
+
if (!context.openOnboardingWizard)
|
|
880703
|
+
return routeUnavailable(surface);
|
|
880704
|
+
const mode = optionalOnboardingMode(args2);
|
|
880705
|
+
context.openOnboardingWizard(mode);
|
|
880706
|
+
return opened(surface, { mode: mode ?? "default" });
|
|
880707
|
+
}
|
|
880708
|
+
}
|
|
880709
|
+
];
|
|
880710
|
+
function findSurfaceById(surfaceId) {
|
|
880711
|
+
return UI_SURFACES.find((surface) => surface.id === surfaceId);
|
|
880712
|
+
}
|
|
880713
|
+
function surfaceMatches(surface, query2) {
|
|
880714
|
+
if (!query2)
|
|
880715
|
+
return true;
|
|
880716
|
+
return [
|
|
880717
|
+
surface.id,
|
|
880718
|
+
surface.label,
|
|
880719
|
+
surface.kind,
|
|
880720
|
+
surface.summary,
|
|
880721
|
+
surface.command,
|
|
880722
|
+
surface.preferredModelRoute
|
|
880723
|
+
].map((value) => String(value ?? "")).join(`
|
|
880724
|
+
`).toLowerCase().includes(query2.toLowerCase());
|
|
880725
|
+
}
|
|
880726
|
+
function describeSurface(context, surface) {
|
|
880727
|
+
return {
|
|
880728
|
+
id: surface.id,
|
|
880729
|
+
label: surface.label,
|
|
880730
|
+
kind: surface.kind,
|
|
880731
|
+
summary: surface.summary,
|
|
880732
|
+
command: surface.command,
|
|
880733
|
+
preferredModelRoute: surface.preferredModelRoute,
|
|
880734
|
+
parameters: surface.parameters ?? [],
|
|
880735
|
+
available: surface.available(context),
|
|
880736
|
+
policy: {
|
|
880737
|
+
effect: "visible-ui-navigation",
|
|
880738
|
+
confirmation: 'agent_harness mode:"open_ui_surface" requires confirm:true and explicitUserRequest.',
|
|
880739
|
+
boundary: "UI surface routing opens the same visible Agent shell surface the user can open. Use first-class model tools, settings modes, workspace actions, or confirmed slash-command mirrors for actual operations."
|
|
880740
|
+
}
|
|
880741
|
+
};
|
|
880742
|
+
}
|
|
880743
|
+
function totalHarnessUiSurfaces() {
|
|
880744
|
+
return UI_SURFACES.length;
|
|
880745
|
+
}
|
|
880746
|
+
function listHarnessUiSurfaces(context, args2) {
|
|
880747
|
+
const query2 = readString55(args2.query);
|
|
880748
|
+
const limit3 = readLimit9(args2.limit, 200);
|
|
880749
|
+
return UI_SURFACES.map((surface) => describeSurface(context, surface)).filter((surface) => surfaceMatches(surface, query2)).slice(0, limit3);
|
|
880750
|
+
}
|
|
880751
|
+
function describeHarnessUiSurface(context, args2) {
|
|
880752
|
+
const surfaceId = readString55(args2.surfaceId || args2.query);
|
|
880753
|
+
if (!surfaceId)
|
|
880754
|
+
return null;
|
|
880755
|
+
const surface = UI_SURFACES.find((entry) => entry.id === surfaceId || entry.label.toLowerCase() === surfaceId.toLowerCase());
|
|
880756
|
+
return surface ? describeSurface(context, surface) : null;
|
|
880757
|
+
}
|
|
880758
|
+
function openHarnessUiSurface(context, args2) {
|
|
880759
|
+
const surfaceId = readString55(args2.surfaceId || args2.query);
|
|
880760
|
+
const surface = UI_SURFACES.find((entry) => entry.id === surfaceId || entry.label.toLowerCase() === surfaceId.toLowerCase());
|
|
880761
|
+
if (!surface) {
|
|
880762
|
+
return {
|
|
880763
|
+
status: "unknown_ui_surface",
|
|
880764
|
+
surfaceId: surfaceId || "<missing>",
|
|
880765
|
+
availableSurfaces: UI_SURFACES.map((entry) => entry.id)
|
|
880766
|
+
};
|
|
880767
|
+
}
|
|
880768
|
+
return {
|
|
880769
|
+
...surface.open(context, args2),
|
|
880770
|
+
descriptor: describeSurface(context, surface)
|
|
880771
|
+
};
|
|
880772
|
+
}
|
|
880773
|
+
|
|
880774
|
+
// src/tools/agent-harness-tool.ts
|
|
880089
880775
|
function isMode(value) {
|
|
880090
|
-
return typeof value === "string" &&
|
|
880776
|
+
return typeof value === "string" && AGENT_HARNESS_MODES.includes(value);
|
|
880091
880777
|
}
|
|
880092
|
-
function
|
|
880778
|
+
function readString56(value) {
|
|
880093
880779
|
return typeof value === "string" ? value.trim() : "";
|
|
880094
880780
|
}
|
|
880095
|
-
function
|
|
880781
|
+
function readLimit10(value, fallback) {
|
|
880096
880782
|
const parsed = typeof value === "string" && value.trim() ? Number(value) : value;
|
|
880097
880783
|
if (typeof parsed !== "number" || !Number.isFinite(parsed))
|
|
880098
880784
|
return fallback;
|
|
@@ -880103,7 +880789,7 @@ function readStringArray12(value) {
|
|
|
880103
880789
|
return [];
|
|
880104
880790
|
return value.map((entry) => typeof entry === "string" ? entry : String(entry));
|
|
880105
880791
|
}
|
|
880106
|
-
function
|
|
880792
|
+
function readFieldMap3(value) {
|
|
880107
880793
|
if (typeof value !== "object" || value === null || Array.isArray(value))
|
|
880108
880794
|
return {};
|
|
880109
880795
|
return Object.fromEntries(Object.entries(value).map(([key, entry]) => [key, typeof entry === "string" ? entry : String(entry)]));
|
|
@@ -880172,8 +880858,8 @@ function describeWorkspaceEditor(editor) {
|
|
|
880172
880858
|
};
|
|
880173
880859
|
}
|
|
880174
880860
|
function selectedRoutineFromArgs(snapshot, args2) {
|
|
880175
|
-
const fields =
|
|
880176
|
-
const routineId =
|
|
880861
|
+
const fields = readFieldMap3(args2.fields);
|
|
880862
|
+
const routineId = readString56(args2.recordId) || readString56(fields.routineId) || readString56(fields.id);
|
|
880177
880863
|
if (!routineId)
|
|
880178
880864
|
return null;
|
|
880179
880865
|
return snapshot.localRoutines.find((routine) => routine.id === routineId || routine.name.toLowerCase() === routineId.toLowerCase()) ?? null;
|
|
@@ -880241,17 +880927,17 @@ function localEditorModelExecution(editorKind) {
|
|
|
880241
880927
|
return "Use the command field, editor schema, or a first-class Agent model tool when available.";
|
|
880242
880928
|
}
|
|
880243
880929
|
function listWorkspaceActions(deps, args2) {
|
|
880244
|
-
const query2 =
|
|
880245
|
-
const categoryId =
|
|
880246
|
-
const limit3 =
|
|
880930
|
+
const query2 = readString56(args2.query);
|
|
880931
|
+
const categoryId = readString56(args2.categoryId || args2.category);
|
|
880932
|
+
const limit3 = readLimit10(args2.limit, 200);
|
|
880247
880933
|
const includeEditor = args2.includeParameters === true;
|
|
880248
880934
|
const editorContext = includeEditor ? buildWorkspaceEditorContext(deps.commandContext, args2) : null;
|
|
880249
880935
|
const source = query2 ? searchAgentWorkspaceActions(AGENT_WORKSPACE_CATEGORIES, query2).map((result2) => ({ category: result2.category, action: result2.action })) : allWorkspaceActions();
|
|
880250
880936
|
return source.filter((entry) => !categoryId || entry.category.id === categoryId).slice(0, limit3).map((entry) => describeWorkspaceAction(entry.category, entry.action, { includeEditor, editorContext }));
|
|
880251
880937
|
}
|
|
880252
880938
|
function findWorkspaceAction(args2) {
|
|
880253
|
-
const actionId =
|
|
880254
|
-
const categoryId =
|
|
880939
|
+
const actionId = readString56(args2.actionId || args2.query);
|
|
880940
|
+
const categoryId = readString56(args2.categoryId || args2.category);
|
|
880255
880941
|
if (!actionId)
|
|
880256
880942
|
return null;
|
|
880257
880943
|
return allWorkspaceActions().find((entry) => {
|
|
@@ -880261,12 +880947,12 @@ function findWorkspaceAction(args2) {
|
|
|
880261
880947
|
}) ?? null;
|
|
880262
880948
|
}
|
|
880263
880949
|
function listCommands(commandRegistry, args2) {
|
|
880264
|
-
const query2 =
|
|
880265
|
-
const limit3 =
|
|
880950
|
+
const query2 = readString56(args2.query);
|
|
880951
|
+
const limit3 = readLimit10(args2.limit, 200);
|
|
880266
880952
|
return commandRegistry.list().filter((command8) => commandMatches(command8, query2)).sort((a4, b3) => a4.name.localeCompare(b3.name)).slice(0, limit3).map(describeCommand);
|
|
880267
880953
|
}
|
|
880268
880954
|
function requireConfirmedAction(args2, action2) {
|
|
880269
|
-
const explicitUserRequest =
|
|
880955
|
+
const explicitUserRequest = readString56(args2.explicitUserRequest);
|
|
880270
880956
|
if (!explicitUserRequest)
|
|
880271
880957
|
return `${action2} requires explicitUserRequest with the user's exact request or a short faithful summary.`;
|
|
880272
880958
|
if (args2.confirm !== true)
|
|
@@ -880274,7 +880960,7 @@ function requireConfirmedAction(args2, action2) {
|
|
|
880274
880960
|
return null;
|
|
880275
880961
|
}
|
|
880276
880962
|
function commandFromArgs(args2) {
|
|
880277
|
-
const rawCommand =
|
|
880963
|
+
const rawCommand = readString56(args2.command);
|
|
880278
880964
|
if (rawCommand) {
|
|
880279
880965
|
const parsed = parseSlashCommand(rawCommand);
|
|
880280
880966
|
if (!parsed.name)
|
|
@@ -880284,7 +880970,7 @@ function commandFromArgs(args2) {
|
|
|
880284
880970
|
args: parsed.args
|
|
880285
880971
|
};
|
|
880286
880972
|
}
|
|
880287
|
-
const commandName =
|
|
880973
|
+
const commandName = readString56(args2.commandName).replace(/^\//, "");
|
|
880288
880974
|
if (!commandName)
|
|
880289
880975
|
return null;
|
|
880290
880976
|
const commandArgs = readStringArray12(args2.args);
|
|
@@ -880334,7 +881020,7 @@ function missingRequiredEditorFields(editor, fields) {
|
|
|
880334
881020
|
return editor.fields.filter((field) => field.required && !readField(field.id).trim()).map((field) => field.id);
|
|
880335
881021
|
}
|
|
880336
881022
|
async function runWorkspaceEditorAction(deps, action2, editor, args2) {
|
|
880337
|
-
const fields =
|
|
881023
|
+
const fields = readFieldMap3(args2.fields);
|
|
880338
881024
|
const missing = missingRequiredEditorFields(editor, fields);
|
|
880339
881025
|
if (missing.length > 0) {
|
|
880340
881026
|
return output7({
|
|
@@ -880472,106 +881158,13 @@ function createAgentHarnessTool(deps) {
|
|
|
880472
881158
|
name: "agent_harness",
|
|
880473
881159
|
description: [
|
|
880474
881160
|
"Discover and operate the GoodVibes Agent harness from the main conversation.",
|
|
880475
|
-
"Use this tool to inspect Agent workspace actions, built-in panels, top-level CLI mirrors, slash commands with policy metadata, model tools, connected-host capabilities, and Agent settings, or to invoke a workspace action/command through the same in-process command registry the user uses in the TUI.",
|
|
880476
|
-
"Discovery modes are read-only. Setting writes, resets, slash command invocation, and workspace action invocation require confirm:true plus explicitUserRequest.",
|
|
881161
|
+
"Use this tool to inspect Agent workspace actions, built-in panels, top-level CLI mirrors, UI surfaces, keybindings, slash commands with policy metadata, model tools, connected-host capabilities, and Agent settings, or to invoke a workspace action/command through the same in-process command registry the user uses in the TUI.",
|
|
881162
|
+
"Discovery modes are read-only. Setting/keybinding writes, resets, UI routing, slash command invocation, and workspace action invocation require confirm:true plus explicitUserRequest.",
|
|
880477
881163
|
"This tool preserves Agent product boundaries: connected-host lifecycle and listener posture stay externally owned, connected-host mode reports allowed and blocked route families, and secret-backed settings store raw values through the secret manager while config receives only a secret reference."
|
|
880478
881164
|
].join(" "),
|
|
880479
881165
|
parameters: {
|
|
880480
881166
|
type: "object",
|
|
880481
|
-
properties:
|
|
880482
|
-
mode: {
|
|
880483
|
-
type: "string",
|
|
880484
|
-
enum: MODES,
|
|
880485
|
-
description: "Harness operation to perform."
|
|
880486
|
-
},
|
|
880487
|
-
query: {
|
|
880488
|
-
type: "string",
|
|
880489
|
-
description: "Search text for command, setting, or tool catalogs."
|
|
880490
|
-
},
|
|
880491
|
-
command: {
|
|
880492
|
-
type: "string",
|
|
880493
|
-
description: 'Full slash command string for mode run_command, for example "/settings get provider.model". In cli_command mode this may also hold a top-level CLI string such as "goodvibes-agent status --json".'
|
|
880494
|
-
},
|
|
880495
|
-
cliCommand: {
|
|
880496
|
-
type: "string",
|
|
880497
|
-
description: 'Top-level CLI command string for mode cli_command, for example "goodvibes-agent status --json" or "profiles list". This mode is read-only metadata/parse inspection.'
|
|
880498
|
-
},
|
|
880499
|
-
commandName: {
|
|
880500
|
-
type: "string",
|
|
880501
|
-
description: "Slash command root without the leading slash for mode command or run_command, or a top-level CLI command token for cli_command."
|
|
880502
|
-
},
|
|
880503
|
-
args: {
|
|
880504
|
-
type: "array",
|
|
880505
|
-
items: { type: "string" },
|
|
880506
|
-
description: "Slash command argument tokens for mode run_command when commandName is used."
|
|
880507
|
-
},
|
|
880508
|
-
categoryId: {
|
|
880509
|
-
type: "string",
|
|
880510
|
-
description: "Agent workspace category id for workspace action filtering."
|
|
880511
|
-
},
|
|
880512
|
-
panelId: {
|
|
880513
|
-
type: "string",
|
|
880514
|
-
description: "Built-in panel id for panel or open_panel modes."
|
|
880515
|
-
},
|
|
880516
|
-
actionId: {
|
|
880517
|
-
type: "string",
|
|
880518
|
-
description: "Agent workspace action id for workspace_action or run_workspace_action."
|
|
880519
|
-
},
|
|
880520
|
-
fields: {
|
|
880521
|
-
type: "object",
|
|
880522
|
-
additionalProperties: { type: "string" },
|
|
880523
|
-
description: "Field values for run_workspace_action when the workspace action opens an editor form."
|
|
880524
|
-
},
|
|
880525
|
-
recordId: {
|
|
880526
|
-
type: "string",
|
|
880527
|
-
description: "Selected Agent-local record id for selection-based local workspace operations."
|
|
880528
|
-
},
|
|
880529
|
-
key: {
|
|
880530
|
-
type: "string",
|
|
880531
|
-
description: "Agent setting key for get_setting, set_setting, or reset_setting."
|
|
880532
|
-
},
|
|
880533
|
-
value: {
|
|
880534
|
-
anyOf: [
|
|
880535
|
-
{ type: "string" },
|
|
880536
|
-
{ type: "number" },
|
|
880537
|
-
{ type: "boolean" }
|
|
880538
|
-
],
|
|
880539
|
-
description: "Setting value for set_setting. Strings, booleans, numbers, and enum strings are accepted."
|
|
880540
|
-
},
|
|
880541
|
-
category: {
|
|
880542
|
-
type: "string",
|
|
880543
|
-
description: "Setting category filter such as provider, behavior, tools, ui, tts, permissions, automation, or surfaces."
|
|
880544
|
-
},
|
|
880545
|
-
prefix: {
|
|
880546
|
-
type: "string",
|
|
880547
|
-
description: "Setting key prefix filter such as surfaces.slack."
|
|
880548
|
-
},
|
|
880549
|
-
includeHidden: {
|
|
880550
|
-
type: "boolean",
|
|
880551
|
-
description: "Include settings hidden from the Agent workspace because they are host-owned or non-Agent lifecycle settings."
|
|
880552
|
-
},
|
|
880553
|
-
includeParameters: {
|
|
880554
|
-
type: "boolean",
|
|
880555
|
-
description: "Include model tool JSON schemas in tools mode, or workspace editor field schemas in workspace_actions mode."
|
|
880556
|
-
},
|
|
880557
|
-
limit: {
|
|
880558
|
-
type: "number",
|
|
880559
|
-
description: "Maximum catalog entries to return."
|
|
880560
|
-
},
|
|
880561
|
-
pane: {
|
|
880562
|
-
type: "string",
|
|
880563
|
-
enum: ["top", "bottom"],
|
|
880564
|
-
description: "Preferred panel pane for open_panel when the current shell supports panel routing."
|
|
880565
|
-
},
|
|
880566
|
-
confirm: {
|
|
880567
|
-
type: "boolean",
|
|
880568
|
-
description: "Required true for set_setting, reset_setting, run_command, open_panel, and mutating run_workspace_action calls after an explicit user request."
|
|
880569
|
-
},
|
|
880570
|
-
explicitUserRequest: {
|
|
880571
|
-
type: "string",
|
|
880572
|
-
description: "Exact user request or faithful short summary authorizing a setting mutation or slash command invocation."
|
|
880573
|
-
}
|
|
880574
|
-
},
|
|
881167
|
+
properties: AGENT_HARNESS_PARAMETER_PROPERTIES,
|
|
880575
881168
|
required: ["mode"],
|
|
880576
881169
|
additionalProperties: false
|
|
880577
881170
|
},
|
|
@@ -880588,6 +881181,9 @@ function createAgentHarnessTool(deps) {
|
|
|
880588
881181
|
cliCommands: totalHarnessCliCommands(),
|
|
880589
881182
|
blockedCliCommandTokens: blockedHarnessCliCommandTokens(),
|
|
880590
881183
|
panels: totalHarnessPanels(deps.commandContext),
|
|
881184
|
+
uiSurfaces: totalHarnessUiSurfaces(),
|
|
881185
|
+
shortcuts: totalHarnessShortcuts(deps.commandContext),
|
|
881186
|
+
keybindings: totalHarnessKeybindings(deps.commandContext),
|
|
880591
881187
|
commands: deps.commandRegistry.list().length,
|
|
880592
881188
|
settings: deps.commandContext.platform.configManager.getSchema().length,
|
|
880593
881189
|
workspaceCategories: AGENT_WORKSPACE_CATEGORIES.length,
|
|
@@ -880596,6 +881192,8 @@ function createAgentHarnessTool(deps) {
|
|
|
880596
881192
|
modelAccess: {
|
|
880597
881193
|
cliCommands: 'Use mode:"cli_commands" and mode:"cli_command" to inspect package CLI mirrors and their preferred in-process model routes. CLI modes are discovery-only.',
|
|
880598
881194
|
panels: 'Use mode:"panels" and mode:"panel" to inspect built-in panel catalog/open state; use mode:"open_panel" with confirm:true plus explicitUserRequest to route a visible panel/workspace change.',
|
|
881195
|
+
uiSurfaces: 'Use mode:"ui_surfaces" and mode:"ui_surface" to inspect modal/overlay/picker/workspace surfaces; use mode:"open_ui_surface" with confirm:true plus explicitUserRequest to route visible UI navigation.',
|
|
881196
|
+
shortcuts: 'Use mode:"shortcuts" to inspect fixed shortcuts plus configurable keybindings. Use mode:"set_keybinding" and mode:"reset_keybinding" with confirm:true plus explicitUserRequest to edit the same config file the user edits.',
|
|
880599
881197
|
slashCommands: 'Use mode:"commands" and mode:"command" to inspect; use mode:"run_command" with confirm:true plus explicitUserRequest to execute.',
|
|
880600
881198
|
workspace: 'Use mode:"workspace_actions" to list and mode:"workspace_action" for editor schemas; set includeParameters:true on workspace_actions to inline editor schemas.',
|
|
880601
881199
|
settings: 'Use mode:"settings", mode:"get_setting", mode:"set_setting", and mode:"reset_setting".',
|
|
@@ -880630,7 +881228,7 @@ function createAgentHarnessTool(deps) {
|
|
|
880630
881228
|
}
|
|
880631
881229
|
if (args2.mode === "panel") {
|
|
880632
881230
|
const panel = describeHarnessPanel(deps.commandContext, args2);
|
|
880633
|
-
return panel ? output7(panel) : error52(`Unknown panel ${
|
|
881231
|
+
return panel ? output7(panel) : error52(`Unknown panel ${readString56(args2.panelId || args2.query) || "<missing>"}.`);
|
|
880634
881232
|
}
|
|
880635
881233
|
if (args2.mode === "open_panel") {
|
|
880636
881234
|
const confirmationError2 = requireConfirmedAction(args2, "Panel routing");
|
|
@@ -880638,12 +881236,46 @@ function createAgentHarnessTool(deps) {
|
|
|
880638
881236
|
return error52(confirmationError2);
|
|
880639
881237
|
return output7(openHarnessPanel(deps.commandContext, args2));
|
|
880640
881238
|
}
|
|
881239
|
+
if (args2.mode === "ui_surfaces") {
|
|
881240
|
+
const surfaces2 = listHarnessUiSurfaces(deps.commandContext, args2);
|
|
881241
|
+
return output7({ surfaces: surfaces2, returned: surfaces2.length, total: totalHarnessUiSurfaces() });
|
|
881242
|
+
}
|
|
881243
|
+
if (args2.mode === "ui_surface") {
|
|
881244
|
+
const surface = describeHarnessUiSurface(deps.commandContext, args2);
|
|
881245
|
+
return surface ? output7(surface) : error52(`Unknown UI surface ${readString56(args2.surfaceId || args2.query) || "<missing>"}.`);
|
|
881246
|
+
}
|
|
881247
|
+
if (args2.mode === "open_ui_surface") {
|
|
881248
|
+
const confirmationError2 = requireConfirmedAction(args2, "UI surface routing");
|
|
881249
|
+
if (confirmationError2)
|
|
881250
|
+
return error52(confirmationError2);
|
|
881251
|
+
return output7(openHarnessUiSurface(deps.commandContext, args2));
|
|
881252
|
+
}
|
|
881253
|
+
if (args2.mode === "shortcuts")
|
|
881254
|
+
return output7(listHarnessShortcuts(deps.commandContext, args2));
|
|
881255
|
+
if (args2.mode === "keybindings")
|
|
881256
|
+
return output7(listHarnessKeybindings(deps.commandContext, args2));
|
|
881257
|
+
if (args2.mode === "keybinding") {
|
|
881258
|
+
const binding = describeHarnessKeybinding(deps.commandContext, args2);
|
|
881259
|
+
return binding ? output7(binding) : error52(`Unknown keybinding action ${readString56(args2.actionId || args2.key || args2.query) || "<missing>"}.`);
|
|
881260
|
+
}
|
|
881261
|
+
if (args2.mode === "set_keybinding") {
|
|
881262
|
+
const confirmationError2 = requireConfirmedAction(args2, "Keybinding mutation");
|
|
881263
|
+
if (confirmationError2)
|
|
881264
|
+
return error52(confirmationError2);
|
|
881265
|
+
return output7(setHarnessKeybinding(deps.commandContext, args2));
|
|
881266
|
+
}
|
|
881267
|
+
if (args2.mode === "reset_keybinding") {
|
|
881268
|
+
const confirmationError2 = requireConfirmedAction(args2, "Keybinding reset");
|
|
881269
|
+
if (confirmationError2)
|
|
881270
|
+
return error52(confirmationError2);
|
|
881271
|
+
return output7(resetHarnessKeybinding(deps.commandContext, args2));
|
|
881272
|
+
}
|
|
880641
881273
|
if (args2.mode === "commands") {
|
|
880642
881274
|
const commands3 = listCommands(deps.commandRegistry, args2);
|
|
880643
881275
|
return output7({ commands: commands3, returned: commands3.length, total: deps.commandRegistry.list().length });
|
|
880644
881276
|
}
|
|
880645
881277
|
if (args2.mode === "command") {
|
|
880646
|
-
const name51 =
|
|
881278
|
+
const name51 = readString56(args2.commandName).replace(/^\//, "");
|
|
880647
881279
|
const command8 = name51 ? deps.commandRegistry.get(name51) : null;
|
|
880648
881280
|
return command8 ? output7(describeCommand(command8)) : error52(`Unknown slash command /${name51 || "<missing>"}.`);
|
|
880649
881281
|
}
|
|
@@ -880651,16 +881283,16 @@ function createAgentHarnessTool(deps) {
|
|
|
880651
881283
|
return runCommand2(deps, args2);
|
|
880652
881284
|
if (args2.mode === "settings") {
|
|
880653
881285
|
const settings = listHarnessSettings(deps.commandContext.platform.configManager, {
|
|
880654
|
-
category:
|
|
880655
|
-
prefix:
|
|
880656
|
-
query:
|
|
881286
|
+
category: readString56(args2.category) || undefined,
|
|
881287
|
+
prefix: readString56(args2.prefix) || undefined,
|
|
881288
|
+
query: readString56(args2.query) || undefined,
|
|
880657
881289
|
includeHidden: args2.includeHidden === true,
|
|
880658
|
-
limit:
|
|
881290
|
+
limit: readLimit10(args2.limit, 100)
|
|
880659
881291
|
});
|
|
880660
881292
|
return output7({ settings, returned: settings.length, policy: settingsPolicySummary() });
|
|
880661
881293
|
}
|
|
880662
881294
|
if (args2.mode === "get_setting") {
|
|
880663
|
-
const key =
|
|
881295
|
+
const key = readString56(args2.key);
|
|
880664
881296
|
const setting = getHarnessSetting(deps.commandContext.platform.configManager, key);
|
|
880665
881297
|
return setting ? output7(setting) : error52(`Unknown setting ${key || "<missing>"}.`);
|
|
880666
881298
|
}
|
|
@@ -880670,7 +881302,7 @@ function createAgentHarnessTool(deps) {
|
|
|
880670
881302
|
return error52(confirmationError2);
|
|
880671
881303
|
if (args2.value === undefined)
|
|
880672
881304
|
return error52("set_setting requires value.");
|
|
880673
|
-
const key =
|
|
881305
|
+
const key = readString56(args2.key);
|
|
880674
881306
|
const result2 = await setHarnessSetting(deps.commandContext.platform.configManager, deps.commandContext.platform.secretsManager, key, args2.value);
|
|
880675
881307
|
return output7(result2);
|
|
880676
881308
|
}
|
|
@@ -880678,7 +881310,7 @@ function createAgentHarnessTool(deps) {
|
|
|
880678
881310
|
const confirmationError2 = requireConfirmedAction(args2, "Setting reset");
|
|
880679
881311
|
if (confirmationError2)
|
|
880680
881312
|
return error52(confirmationError2);
|
|
880681
|
-
const key =
|
|
881313
|
+
const key = readString56(args2.key);
|
|
880682
881314
|
const result2 = await resetHarnessSetting(deps.commandContext.platform.configManager, deps.commandContext.platform.secretsManager, key);
|
|
880683
881315
|
return output7(result2);
|
|
880684
881316
|
}
|
|
@@ -880695,7 +881327,7 @@ function createAgentHarnessTool(deps) {
|
|
|
880695
881327
|
if (args2.mode === "workspace_action") {
|
|
880696
881328
|
const found = findWorkspaceAction(args2);
|
|
880697
881329
|
const editorContext = buildWorkspaceEditorContext(deps.commandContext, args2);
|
|
880698
|
-
return found ? output7(describeWorkspaceAction(found.category, found.action, { includeEditor: true, editorContext })) : error52(`Unknown Agent workspace action ${
|
|
881330
|
+
return found ? output7(describeWorkspaceAction(found.category, found.action, { includeEditor: true, editorContext })) : error52(`Unknown Agent workspace action ${readString56(args2.actionId || args2.query) || "<missing>"}.`);
|
|
880699
881331
|
}
|
|
880700
881332
|
if (args2.mode === "run_workspace_action")
|
|
880701
881333
|
return runWorkspaceAction(deps, args2);
|
|
@@ -882518,7 +883150,7 @@ function mergeFeatureFlagConfigValue(config6, key, value) {
|
|
|
882518
883150
|
|
|
882519
883151
|
// src/runtime/onboarding/verify.ts
|
|
882520
883152
|
init_config8();
|
|
882521
|
-
import { existsSync as
|
|
883153
|
+
import { existsSync as existsSync83 } from "fs";
|
|
882522
883154
|
import { join as join98 } from "path";
|
|
882523
883155
|
function getNow(deps) {
|
|
882524
883156
|
return deps.clock?.() ?? Date.now();
|
|
@@ -882600,7 +883232,7 @@ function verifyAuthOperation(_deps, operation) {
|
|
|
882600
883232
|
}
|
|
882601
883233
|
function verifyCreateAgentProfileOperation(deps, operation) {
|
|
882602
883234
|
const resolution2 = resolveAgentRuntimeProfileHome(deps.shellPaths.homeDirectory, operation.name);
|
|
882603
|
-
const ok3 =
|
|
883235
|
+
const ok3 = existsSync83(join98(resolution2.homeDirectory, "profile.json"));
|
|
882604
883236
|
return {
|
|
882605
883237
|
id: `agent-profile:${resolution2.id}`,
|
|
882606
883238
|
status: ok3 ? "pass" : "fail",
|
|
@@ -882698,22 +883330,22 @@ async function verifyOnboardingRequest(deps, request2) {
|
|
|
882698
883330
|
}
|
|
882699
883331
|
|
|
882700
883332
|
// src/runtime/onboarding/apply-file-helpers.ts
|
|
882701
|
-
import { existsSync as
|
|
882702
|
-
import { dirname as
|
|
883333
|
+
import { existsSync as existsSync84, mkdirSync as mkdirSync68, readFileSync as readFileSync90, unlinkSync as unlinkSync11, writeFileSync as writeFileSync59 } from "fs";
|
|
883334
|
+
import { dirname as dirname67 } from "path";
|
|
882703
883335
|
function isPlainObject3(value) {
|
|
882704
883336
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
882705
883337
|
}
|
|
882706
883338
|
function readJsonObject(path7) {
|
|
882707
|
-
if (!
|
|
883339
|
+
if (!existsSync84(path7))
|
|
882708
883340
|
return {};
|
|
882709
|
-
const parsed = JSON.parse(
|
|
883341
|
+
const parsed = JSON.parse(readFileSync90(path7, "utf-8"));
|
|
882710
883342
|
if (!isPlainObject3(parsed))
|
|
882711
883343
|
throw new Error(`Expected an object JSON payload at ${path7}.`);
|
|
882712
883344
|
return parsed;
|
|
882713
883345
|
}
|
|
882714
883346
|
function writeJsonObject(path7, payload) {
|
|
882715
|
-
|
|
882716
|
-
|
|
883347
|
+
mkdirSync68(dirname67(path7), { recursive: true });
|
|
883348
|
+
writeFileSync59(path7, `${JSON.stringify(payload, null, 2)}
|
|
882717
883349
|
`, "utf-8");
|
|
882718
883350
|
}
|
|
882719
883351
|
function setNestedValue(root, key, value) {
|
|
@@ -882734,16 +883366,16 @@ function setNestedValue(root, key, value) {
|
|
|
882734
883366
|
}
|
|
882735
883367
|
function restoreFile(path7, previous, reload) {
|
|
882736
883368
|
if (previous === null) {
|
|
882737
|
-
if (
|
|
883369
|
+
if (existsSync84(path7))
|
|
882738
883370
|
unlinkSync11(path7);
|
|
882739
883371
|
} else {
|
|
882740
|
-
|
|
882741
|
-
|
|
883372
|
+
mkdirSync68(dirname67(path7), { recursive: true });
|
|
883373
|
+
writeFileSync59(path7, previous, "utf-8");
|
|
882742
883374
|
}
|
|
882743
883375
|
reload?.();
|
|
882744
883376
|
}
|
|
882745
883377
|
function snapshotFileRollback(path7, reload) {
|
|
882746
|
-
const previous =
|
|
883378
|
+
const previous = existsSync84(path7) ? readFileSync90(path7, "utf-8") : null;
|
|
882747
883379
|
return () => restoreFile(path7, previous, reload);
|
|
882748
883380
|
}
|
|
882749
883381
|
async function runRollbacks(rollbacks) {
|
|
@@ -882862,7 +883494,7 @@ function validateCreateAgentProfileOperation(deps, operation) {
|
|
|
882862
883494
|
if (name51.length === 0)
|
|
882863
883495
|
throw new Error("Agent profile name is required.");
|
|
882864
883496
|
const resolution2 = resolveAgentRuntimeProfileHome(deps.shellPaths.homeDirectory, name51);
|
|
882865
|
-
if (
|
|
883497
|
+
if (existsSync85(resolution2.homeDirectory)) {
|
|
882866
883498
|
throw new Error(`Agent profile already exists: ${resolution2.id}`);
|
|
882867
883499
|
}
|
|
882868
883500
|
const templateId = operation.templateId?.trim();
|
|
@@ -882874,7 +883506,7 @@ function validateSelectAgentProfileOperation(deps, operation) {
|
|
|
882874
883506
|
if (name51.length === 0)
|
|
882875
883507
|
throw new Error("Agent profile name is required.");
|
|
882876
883508
|
const resolution2 = resolveAgentRuntimeProfileHome(deps.shellPaths.homeDirectory, name51);
|
|
882877
|
-
if (!
|
|
883509
|
+
if (!existsSync85(resolution2.homeDirectory)) {
|
|
882878
883510
|
throw new Error(`Agent profile does not exist: ${resolution2.id}`);
|
|
882879
883511
|
}
|
|
882880
883512
|
}
|
|
@@ -882982,7 +883614,7 @@ async function buildSecretRollbackAction(deps, operation) {
|
|
|
882982
883614
|
throw new Error(`Secret storage locations for ${scope} scope are unavailable.`);
|
|
882983
883615
|
const snapshots = locations.map((location) => ({
|
|
882984
883616
|
path: location.path,
|
|
882985
|
-
previous:
|
|
883617
|
+
previous: existsSync85(location.path) ? readFileSync91(location.path, "utf-8") : null
|
|
882986
883618
|
}));
|
|
882987
883619
|
return () => {
|
|
882988
883620
|
for (const snapshot of snapshots)
|
|
@@ -883016,7 +883648,7 @@ async function buildRollbackAction(deps, operation) {
|
|
|
883016
883648
|
if (operation.kind === "create-agent-profile") {
|
|
883017
883649
|
const resolution2 = resolveAgentRuntimeProfileHome(deps.shellPaths.homeDirectory, operation.name);
|
|
883018
883650
|
return () => {
|
|
883019
|
-
if (
|
|
883651
|
+
if (existsSync85(resolution2.homeDirectory))
|
|
883020
883652
|
rmSync10(resolution2.homeDirectory, { recursive: true, force: true });
|
|
883021
883653
|
};
|
|
883022
883654
|
}
|
|
@@ -883352,8 +883984,8 @@ async function applyOnboardingRequest(deps, request2) {
|
|
|
883352
883984
|
};
|
|
883353
883985
|
}
|
|
883354
883986
|
// src/runtime/onboarding/markers.ts
|
|
883355
|
-
import { existsSync as
|
|
883356
|
-
import { dirname as
|
|
883987
|
+
import { existsSync as existsSync86, mkdirSync as mkdirSync69, readFileSync as readFileSync92, writeFileSync as writeFileSync60 } from "fs";
|
|
883988
|
+
import { dirname as dirname68 } from "path";
|
|
883357
883989
|
var ONBOARDING_CHECK_MARKER_FILE = "onboarding-checked.json";
|
|
883358
883990
|
function resolveMarkerPath(shellPaths3, scope) {
|
|
883359
883991
|
return scope === "project" ? shellPaths3.resolveProjectPath(GOODVIBES_AGENT_SURFACE_ROOT, ONBOARDING_CHECK_MARKER_FILE) : shellPaths3.resolveUserPath(GOODVIBES_AGENT_SURFACE_ROOT, ONBOARDING_CHECK_MARKER_FILE);
|
|
@@ -883396,10 +884028,10 @@ function getOnboardingCheckMarkerPath(shellPaths3, scope = "user") {
|
|
|
883396
884028
|
}
|
|
883397
884029
|
function readOnboardingCheckMarker(shellPaths3, scope = "user") {
|
|
883398
884030
|
const path7 = resolveMarkerPath(shellPaths3, scope);
|
|
883399
|
-
if (!
|
|
884031
|
+
if (!existsSync86(path7))
|
|
883400
884032
|
return buildMissingMarkerState(scope, path7);
|
|
883401
884033
|
try {
|
|
883402
|
-
const parsed = JSON.parse(
|
|
884034
|
+
const parsed = JSON.parse(readFileSync92(path7, "utf-8"));
|
|
883403
884035
|
if (!isCheckMarkerPayload(parsed)) {
|
|
883404
884036
|
return buildParseErrorState(scope, path7, "Invalid onboarding check marker payload.");
|
|
883405
884037
|
}
|
|
@@ -883435,13 +884067,13 @@ function writeOnboardingCheckMarker(shellPaths3, options = {}) {
|
|
|
883435
884067
|
...options.mode ? { mode: options.mode } : {},
|
|
883436
884068
|
...options.workspaceRoot ? { workspaceRoot: options.workspaceRoot } : {}
|
|
883437
884069
|
};
|
|
883438
|
-
|
|
883439
|
-
|
|
884070
|
+
mkdirSync69(dirname68(path7), { recursive: true });
|
|
884071
|
+
writeFileSync60(path7, `${JSON.stringify(payload, null, 2)}
|
|
883440
884072
|
`, "utf-8");
|
|
883441
884073
|
return readOnboardingCheckMarker(shellPaths3, scope);
|
|
883442
884074
|
}
|
|
883443
884075
|
// src/input/handler-content-actions.ts
|
|
883444
|
-
import { existsSync as
|
|
884076
|
+
import { existsSync as existsSync87, lstatSync as lstatSync3, readFileSync as readFileSync93, readdirSync as readdirSync22 } from "fs";
|
|
883445
884077
|
import { basename as basename6, relative as relative15 } from "path";
|
|
883446
884078
|
var MARKER_REGEX = /\[(TEXT|IMAGE): [^\]]+\]/g;
|
|
883447
884079
|
var IMAGE_PREFIXES = [
|
|
@@ -883501,7 +884133,7 @@ function readContextFileBlock(reference, projectRoot) {
|
|
|
883501
884133
|
logger.debug("expandPrompt: context reference rejected", { reference, error: summarizeError(error53) });
|
|
883502
884134
|
return null;
|
|
883503
884135
|
}
|
|
883504
|
-
if (!
|
|
884136
|
+
if (!existsSync87(resolvedPath3))
|
|
883505
884137
|
return null;
|
|
883506
884138
|
const stat6 = lstatSync3(resolvedPath3);
|
|
883507
884139
|
const label = escapeContextAttribute(relative15(projectRoot, resolvedPath3) || basename6(resolvedPath3));
|
|
@@ -883520,14 +884152,14 @@ function readContextFileBlock(reference, projectRoot) {
|
|
|
883520
884152
|
if (stat6.size > MAX_CONTEXT_FILE_BYTES) {
|
|
883521
884153
|
return [
|
|
883522
884154
|
`<context-file path="${label}" truncated="true" bytes="${stat6.size}">`,
|
|
883523
|
-
|
|
884155
|
+
readFileSync93(resolvedPath3, "utf-8").slice(0, MAX_CONTEXT_FILE_BYTES),
|
|
883524
884156
|
"</context-file>"
|
|
883525
884157
|
].join(`
|
|
883526
884158
|
`);
|
|
883527
884159
|
}
|
|
883528
884160
|
return [
|
|
883529
884161
|
`<context-file path="${label}" bytes="${stat6.size}">`,
|
|
883530
|
-
|
|
884162
|
+
readFileSync93(resolvedPath3, "utf-8"),
|
|
883531
884163
|
"</context-file>"
|
|
883532
884164
|
].join(`
|
|
883533
884165
|
`);
|
|
@@ -883584,8 +884216,8 @@ function registerPaste(state4, content, projectRoot) {
|
|
|
883584
884216
|
if (IMAGE_EXTENSIONS2.some((ext) => trimmed2.toLowerCase().endsWith(ext))) {
|
|
883585
884217
|
try {
|
|
883586
884218
|
const resolvedPath3 = resolveAndValidatePath(trimmed2, projectRoot);
|
|
883587
|
-
if (
|
|
883588
|
-
const data =
|
|
884219
|
+
if (existsSync87(resolvedPath3)) {
|
|
884220
|
+
const data = readFileSync93(resolvedPath3);
|
|
883589
884221
|
const base644 = data.toString("base64");
|
|
883590
884222
|
const ext = trimmed2.slice(trimmed2.lastIndexOf("."));
|
|
883591
884223
|
const mediaType = mediaTypeFromExt(ext);
|
|
@@ -883635,7 +884267,7 @@ function expandPrompt(pasteRegistry, imageRegistry, text, projectRoot) {
|
|
|
883635
884267
|
const filePath = injectMatch[1];
|
|
883636
884268
|
try {
|
|
883637
884269
|
const resolvedPath3 = resolveAndValidatePath(filePath, projectRoot);
|
|
883638
|
-
const content =
|
|
884270
|
+
const content = readFileSync93(resolvedPath3, "utf-8");
|
|
883639
884271
|
expanded = expanded.slice(0, injectMatch.index) + content + expanded.slice(injectMatch.index + injectMatch[0].length);
|
|
883640
884272
|
injectRegex.lastIndex = injectMatch.index + content.length;
|
|
883641
884273
|
} catch (err2) {
|
|
@@ -892908,7 +893540,7 @@ function handleProfilePickerToken(state4, token) {
|
|
|
892908
893540
|
}
|
|
892909
893541
|
|
|
892910
893542
|
// src/input/handler-picker-routes.ts
|
|
892911
|
-
import { readFileSync as
|
|
893543
|
+
import { readFileSync as readFileSync94 } from "fs";
|
|
892912
893544
|
|
|
892913
893545
|
// src/renderer/model-picker-overlay.ts
|
|
892914
893546
|
var MODEL_PICKER_CHROME_LINES = 7;
|
|
@@ -893200,7 +893832,7 @@ function handleFilePickerToken(state4, token) {
|
|
|
893200
893832
|
throw new Error("working directory is unavailable");
|
|
893201
893833
|
}
|
|
893202
893834
|
const resolvedPath3 = resolveAndValidatePath(selected, projectRoot);
|
|
893203
|
-
const data =
|
|
893835
|
+
const data = readFileSync94(resolvedPath3);
|
|
893204
893836
|
const base644 = data.toString("base64");
|
|
893205
893837
|
const mediaType = state4.mediaTypeFromExt(ext);
|
|
893206
893838
|
const filename = selected.split("/").pop() ?? selected;
|
|
@@ -898914,7 +899546,7 @@ function wireShellUiOpeners(options) {
|
|
|
898914
899546
|
}
|
|
898915
899547
|
|
|
898916
899548
|
// src/cli/entrypoint.ts
|
|
898917
|
-
import { existsSync as
|
|
899549
|
+
import { existsSync as existsSync89 } from "fs";
|
|
898918
899550
|
import { join as join101 } from "path";
|
|
898919
899551
|
// src/cli/status.ts
|
|
898920
899552
|
function yesNo3(value) {
|
|
@@ -899160,12 +899792,12 @@ function renderOnboardingCliStatus(options) {
|
|
|
899160
899792
|
`);
|
|
899161
899793
|
}
|
|
899162
899794
|
// src/cli/external-runtime.ts
|
|
899163
|
-
import { existsSync as
|
|
899795
|
+
import { existsSync as existsSync88, readFileSync as readFileSync95 } from "fs";
|
|
899164
899796
|
import { join as join100 } from "path";
|
|
899165
899797
|
function isRecord43(value) {
|
|
899166
899798
|
return Boolean(value) && typeof value === "object" && !Array.isArray(value);
|
|
899167
899799
|
}
|
|
899168
|
-
function
|
|
899800
|
+
function readString57(record2, key) {
|
|
899169
899801
|
const value = record2?.[key];
|
|
899170
899802
|
return typeof value === "string" ? value : null;
|
|
899171
899803
|
}
|
|
@@ -899176,10 +899808,10 @@ function resolveBaseUrl2(configManager) {
|
|
|
899176
899808
|
}
|
|
899177
899809
|
function readOperatorToken2(homeDirectory) {
|
|
899178
899810
|
const path7 = join100(homeDirectory, ".goodvibes", "daemon", "operator-tokens.json");
|
|
899179
|
-
if (!
|
|
899811
|
+
if (!existsSync88(path7))
|
|
899180
899812
|
return { token: null, path: path7 };
|
|
899181
899813
|
try {
|
|
899182
|
-
const parsed = JSON.parse(
|
|
899814
|
+
const parsed = JSON.parse(readFileSync95(path7, "utf-8"));
|
|
899183
899815
|
const token = isRecord43(parsed) && typeof parsed.token === "string" ? parsed.token : null;
|
|
899184
899816
|
return { token, path: path7 };
|
|
899185
899817
|
} catch {
|
|
@@ -899216,7 +899848,7 @@ async function inspectCliExternalRuntime(options) {
|
|
|
899216
899848
|
try {
|
|
899217
899849
|
const status = await fetchJson2(`${baseUrl}/status`, token.token, timeoutMs);
|
|
899218
899850
|
const statusRecord = isRecord43(status.body) ? status.body : {};
|
|
899219
|
-
const version6 =
|
|
899851
|
+
const version6 = readString57(statusRecord, "version") ?? "unknown";
|
|
899220
899852
|
const compatible = status.ok && version6 === SDK_VERSION;
|
|
899221
899853
|
if (!status.ok) {
|
|
899222
899854
|
return {
|
|
@@ -899671,11 +900303,11 @@ async function prepareShellCliRuntime(argv, roots, binary2 = "goodvibes-agent")
|
|
|
899671
900303
|
onboardingMarkers,
|
|
899672
900304
|
auth: {
|
|
899673
900305
|
userStorePath,
|
|
899674
|
-
userStorePresent:
|
|
900306
|
+
userStorePresent: existsSync89(userStorePath),
|
|
899675
900307
|
bootstrapCredentialPath,
|
|
899676
|
-
bootstrapCredentialPresent:
|
|
900308
|
+
bootstrapCredentialPresent: existsSync89(bootstrapCredentialPath),
|
|
899677
900309
|
operatorTokenPath,
|
|
899678
|
-
operatorTokenPresent:
|
|
900310
|
+
operatorTokenPresent: existsSync89(operatorTokenPath)
|
|
899679
900311
|
},
|
|
899680
900312
|
service,
|
|
899681
900313
|
externalRuntime,
|