@agntn/harnesses 0.3.1 → 0.4.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,4 +1,4 @@
1
- import { A as AvailableModel, F as HarnessId, G as PathCandidate, J as PromptTemplateSyncTarget, L as HarnessInvocationModes, N as HarnessCapabilities, P as HarnessDetection, Q as StorageDescriptor, W as McpServerConfig, X as ResolvedPaths, Z as SkillsSyncTarget, _ as McpConfigListing, j as EnvOverride, n as SkillsSyncReport, o as PromptSyncReport, p as AgentsSyncReport, y as SyncReport } from "./_chunks/skills-sync.mjs";
1
+ import { $ as StorageDescriptor, F as HarnessDetection, G as McpServerConfig, I as HarnessId, K as PathCandidate, M as EnvOverride, P as HarnessCapabilities, Q as SkillsSyncTarget, R as HarnessInvocationModes, Y as PromptTemplateSyncTarget, Z as ResolvedPaths, _ as McpConfigListing, b as SyncReport, j as AvailableModel, n as SkillsSyncReport, o as PromptSyncReport, p as AgentsSyncReport } from "./_chunks/skills-sync.mjs";
2
2
  import { n as HARNESS_INFO_MAX_ITEMS } from "./_chunks/tool-schemas.mjs";
3
3
  //#region src/tool-operations.d.ts
4
4
  /** Text for the model plus details for the harness, shared by every tool surface. */
@@ -11,12 +11,18 @@ export interface ToolResult<Details> {
11
11
  /** Set when the tool could not answer. */
12
12
  isError?: boolean;
13
13
  }
14
- /** Install state of one harness on this machine. */
14
+ /** Install state of one harness on this machine, plus the runs harnesses_run takes for it. */
15
15
  export interface HarnessStatus {
16
16
  id: HarnessId;
17
17
  name: string;
18
18
  installed: boolean;
19
19
  version: string | null;
20
+ /** Takes `tools: false`, an advisor without tools. */
21
+ advisor: boolean;
22
+ /** Takes `tools: true` with `readOnly: true`; false while the installed CLI is too old for it. */
23
+ readOnly: boolean;
24
+ /** Takes `tools: true`, the full agent. */
25
+ agent: boolean;
20
26
  }
21
27
  /** Every registered harness with its install state, as scanned by {@link detectHarnesses}. */
