@brainbase-labs/cli 0.30.0 → 0.31.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. package/README.md +3 -1
  2. package/dist/index.js +50 -12
  3. package/package.json +1 -1
package/README.md CHANGED
@@ -83,7 +83,9 @@ prompt.
83
83
  Idempotency is explicit-only: requests omit the idempotency header unless
84
84
  `--idempotency-key` is supplied. Reuse a key only for an identical retry.
85
85
  Starting a run requires `--yes`; confirming the same plan ID is replay-safe.
86
- Interrupting `run watch` does not cancel the remote run.
86
+ Interrupting `run watch` does not cancel the remote run. A run that MAS pauses
87
+ for billing stops `run watch` with exit code 1; once billing is fixed, run
88
+ `brainbase benchmark run resume <run-id> --yes` to put it back in the queue.
87
89
 
88
90
  Use `brainbase benchmark --help`, `brainbase benchmark run --help`, or
89
91
  `brainbase benchmark <command> --help` for local command help.
package/dist/index.js CHANGED
@@ -36018,7 +36018,7 @@ function padStart(s, n) {
36018
36018
  // package.json
36019
36019
  var package_default = {
36020
36020
  name: "@brainbase-labs/cli",
36021
- version: "0.30.0",
36021
+ version: "0.31.0",
36022
36022
  description: "Pack, share, and install agent templates across harnesses (Claude Code, Codex, ...).",
36023
36023
  type: "module",
36024
36024
  bin: {
@@ -84745,7 +84745,7 @@ class BenchmarkApiClient {
84745
84745
  try {
84746
84746
  responseBody = text3 ? JSON.parse(text3) : null;
84747
84747
  } catch {}
84748
- throw new BenchmarkApiError(redactSensitiveText(apiErrorMessage(responseBody, response.status)), response.status, responseBody, safeCode(responseBody), response.headers.get("x-request-id") ?? response.headers.get("x-correlation-id") ?? undefined);
84748
+ throw new BenchmarkApiError(redactSensitiveText(masApiErrorMessage(responseBody, response.status)), response.status, responseBody, safeCode(responseBody), response.headers.get("x-request-id") ?? response.headers.get("x-correlation-id") ?? undefined);
84749
84749
  }
84750
84750
  if (options.mode === "binary") {
84751
84751
  return {
@@ -84960,6 +84960,11 @@ class BenchmarkApiClient {
84960
84960
  method: "POST"
84961
84961
  });
84962
84962
  }
84963
+ resumeRun(runId) {
84964
+ return this.request(`/runs/${encodeURIComponent(runId)}/resume`, {
84965
+ method: "POST"
84966
+ });
84967
+ }
84963
84968
  listDiagnoses(runId, query = {}) {
84964
84969
  return this.request(`/runs/${encodeURIComponent(runId)}/diagnoses`, {
84965
84970
  query: {
@@ -87345,6 +87350,12 @@ class BenchmarkControlOutput {
87345
87350
  `);
87346
87351
  }
87347
87352
  }
87353
+ hint(text2) {
87354
+ if (this.mode.json || this.mode.jsonl)
87355
+ return;
87356
+ this.writer.stdout(`${text2}
87357
+ `);
87358
+ }
87348
87359
  page(page, all = false) {
87349
87360
  if (this.mode.jsonl) {
87350
87361
  for (const item of page.items)
@@ -87376,6 +87387,7 @@ class BenchmarkControlOutput {
87376
87387
 
87377
87388
  // src/cli/benchmark-control.ts
87378
87389
  var TERMINAL_RUN_STATUSES = new Set(["cancelled", "failed", "succeeded"]);
87390
+ var PAUSED_RUN_STATUS = "paused";
87379
87391
  var MAX_MANIFEST_IMPORT_BYTES = 2 * 1024 * 1024;
87380
87392
  var MAX_CSV_IMPORT_BYTES = 10 * 1024 * 1024;
87381
87393
  var MAX_PAGINATION_PAGES = 1e4;
@@ -87552,7 +87564,7 @@ function commandHelp() {
87552
87564
  "",
87553
87565
  ` ${import_picocolors60.default.cyan("init | list | show | create | validate | pull | push")}`,
87554
87566
  ` ${import_picocolors60.default.cyan("publish | revisions | import | export | archive | restore")}`,
87555
- ` ${import_picocolors60.default.cyan("run plan|start|watch|list|show|cancel")}`,
87567
+ ` ${import_picocolors60.default.cyan("run plan|start|watch|list|show|cancel|resume")}`,
87556
87568
  ` ${import_picocolors60.default.cyan("results | diagnoses | attempt | artifacts | export-results")}`,
87557
87569
  ` ${import_picocolors60.default.cyan("history | baseline show|set|clear")}`,
87558
87570
  "",
@@ -87952,7 +87964,7 @@ function runPlanInput(options, revisionId) {
87952
87964
  revision_id: revisionId,
87953
87965
  variants: variants.length > 0 ? variants.map(parseVariant) : [{ key: "default" }],
87954
87966
  repetitions: integerOption(options.parsed, "repetitions", { min: 1, max: 10 }) ?? 1,
87955
- concurrency: integerOption(options.parsed, "concurrency", { min: 1, max: 10 }) ?? 5
87967
+ concurrency: integerOption(options.parsed, "concurrency", { min: 1, max: 50 }) ?? 5
87956
87968
  };
87957
87969
  if (cases.length > 0)
87958
87970
  input.case_keys = cases;
@@ -87998,7 +88010,15 @@ async function runStart(cwd2, argv, deps) {
87998
88010
  const { client, output } = context(cwd2, "benchmark run start", options, deps);
87999
88011
  output.result(json(await client.confirmRunPlan(planId)));
88000
88012
  }
88001
- async function watchRun(client, output, runId, interval, deps) {
88013
+ function pausedRunHint(runId, run, agentId) {
88014
+ const reason = run.paused_reason;
88015
+ const message = reason && typeof reason === "object" && !Array.isArray(reason) ? reason.message : undefined;
88016
+ const first = typeof message === "string" && message.trim() ? `Run paused: ${message.trim()}` : "Run paused.";
88017
+ const agent = agentId ? ` --agent ${agentId}` : "";
88018
+ return `${first}
88019
+ Resume with: brainbase benchmark run resume ${runId} --yes${agent}`;
88020
+ }
88021
+ async function watchRun(client, output, runId, interval, agentId, deps) {
88002
88022
  let interrupted = false;
88003
88023
  const controller = new AbortController;
88004
88024
  const onInterrupt = () => {
@@ -88020,9 +88040,16 @@ async function watchRun(client, output, runId, interval, deps) {
88020
88040
  const digest2 = output.digest(latest);
88021
88041
  if (digest2 !== previous) {
88022
88042
  const status = typeof latest.status === "string" ? latest.status : "unknown";
88023
- output.event(TERMINAL_RUN_STATUSES.has(status) ? "run.completed" : "run.updated", latest, typeof latest.updated_at === "string" ? latest.updated_at : undefined);
88043
+ const terminal = TERMINAL_RUN_STATUSES.has(status);
88044
+ const paused = status === PAUSED_RUN_STATUS;
88045
+ output.event(terminal ? "run.completed" : paused ? "run.paused" : "run.updated", latest, typeof latest.updated_at === "string" ? latest.updated_at : undefined);
88024
88046
  previous = digest2;
88025
- if (TERMINAL_RUN_STATUSES.has(status)) {
88047
+ if (paused) {
88048
+ output.hint(pausedRunHint(runId, latest, agentId));
88049
+ deps.setExitCode(1);
88050
+ return { run: latest, interrupted: false };
88051
+ }
88052
+ if (terminal) {
88026
88053
  if (status !== "succeeded")
88027
88054
  deps.setExitCode(1);
88028
88055
  return { run: latest, interrupted: false };
@@ -88044,7 +88071,7 @@ async function runWatch(cwd2, argv, deps) {
88044
88071
  const watched = await watchRun(client, output, options.positionals[0], integerOption(options.parsed, "interval", {
88045
88072
  min: 100,
88046
88073
  max: 60000
88047
- }) ?? 2000, deps);
88074
+ }) ?? 2000, options.agent, deps);
88048
88075
  if (options.json) {
88049
88076
  output.result({
88050
88077
  run: watched.run,
@@ -88084,6 +88111,15 @@ async function runCancel(cwd2, argv, deps) {
88084
88111
  const { client, output } = context(cwd2, "benchmark run cancel", options, deps);
88085
88112
  output.result(json(await client.cancelRun(options.positionals[0])));
88086
88113
  }
88114
+ async function runResume(cwd2, argv, deps) {
88115
+ const options = parseControlOptions(argv, ["yes"]);
88116
+ expectPositionals(options.positionals, 1, 1, "brainbase benchmark run resume <run-id>");
88117
+ if (!bool(options.parsed, "yes")) {
88118
+ throw usageError("--yes is required to resume a benchmark run");
88119
+ }
88120
+ const { client, output } = context(cwd2, "benchmark run resume", options, deps);
88121
+ output.result(json(await client.resumeRun(options.positionals[0])));
88122
+ }
88087
88123
  async function runOneShot(cwd2, argv, deps) {
88088
88124
  const options = parseControlOptions(argv, [
88089
88125
  ...RUN_PLAN_OPTIONS,
@@ -88123,7 +88159,7 @@ async function runOneShot(cwd2, argv, deps) {
88123
88159
  const watched = await watchRun(client, output, runId, integerOption(options.parsed, "interval", {
88124
88160
  min: 100,
88125
88161
  max: 60000
88126
- }) ?? 2000, deps);
88162
+ }) ?? 2000, options.agent, deps);
88127
88163
  if (options.json) {
88128
88164
  output.result({
88129
88165
  plan,
@@ -88149,6 +88185,8 @@ async function runRunRouter(cwd2, argv, deps) {
88149
88185
  case "cancel":
88150
88186
  case "stop":
88151
88187
  return await runCancel(cwd2, rest2, deps);
88188
+ case "resume":
88189
+ return await runResume(cwd2, rest2, deps);
88152
88190
  case undefined:
88153
88191
  case "help":
88154
88192
  case "--help":
@@ -88422,10 +88460,10 @@ function commandLevelHelp(sub, argv) {
88422
88460
  if (action === "show") {
88423
88461
  return usage("brainbase benchmark run show <run-id>");
88424
88462
  }
88425
- if (action === "cancel" || action === "stop") {
88463
+ if (action === "cancel" || action === "stop" || action === "resume") {
88426
88464
  return usage(`brainbase benchmark run ${action} <run-id> --yes`);
88427
88465
  }
88428
- return usage("brainbase benchmark run <benchmark-id> --yes [--revision <revision-id>] [--watch] [--idempotency-key <key>]", "brainbase benchmark run plan <benchmark-id> --revision <revision-id>", "brainbase benchmark run start <plan-id> --yes", "brainbase benchmark run watch <run-id> [--interval-ms <n>]", "brainbase benchmark run list [benchmark-id] [--status <status>] [--limit <n>] [--cursor <cursor>] [--all]", "brainbase benchmark run show <run-id>", "brainbase benchmark run cancel <run-id> --yes");
88466
+ return usage("brainbase benchmark run <benchmark-id> --yes [--revision <revision-id>] [--watch] [--idempotency-key <key>]", "brainbase benchmark run plan <benchmark-id> --revision <revision-id>", "brainbase benchmark run start <plan-id> --yes", "brainbase benchmark run watch <run-id> [--interval-ms <n>]", "brainbase benchmark run list [benchmark-id] [--status <status>] [--limit <n>] [--cursor <cursor>] [--all]", "brainbase benchmark run show <run-id>", "brainbase benchmark run cancel <run-id> --yes", "brainbase benchmark run resume <run-id> --yes");
88429
88467
  case "results":
88430
88468
  return usage("brainbase benchmark results <run-id> [--baseline-target <target-id>]");
88431
88469
  case "diagnoses":
@@ -88458,7 +88496,7 @@ function automationCommand(sub, argv) {
88458
88496
  const action = argv[0];
88459
88497
  if (action === "stop")
88460
88498
  return "benchmark run cancel";
88461
- if (action && ["plan", "start", "watch", "list", "show", "cancel"].includes(action)) {
88499
+ if (action && ["plan", "start", "watch", "list", "show", "cancel", "resume"].includes(action)) {
88462
88500
  return `benchmark run ${action}`;
88463
88501
  }
88464
88502
  return "benchmark run";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@brainbase-labs/cli",
3
- "version": "0.30.0",
3
+ "version": "0.31.0",
4
4
  "description": "Pack, share, and install agent templates across harnesses (Claude Code, Codex, ...).",
5
5
  "type": "module",
6
6
  "bin": {