@lambdacurry/arbor 0.22.30 → 0.22.31

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.
Files changed (2) hide show
  1. package/dist/arbor.js +19 -11
  2. package/package.json +1 -1
package/dist/arbor.js CHANGED
@@ -2,7 +2,7 @@
2
2
  // package.json
3
3
  var package_default = {
4
4
  name: "@lambdacurry/arbor",
5
- version: "0.22.30",
5
+ version: "0.22.31",
6
6
  description: "The Arbor CLI — a shared workspace for people and agents. The human + headless-agent write path over Arbor's guarded operation surface.",
7
7
  keywords: [
8
8
  "agents",
@@ -10130,7 +10130,7 @@ Arbor's MCP is the collaboration and durable-knowledge surface. Configure, autho
10130
10130
 
10131
10131
  Run \`arbor help\` (or read the MCP tool list) for the exact command/flags — those stay generated from the live action surface, so they're always current.`;
10132
10132
  var ARBOR_SKILL_MARKDOWN = renderArborSkill(ORIENTATION);
10133
- var COMPUTER_ORIENTATION = `Long Computer work returns a processId handle — do not hold one tool call for a full test or build. \`computer_exec\` runs a command; if the result is still running, observe it with \`computer_process_read\`; read a truncated continuation only when you need more output. Finish and suspend preserve unread terminal output internally, with original process IDs/cursors recoverable for 30 days. Do not chain \`pnpm test && pnpm build\` in one exec; split steps or pass \`background:true\`. The CLI polls only while the process is silent unless \`--no-wait\`; it returns the first bounded output page instead of concatenating continuation pages into one agent context.
10133
+ var COMPUTER_ORIENTATION = `Long Computer work returns a processId handle — do not hold one tool call for a full test or build. \`computer_exec\` runs a command; if the result is still running, observe it with \`computer_process_read\`; read a truncated continuation only when you need more output. Finish and suspend preserve unread terminal output internally, with original process IDs/cursors recoverable for 30 days. Do not chain \`pnpm test && pnpm build\` in one exec; split steps or pass \`background:true\`. An explicit waitForTerminalMs uses one server wait and canonical output page; otherwise the CLI polls only while the process is silent unless \`--no-wait\`. It never concatenates continuation pages into one agent context.
10134
10134
 
10135
10135
  Arbor Computer is the complete software execution platform attached to Arbor's durable collaboration graph. It configures project environments, executes and verifies work, packages and releases Apps, and preserves reviewable evidence; it does not schedule agents or replace Arbor collaboration.
10136
10136
 
@@ -10954,16 +10954,17 @@ var ACTION_DEFINITIONS = [
10954
10954
  {
10955
10955
  name: "computer_exec",
10956
10956
  title: "Run a command",
10957
- description: "Run a shell command in runId with ambient GitHub authorization and /workspace/.local/bin on PATH; timeout kills the process. Observe running work with computer_process_read, use nextCursor for a truncated output page when needed, and finish without draining; after a missed response use computer_run_receipt.operations[].operationId with computer_process_read instead of repeating the mutation.",
10957
+ description: "Run a shell command in runId with ambient GitHub authorization; timeout kills the process. Use waitForTerminalMs for immediate or bounded native observation, then continue with computer_process_read and nextCursor for a truncated output page; background is mutually exclusive, and after response loss read computer_run_receipt.operations[].operationId instead of repeating the mutation.",
10958
10958
  inputSchema: {
10959
10959
  computerSessionId: string2().optional().describe("legacy alternative to runId: a computerSessionId on that Computer, cms_…; required unless runId is supplied"),
10960
10960
  command: string2().min(1).describe("the shell command to run"),
10961
10961
  runId: string2().optional().describe("route this command according to this Run execution placement, run_… (from computer_run_start)"),
10962
10962
  cwd: string2().optional().describe("working directory under /workspace, or under the run; omit to use defaultCwd"),
10963
10963
  timeout: number2().int().min(1000).max(1800000).optional().describe("process kill deadline in milliseconds, from 1,000 through 1,800,000 — not the RPC hold"),
10964
- background: boolean2().optional().describe("start the process and return immediately without the short RPC wait"),
10965
- activityLabel: string2().min(1).max(COMPUTER_RUN_ACTIVITY_LABEL_MAX).optional().describe("short human-readable label for run-scoped background work; Arbor records this label instead of the raw command or output"),
10966
- activityKind: literal("verification").optional().describe("mark a labeled run-scoped background command as a verification check; its provider-observed terminal result is recorded as verification.finished"),
10964
+ background: boolean2().optional().describe("start the process and return immediately without the short RPC wait; mutually exclusive with waitForTerminalMs"),
10965
+ waitForTerminalMs: number2().int().min(0).max(45000).optional().describe("explicit terminal-observation window from 0 through 45,000 milliseconds; 0 returns immediately, a positive value returns one canonical output page when the native wait ends or expires, and descendants may keep the result running; mutually exclusive with background"),
10966
+ activityLabel: string2().min(1).max(COMPUTER_RUN_ACTIVITY_LABEL_MAX).optional().describe("short human-readable label for retained run-scoped work selected by background or waitForTerminalMs; Arbor records this label instead of the raw command or output"),
10967
+ activityKind: literal("verification").optional().describe("mark labeled retained run-scoped work as a verification check; its provider-observed terminal result is recorded as verification.finished"),
10967
10968
  strict: boolean2().optional().describe("fail on the first unhandled command or pipeline failure; defaults to true, set false only for intentional best-effort execution")
10968
10969
  },
10969
10970
  surfaces: ["computer-mcp", "computer-cli"],
@@ -10973,13 +10974,14 @@ var ACTION_DEFINITIONS = [
10973
10974
  {
10974
10975
  name: "computer_process_read",
10975
10976
  title: "Read a background process",
10976
- description: "Read original process output using nextCursor; preserved output stays readable for 30 days after preservation, including repeated cursors after finish/suspend, without provider wake. Live reads retain the latest observation; a later timeout remains unknown/unsafe with its age, and Arbor settles the durable operation only from terminal or exact provider-absence proof.",
10977
+ description: "Read process output with nextCursor; preserved bytes remain available for 30 days after preservation, including repeated cursors after finish/suspend, without provider wake. waitForTerminalMs adds one bounded native observation and page; expiry or descendants may still run, transport failure stays unknown/unsafe, and Arbor settles the durable operation only from terminal or exact absence proof.",
10977
10978
  inputSchema: {
10978
10979
  computerSessionId: string2().optional().describe("legacy alternative to runId: a computerSessionId on that Computer, cms_…; required unless runId is supplied"),
10979
10980
  runId: string2().optional().describe("the Run that owns this process, if it was started inside a Run"),
10980
10981
  processId: string2().min(1).describe("the processId returned by background exec, or matching computer_run_receipt.operations[].operationId for recovered foreground Run work, proc_…"),
10981
10982
  cursor: string2().optional().describe("continue after nextCursor from the prior result; omit to read from the beginning"),
10982
- maxBytes: number2().int().min(1024).max(65536).optional().describe("maximum combined output bytes to return; default 4,096, opt up only when needed")
10983
+ maxBytes: number2().int().min(1024).max(65536).optional().describe("maximum combined output bytes to return; default 4,096, opt up only when needed"),
10984
+ waitForTerminalMs: number2().int().min(0).max(45000).optional().describe("use one native terminal-observation window up to this many milliseconds, then return one canonical output page; 0 is immediate, surviving descendants may remain running, and omission preserves the current read behavior")
10983
10985
  },
10984
10986
  surfaces: ["computer-mcp", "computer-cli"],
10985
10987
  toolset: "loop",
@@ -14149,7 +14151,7 @@ Alias: \`arbor ${aliases[0]}\` (the tool-name form) resolves to this same comman
14149
14151
  Aliases: ${aliases.map((alias) => `\`arbor ${alias}\``).join(", ")} (tool-name forms) resolve to this same command.` : "";
14150
14152
  const heading = `${commandWords(action)}${aliases.length === 1 ? ` (alias: ${aliases[0]})` : aliases.length > 1 ? ` (aliases: ${aliases.join(", ")})` : ""}`;
14151
14153
  const waitLines = action.name === "computer_exec" ? [
14152
- " --no-wait [<boolean>] [optional] — return a running processId immediately instead of polling computer_process_read"
14154
+ " --no-wait [<boolean>] [optional] — return a running processId immediately instead of polling computer_process_read; mutually exclusive with --wait-for-terminal-ms"
14153
14155
  ] : [];
14154
14156
  return `${heading} — ${action.description}