22
28
  export interface HarnessListing {
@@ -31,6 +37,7 @@ export interface HarnessMetadata {
31
37
  invocationModes: HarnessInvocationModes;
32
38
  modelListing: boolean;
33
39
  modelSelection: boolean;
40
+ effortSelection: boolean;
34
41
  config: PathCandidate[];
35
42
  sessions: PathCandidate[];
36
43
  instructions: PathCandidate[];
@@ -64,7 +71,7 @@ export declare const RUN_DEFAULT_TIMEOUT_SECONDS = 600;
64
71
  /** The run tool's per-stream cap: harness output is unbounded, model context is not. */
65
72
  export declare const RUN_MAX_OUTPUT_CHARS = 8000;
66
73
  /**
67
- * Scans every registered harness for its binaries and version.
74
+ * Scans every registered harness for its binaries and version, next to the modes it runs in.
68
75
  *
69
76
  * @returns {ToolResult<HarnessListing>} The complete installation listing.
70
77
  */
@@ -110,6 +117,8 @@ export interface RunOptions {
110
117
  cwd?: string;
111
118
  /** Harness-native model id or selector. */
112
119
  model?: string;
120
+ /** Reasoning effort in the harness's own words; rejected where `effortArgs` is missing. */
121
+ effort?: string;
113
122
  /** Wall-clock budget in seconds; defaults to {@link RUN_DEFAULT_TIMEOUT_SECONDS}. */
114
123
  timeoutSeconds?: number;
115
124
  /** Cancel the owned command through the host request signal. */
@@ -128,6 +137,7 @@ export interface RunOutcome {
128
137
  /** Expanded arguments; the model's text keeps "{prompt}" instead, it wrote the prompt itself. */
129
138
  args: string[];
130
139
  model?: string;
140
+ effort?: string;
131
141
  structured: boolean;
132
142
  tools: boolean;
133
143
  readOnly: boolean;
@@ -158,7 +168,7 @@ export interface RunFailure {
158
168
  *
159
169
  * Tool use defaults to a native advisor without tools invocation. Harnesses that
160
170
  * cannot disable tools reject that mode; setting `tools` selects their full
161
- * agent invocation. `model` is translated through the harness-specific recipe.
171
+ * agent invocation. `model` and `effort` are translated through the harness-specific recipe.
162
172
  * This layer also closes stdin, enforces the timeout, caps the echoed output,
163
173
  * and leaves the prompt out of the echoed invocation.
164
174
  *
@@ -1 +1 @@
1
- {"version":3,"file":"tool-operations.d.mts","names":[],"sources":["../src/tool-operations.ts"],"mappings":";;;;iBAiDiB,WAAW;EAC1B,SAAS;IAAQ;IAAc;;EAC/B,SAAS;;EAET;;;iBAIe;EACf,IAAI;EACJ;EACA;EACA;;;iBAIe;EACf,WAAW;;;iBAII;EACf,IAAI;EACJ;EACA;EACA,cAAc;EACd,iBAAiB;EACjB;EACA;EACA,QAAQ;EACR,UAAU;EACV,cAAc;EACd,QAAQ;EACR,kBAAkB;EAClB,UAAU;EACV,iBAAiB;EACjB,0BAA0B;EAC1B,OAAO;EACP,MAAM;EACN,cAAc;EACd,aAAa;EACb,WAAW;EACX,UAAU;;;iBAIK;EACf;EACA,OAAO;;;iBAIQ;EACf;;;YAIU,oBAAoB,kBAAkB;;YAGtC,qBAAqB,oBAAoB,sBAAsB;;qBAM9D;;qBAGA;;;;;;wBAoKG,mBAAmB,WAAW;;wBAyG9B,YAAY,aAAa,WAAW;;wBAEpC,YACd,yBACC,WAAW,sBAAsB;wBACpB,YAAY,oCAAoC,WAAW;;iBA2B1D;EACf;EACA;;EAEA;;EAEA,SAAS;;;iBAIM;EACf,IAAI;EACJ;EACA;EACA;EACA,QAAQ;EACR;EACA;EACA;;EAEA;EACA;;;;;;;;;wBAUoB,kBACpB,YACA,UAAS,gBACR,QAAQ,WAAW,gBAAgB;;iBAsDrB;EACf;;EAEA;;EAEA;;EAEA,SAAS;;EAET;;EAEA;;EAEA;;;iBAIe;EACf,IAAI;EACJ;;EAEA;EACA;EACA;EACA;EACA;EACA;EACA;EACA;;EAEA;EACA;EACA;;;iBAIe;EACf;EACA,QAAQ;;EAER,kBAAkB;;EAElB;IAAU;IAAmB;;IAAsB;;;;;;;;;;;;;;;;;wBAyB/B,WACpB,YACA,gBACA,UAAS,aACR,QAAQ,WAAW,aAAa;;iBAkClB;EACf,WAAW;IAAQ,IAAI;IAAW,SAAS;;;;iBAY5B;EACf,IAAI;EACJ;EACA;;;iBAIe;EACf;EACA,YAAY;EACZ;EACA;EACA,MAAM;EACN;EACA,UAAU;;;;;;;;wBASI,kBAAkB,QAAQ,kBAAkB;;;;;;;wBAmB5C,QAAQ,cAAc,WAAW,aAAa;;;;;;;;;wBAgD9C,OACd,YACA,QAAQ,iBACR,6BACC,WAAW,cAAc;;;;;;;;;wBAeZ,UACd,YACA,cACA,6BACC,WAAW,cAAc;;;;;;;wBAaZ,QAAQ,cAAc,WAAW,aAAa;;;;;;;;wBA+B9C,WAAW,aAAa,kBAAgB,WAAW,mBAAmB;;;;;;;;wBAgCtE,YAAY,aAAa,kBAAgB,WAAW,mBAAmB;;;;;;;;wBAsBvE,WAAW,aAAa,kBAAgB,WAAW,mBAAmB"}
1
+ {"version":3,"file":"tool-operations.d.mts","names":[],"sources":["../src/tool-operations.ts"],"mappings":";;;;iBAkDiB,WAAW;EAC1B,SAAS;IAAQ;IAAc;;EAC/B,SAAS;;EAET;;;iBAIe;EACf,IAAI;EACJ;EACA;EACA;;EAEA;;EAEA;;EAEA;;;iBAIe;EACf,WAAW;;;iBAII;EACf,IAAI;EACJ;EACA;EACA,cAAc;EACd,iBAAiB;EACjB;EACA;EACA;EACA,QAAQ;EACR,UAAU;EACV,cAAc;EACd,QAAQ;EACR,kBAAkB;EAClB,UAAU;EACV,iBAAiB;EACjB,0BAA0B;EAC1B,OAAO;EACP,MAAM;EACN,cAAc;EACd,aAAa;EACb,WAAW;EACX,UAAU;;;iBAIK;EACf;EACA,OAAO;;;iBAIQ;EACf;;;YAIU,oBAAoB,kBAAkB;;YAGtC,qBAAqB,oBAAoB,sBAAsB;;qBAM9D;;qBAGA;;;;;;wBA+KG,mBAAmB,WAAW;;wBAmH9B,YAAY,aAAa,WAAW;;wBAEpC,YACd,yBACC,WAAW,sBAAsB;wBACpB,YAAY,oCAAoC,WAAW;;iBA2B1D;EACf;EACA;;EAEA;;EAEA,SAAS;;;iBAIM;EACf,IAAI;EACJ;EACA;EACA;EACA,QAAQ;EACR;EACA;EACA;;EAEA;EACA;;;;;;;;;wBAUoB,kBACpB,YACA,UAAS,gBACR,QAAQ,WAAW,gBAAgB;;iBAqDrB;EACf;;EAEA;;EAEA;;EAEA;;EAEA,SAAS;;EAET;;EAEA;;EAEA;;;iBAIe;EACf,IAAI;EACJ;;EAEA;EACA;EACA;EACA;EACA;EACA;EACA;EACA;EACA;;EAEA;EACA;EACA;;;iBAIe;EACf;EACA,QAAQ;;EAER,kBAAkB;;EAElB;IAAU;IAAmB;;IAAsB;;;;;;;;;;;;;;;;;wBAyB/B,WACpB,YACA,gBACA,UAAS,aACR,QAAQ,WAAW,aAAa;;iBAyClB;EACf,WAAW;IAAQ,IAAI;IAAW,SAAS;;;;iBAY5B;EACf,IAAI;EACJ;EACA;;;iBAIe;EACf;EACA,YAAY;EACZ;EACA;EACA,MAAM;EACN;EACA,UAAU;;;;;;;;wBASI,kBAAkB,QAAQ,kBAAkB;;;;;;;wBAmB5C,QAAQ,cAAc,WAAW,aAAa;;;;;;;;;wBAgD9C,OACd,YACA,QAAQ,iBACR,6BACC,WAAW,cAAc;;;;;;;;;wBAeZ,UACd,YACA,cACA,6BACC,WAAW,cAAc;;;;;;;wBAaZ,QAAQ,cAAc,WAAW,aAAa;;;;;;;;wBA+B9C,WAAW,aAAa,kBAAgB,WAAW,mBAAmB;;;;;;;;wBAgCtE,YAAY,aAAa,kBAAgB,WAAW,mBAAmB;;;;;;;;wBAsBvE,WAAW,aAAa,kBAAgB,WAAW,mBAAmB"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@agntn/harnesses",
3
- "version": "0.3.1",
3
+ "version": "0.4.1",
4
4
  "description": "Metadata registry for AI coding harnesses: binaries, configs, sessions, and capabilities.",
5
5
  "homepage": "https://harnesses.agntn.dev",
6
6
  "bugs": "https://github.com/agntn/harnesses/issues",
@@ -79,7 +79,7 @@
79
79
  }
80
80
  },
81
81
  "engines": {
82
- "node": ">=24"
82
+ "node": ">=26"
83
83
  },
84
84
  "omp": {
85
85
  "extensions": [
@@ -67,13 +67,13 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
67
67
  pi.registerTool({
68
68
  name: "harnesses_detect",
69
69
  label: HARNESS_TOOL_LABELS.harnesses_detect,
70
- description: "List every known AI coding harness with its install state and version",
70
+ description:
71
+ "List every known AI coding harness with its install state, version and the harnesses_run modes it takes: advisor (tools=false), readOnly (tools=true with readOnly=true) and agent (tools=true)",
71
72
  parameters: schemas.detect,
72
73
  approval: HARNESS_TOOL_APPROVALS.harnesses_detect,
73
74
  async execute(_toolCallId, _params): Promise<AgentToolResult<HarnessTools.HarnessListing>> {
74
75
  const { detectHarnesses } = await loadToolOperations();
75
- const { content, details } = detectHarnesses();
76
- return { content, details };
76
+ return detectHarnesses();
77
77
  },
78
78
  ...statusRenderers("harnesses_detect"),
79
79
  });
@@ -90,8 +90,7 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
90
90
  params: HarnessSchemas.InfoParams,
91
91
  ): Promise<AgentToolResult<HarnessTools.HarnessInfoDetails>> {
92
92
  const { harnessInfo } = await loadToolOperations();
93
- const { content, details } = harnessInfo(params.id);
94
- return { content, details };
93
+ return harnessInfo(params.id);
95
94
  },
96
95
  ...statusRenderers("harnesses_info"),
97
96
  });
@@ -109,24 +108,12 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
109
108
  signal,
110
109
  ): Promise<AgentToolResult<HarnessTools.ModelsOutcome | HarnessTools.RunFailure>> {
111
110
  const { listHarnessModels } = await loadToolOperations();
112
- const { content, details, isError } = await listHarnessModels(params.id, {
111
+ return listHarnessModels(params.id, {
113
112
  search: params.search,
114
113
  cwd: params.cwd,
115
114
  timeoutSeconds: params.timeoutSeconds,
116
115
  signal,
117
116
  });
118
- if (isError) {
119
- const message =
120
- "error" in details
121
- ? details.error
122
- : details.aborted
123
- ? `Harness ${details.id} model listing aborted`
124
- : details.timedOut
125
- ? `Harness ${details.id} model listing timed out`
126
- : details.stderr || `Harness ${details.id} exited with code ${details.exitCode}`;
127
- throw new Error(message);
128
- }
129
- return { content, details };
130
117
  },
131
118
  ...statusRenderers("harnesses_models"),
132
119
  });
@@ -135,7 +122,7 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
135
122
  name: "harnesses_run",
136
123
  label: HARNESS_TOOL_LABELS.harnesses_run,
137
124
  description:
138
- "Run one prompt through a harness. Always choose tools explicitly. Add readOnly when tools is true to require native read-only enforcement, or use tools false for an advisor without tools.",
125
+ "Run one prompt through a harness. Always choose tools explicitly. Add readOnly when tools is true to require native read-only enforcement, or use tools false for an advisor without tools. harnesses_detect shows which modes each harness takes.",
139
126
  parameters: schemas.run,
140
127
  approval: HARNESS_TOOL_APPROVALS.harnesses_run,
141
128
  async execute(
@@ -144,25 +131,16 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
144
131
  signal,
145
132
  ): Promise<AgentToolResult<HarnessTools.RunOutcome | HarnessTools.RunFailure>> {
146
133
  const { runHarness } = await loadToolOperations();
147
- const { content, details, isError } = await runHarness(params.id, params.prompt, {
134
+ return runHarness(params.id, params.prompt, {
148
135
  cwd: params.cwd,
149
136
  model: params.model,
137
+ effort: params.effort,
150
138
  timeoutSeconds: params.timeoutSeconds,
151
139
  signal,
152
140
  structured: params.structured,
153
141
  tools: params.tools,
154
142
  readOnly: params.readOnly,
155
143
  });
156
- if (isError) {
157
- if ("error" in details) throw new Error(details.error);
158
- const message =
159
- content[0]?.text ??
160
- (details.timedOut
161
- ? `Harness ${details.id} timed out`
162
- : details.stderr || `Harness ${details.id} exited with code ${details.exitCode}`);
163
- throw new Error(message);
164
- }
165
- return { content, details };
166
144
  },
167
145
  ...statusRenderers("harnesses_run"),
168
146
  });
@@ -179,8 +157,7 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
179
157
  params: HarnessSchemas.McpListParams,
180
158
  ): Promise<AgentToolResult<HarnessTools.McpListing | HarnessTools.UnknownHarness>> {
181
159
  const { mcpList } = await loadToolOperations();
182
- const { content, details } = mcpList(params.id);
183
- return { content, details };
160
+ return mcpList(params.id);
184
161
  },
185
162
  ...statusRenderers("harnesses_mcp_list"),
186
163
  });