14155
14157
 
@@ -14178,7 +14180,7 @@ function commandCatalog() {
14178
14180
  kind: "boolean",
14179
14181
  required: false,
14180
14182
  acceptsFile: false,
14181
- description: "return a running processId immediately instead of polling computer_process_read"
14183
+ description: "return a running processId immediately instead of polling computer_process_read; mutually exclusive with --wait-for-terminal-ms"
14182
14184
  }
14183
14185
  ] : []
14184
14186
  ]
@@ -14240,6 +14242,12 @@ async function runObjectVerb(positionals, flags, ctx) {
14240
14242
  delete inputFlags.json;
14241
14243
  }
14242
14244
  const input = buildInput(action.inputSchema, inputFlags, commandWords(action));
14245
+ if (action.name === "computer_exec" && flags["no-wait"] !== undefined && input.waitForTerminalMs !== undefined) {
14246
+ throw new UsageError("--no-wait and --wait-for-terminal-ms are mutually exclusive", {
14247
+ reason: "validation.invalid_value",
14248
+ field: "waitForTerminalMs"
14249
+ });
14250
+ }
14243
14251
  if (action.name === "app_request" && input.json !== undefined) {
14244
14252
  if (input.body !== undefined) {
14245
14253
  throw new UsageError("--json and --body are mutually exclusive", {
@@ -14261,7 +14269,7 @@ async function runObjectVerb(positionals, flags, ctx) {
14261
14269
  `, ctx);
14262
14270
  }
14263
14271
  let value = await action.run(httpExecutor, input);
14264
- if (action.name === "computer_exec" && !truthyFlag(flags["no-wait"])) {
14272
+ if (action.name === "computer_exec" && !truthyFlag(flags["no-wait"]) && input.waitForTerminalMs === undefined) {
14265
14273
  value = await waitForComputerExec(httpExecutor, input, value, ctx);
14266
14274
  }
14267
14275
  emitData(shapeActionOutput(action.name, value, input), action.name, ctx);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lambdacurry/arbor",
3
- "version": "0.22.30",
3
+ "version": "0.22.31",
4
4
  "description": "The Arbor CLI — a shared workspace for people and agents. The human + headless-agent write path over Arbor's guarded operation surface.",
5
5
  "keywords": [
6
6
  "agents",