@@ -197,8 +174,7 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
197
174
  params: HarnessSchemas.McpAddParams,
198
175
  ): Promise<AgentToolResult<HarnessTools.McpMutation | HarnessTools.RunFailure>> {
199
176
  const { mcpAdd } = await loadToolOperations();
200
- const { content, details } = mcpAdd(params.id, params, params.scope ?? "user");
201
- return { content, details };
177
+ return mcpAdd(params.id, params, params.scope ?? "user");
202
178
  },
203
179
  ...statusRenderers("harnesses_mcp_add"),
204
180
  });
@@ -215,8 +191,7 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
215
191
  params: HarnessSchemas.McpSyncParams,
216
192
  ): Promise<AgentToolResult<HarnessTools.SyncReport | HarnessTools.RunFailure>> {
217
193
  const { mcpSync } = await loadToolOperations();
218
- const { content, details } = mcpSync(params.id);
219
- return { content, details };
194
+ return mcpSync(params.id);
220
195
  },
221
196
  ...statusRenderers("harnesses_mcp_sync"),
222
197
  });
@@ -233,8 +208,7 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
233
208
  params: HarnessSchemas.AgentsSyncParams,
234
209
  ): Promise<AgentToolResult<HarnessTools.AgentsSyncReport | HarnessTools.RunFailure>> {
235
210
  const { agentsSync } = await loadToolOperations();
236
- const { content, details } = agentsSync(params.id, params.check === true);
237
- return { content, details };
211
+ return agentsSync(params.id, params.check === true);
238
212
  },
239
213
  ...statusRenderers("harnesses_agents_sync"),
240
214
  });
@@ -251,8 +225,7 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
251
225
  params: Readonly<HarnessSchemas.PromptsSyncParams>,
252
226
  ): Promise<AgentToolResult<HarnessTools.PromptSyncReport | HarnessTools.RunFailure>> {
253
227
  const { promptsSync } = await loadToolOperations();
254
- const { content, details, isError } = promptsSync(params.id, params.check === true);
255
- return { content, details, isError };
228
+ return promptsSync(params.id, params.check === true);
256
229
  },
257
230
  ...statusRenderers("harnesses_prompts_sync"),
258
231
  });
@@ -269,8 +242,7 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
269
242
  params: Readonly<HarnessSchemas.SkillsSyncParams>,
270
243
  ): Promise<AgentToolResult<HarnessTools.SkillsSyncReport | HarnessTools.RunFailure>> {
271
244
  const { skillsSync } = await loadToolOperations();
272
- const { content, details, isError } = skillsSync(params.id, params.check === true);
273
- return { content, details, isError };
245
+ return skillsSync(params.id, params.check === true);
274
246
  },
275
247
  ...statusRenderers("harnesses_skills_sync"),
276
248
  });
@@ -287,8 +259,7 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
287
259
  params: HarnessSchemas.McpRemoveParams,
288
260
  ): Promise<AgentToolResult<HarnessTools.McpMutation | HarnessTools.RunFailure>> {
289
261
  const { mcpRemove } = await loadToolOperations();
290
- const { content, details } = mcpRemove(params.id, params.name, params.scope ?? "user");
291
- return { content, details };
262
+ return mcpRemove(params.id, params.name, params.scope ?? "user");
292
263
  },
293
264
  ...statusRenderers("harnesses_mcp_remove"),
294
265
  });
@@ -79,10 +79,13 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
79
79
  pi.registerTool({
80
80
  name: "harnesses_detect",
81
81
  label: HARNESS_TOOL_LABELS.harnesses_detect,
82
- description: "List every known AI coding harness with its install state and version",
83
- promptSnippet: "Use harnesses_detect to see which AI coding harnesses are installed.",
82
+ description:
83
+ "List every known AI coding harness with its install state, version and the harnesses_run modes it takes: advisor (tools=false), readOnly (tools=true with readOnly=true) and agent (tools=true)",
84
+ promptSnippet:
85
+ "Use harnesses_detect to see which AI coding harnesses are installed and how each one runs.",
84
86
  promptGuidelines: [
85
87
  "The scan checks binaries on PATH. Versions come from native metadata or the CLI.",
88
+ "advisor, readOnly and agent say whether harnesses_run takes tools false, tools true with readOnly, or tools true for that harness.",
86
89
  ],
87
90
  parameters: schemas.detect,
88
91
  ...statusRenderers("harnesses_detect"),
@@ -146,13 +149,13 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
146
149
  name: "harnesses_run",
147
150
  label: HARNESS_TOOL_LABELS.harnesses_run,
148
151
  description:
149
- "Run one prompt through an AI coding harness's normalized non-interactive invocation, optionally selecting a model, and return its output",
152
+ "Run one prompt through an AI coding harness's normalized non-interactive invocation, optionally selecting a model and reasoning effort, and return its output",
150
153
  promptSnippet: "Use harnesses_run to delegate one prompt to another installed coding harness.",
151
154
  promptGuidelines: [
152
155
  "Always choose tools explicitly. Set true whenever the task needs harness tools, including Grok native X search.",
153
156
  "Add readOnly when tools is true to require native read-only enforcement. Unsupported harnesses reject it instead of widening access.",
154
157
  "Set tools false only for an advisor without tools. It never silently falls back to a full agent.",
155
- "An unsupported mode returns an explicit retry when the alternate mode is available.",
158
+ "An unsupported mode returns an explicit retry when the alternate mode is available. harnesses_detect shows the modes up front.",
156
159
  "Output is capped for context; long runs stop at the timeout.",
157
160
  ],
158
161
  parameters: schemas.run,
@@ -166,6 +169,7 @@ export default function harnessesExtension(pi: ExtensionAPI): void {
166
169
  return runHarness(params.id, params.prompt, {
167
170
  cwd: params.cwd,
168
171
  model: params.model,
172
+ effort: params.effort,
169
173
  timeoutSeconds: params.timeoutSeconds,
170
174
  signal,
171
175
  structured: params.structured,