@integrity-labs/agt-cli 0.28.387 → 0.28.388

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/bin/agt.js CHANGED
@@ -40,7 +40,7 @@ import {
40
40
  success,
41
41
  table,
42
42
  warn
43
- } from "../chunk-ZNFB4AKQ.js";
43
+ } from "../chunk-3TKW2SSS.js";
44
44
  import {
45
45
  AnchorSessionClient,
46
46
  CHANNEL_REGISTRY,
@@ -70,7 +70,7 @@ import {
70
70
  renderTemplate,
71
71
  resolveChannels,
72
72
  serializeManifestForSlackCli
73
- } from "../chunk-LAO2CUZU.js";
73
+ } from "../chunk-IJF4W6LC.js";
74
74
  import "../chunk-XWVM4KPK.js";
75
75
 
76
76
  // src/bin/agt.ts
@@ -4829,7 +4829,7 @@ import { execFileSync, execSync } from "child_process";
4829
4829
  import { existsSync as existsSync10, realpathSync as realpathSync2 } from "fs";
4830
4830
  import chalk18 from "chalk";
4831
4831
  import ora16 from "ora";
4832
- var cliVersion = true ? "0.28.387" : "dev";
4832
+ var cliVersion = true ? "0.28.388" : "dev";
4833
4833
  async function fetchLatestVersion() {
4834
4834
  const host2 = getHost();
4835
4835
  if (!host2) return null;
@@ -6001,7 +6001,7 @@ function handleError(err) {
6001
6001
  }
6002
6002
 
6003
6003
  // src/bin/agt.ts
6004
- var cliVersion2 = true ? "0.28.387" : "dev";
6004
+ var cliVersion2 = true ? "0.28.388" : "dev";
6005
6005
  var program = new Command();
6006
6006
  program.name("agt").description("Augmented CLI \u2014 agent provisioning and management").version(cliVersion2).option("--json", "Emit machine-readable JSON output (suppress spinners and colors)").option("--skip-update-check", "Skip the automatic update check on startup");
6007
6007
  program.hook("preAction", async (thisCommand, actionCommand) => {
@@ -25,7 +25,7 @@ import {
25
25
  resolveConnectivityProbe,
26
26
  worseConnectivityOutcome,
27
27
  wrapScheduledTaskPrompt
28
- } from "./chunk-LAO2CUZU.js";
28
+ } from "./chunk-IJF4W6LC.js";
29
29
  import {
30
30
  parsePsRows
31
31
  } from "./chunk-XWVM4KPK.js";
@@ -6184,7 +6184,7 @@ function requireHost() {
6184
6184
  }
6185
6185
 
6186
6186
  // src/lib/api-client.ts
6187
- var agtCliVersion = true ? "0.28.387" : "dev";
6187
+ var agtCliVersion = true ? "0.28.388" : "dev";
6188
6188
  var lastConfigHash = null;
6189
6189
  function setConfigHash(hash) {
6190
6190
  lastConfigHash = hash && hash.length > 0 ? hash : null;
@@ -8638,4 +8638,4 @@ export {
8638
8638
  managerInstallSystemUnitCommand,
8639
8639
  managerUninstallSystemUnitCommand
8640
8640
  };
8641
- //# sourceMappingURL=chunk-ZNFB4AKQ.js.map
8641
+ //# sourceMappingURL=chunk-3TKW2SSS.js.map
@@ -9412,6 +9412,120 @@ function buildPart(p2, redact, maxPartChars) {
9412
9412
  return { kind: "other" };
9413
9413
  }
9414
9414
 
9415
+ // ../../packages/core/dist/provisioning/frameworks/opencode/opencode-run.js
9416
+ var OpencodeRunError = class extends Error {
9417
+ admitted;
9418
+ constructor(message, admitted, options) {
9419
+ super(message, options);
9420
+ this.name = "OpencodeRunError";
9421
+ this.admitted = admitted;
9422
+ }
9423
+ };
9424
+ function runCrossedAdmission(stdout) {
9425
+ for (const line2 of stdout.split("\n")) {
9426
+ const trimmed = line2.trim();
9427
+ if (!trimmed)
9428
+ continue;
9429
+ try {
9430
+ JSON.parse(trimmed);
9431
+ return true;
9432
+ } catch {
9433
+ }
9434
+ }
9435
+ return false;
9436
+ }
9437
+ function buildOpencodeRunArgs(params, opts = {}) {
9438
+ const args = [
9439
+ "run",
9440
+ "--attach",
9441
+ params.serveUrl,
9442
+ "--dir",
9443
+ params.projectDir,
9444
+ "--session",
9445
+ params.sessionID,
9446
+ "--format",
9447
+ "json"
9448
+ ];
9449
+ if (opts.includePasswordArg && params.password) {
9450
+ args.push("-p", params.password);
9451
+ }
9452
+ if (params.model) {
9453
+ args.push("--model", `${params.model.providerID}/${params.model.id}`);
9454
+ }
9455
+ if (params.agent) {
9456
+ args.push("--agent", params.agent);
9457
+ }
9458
+ args.push(params.text);
9459
+ return args;
9460
+ }
9461
+ function parseOpencodeRunReply(stdout) {
9462
+ const parts = [];
9463
+ for (const line2 of stdout.split("\n")) {
9464
+ const trimmed = line2.trim();
9465
+ if (!trimmed)
9466
+ continue;
9467
+ let evt;
9468
+ try {
9469
+ evt = JSON.parse(trimmed);
9470
+ } catch {
9471
+ continue;
9472
+ }
9473
+ const e = evt;
9474
+ if (e?.type === "text" && e.part && e.part.type === "text" && typeof e.part.text === "string") {
9475
+ parts.push(e.part.text);
9476
+ }
9477
+ }
9478
+ const reply = parts.join("").trim();
9479
+ return reply.length > 0 ? reply : null;
9480
+ }
9481
+ function parseOpencodeRunError(stdout) {
9482
+ for (const line2 of stdout.split("\n")) {
9483
+ const trimmed = line2.trim();
9484
+ if (!trimmed)
9485
+ continue;
9486
+ let evt;
9487
+ try {
9488
+ evt = JSON.parse(trimmed);
9489
+ } catch {
9490
+ continue;
9491
+ }
9492
+ const e = evt;
9493
+ if (e?.type === "error") {
9494
+ const msg = e.error?.data?.message;
9495
+ if (typeof msg === "string" && msg.length > 0)
9496
+ return msg;
9497
+ const name = e.error?.name;
9498
+ if (typeof name === "string" && name.length > 0)
9499
+ return name;
9500
+ return "opencode run reported an error event";
9501
+ }
9502
+ }
9503
+ return null;
9504
+ }
9505
+ function parseRunToolCalls(stdout) {
9506
+ const seen = /* @__PURE__ */ new Set();
9507
+ const out = [];
9508
+ for (const line2 of stdout.split("\n")) {
9509
+ const trimmed = line2.trim();
9510
+ if (!trimmed)
9511
+ continue;
9512
+ let evt;
9513
+ try {
9514
+ evt = JSON.parse(trimmed);
9515
+ } catch {
9516
+ continue;
9517
+ }
9518
+ const e = evt;
9519
+ if (e.part && e.part.type === "tool" && typeof e.part.tool === "string") {
9520
+ if (!seen.has(e.part.tool)) {
9521
+ seen.add(e.part.tool);
9522
+ out.push(e.part.tool);
9523
+ }
9524
+ }
9525
+ }
9526
+ return out;
9527
+ }
9528
+
9415
9529
  // ../../packages/core/dist/provisioning/frameworks/opencode/inbound-bridge.js
9416
9530
  var InboundError = class extends Error {
9417
9531
  /** True once `prompt()` has durably admitted the turn. Retry is unsafe. */
@@ -9446,6 +9560,7 @@ var OpencodeInboundBridge = class {
9446
9560
  sessionDefaults;
9447
9561
  delivery;
9448
9562
  awaitReply;
9563
+ runTurn;
9449
9564
  /** conversationKey → sessionID (one session per thread/DM). */
9450
9565
  sessions = /* @__PURE__ */ new Map();
9451
9566
  /** conversationKey → in-flight createSession, so concurrent inbound for the
@@ -9457,6 +9572,10 @@ var OpencodeInboundBridge = class {
9457
9572
  this.sessionDefaults = opts.sessionDefaults;
9458
9573
  this.delivery = opts.delivery ?? "queue";
9459
9574
  this.awaitReply = opts.awaitReply ?? true;
9575
+ this.runTurn = opts.runTurn;
9576
+ if (this.runTurn && this.delivery === "steer") {
9577
+ console.warn("[opencode-bridge] delivery:'steer' is ignored when runTurn is set - opencode run cannot steer an in-flight turn; falling back to queue semantics.");
9578
+ }
9460
9579
  }
9461
9580
  /** Resolve (creating on first use) the opencode session for a conversation. */
9462
9581
  async ensureSession(conversationKey) {
@@ -9506,6 +9625,24 @@ var OpencodeInboundBridge = class {
9506
9625
  cause: err
9507
9626
  });
9508
9627
  }
9628
+ if (this.runTurn) {
9629
+ const runner = this.runTurn;
9630
+ const framed = frameInboundPrompt(msg);
9631
+ const model = this.sessionDefaults?.model ?? null;
9632
+ if (!awaitReply) {
9633
+ void runner({ sessionID, text: framed, model }).catch((err) => {
9634
+ console.error(`[opencode-bridge] fire-and-forget run turn failed for session ${sessionID}:`, err instanceof Error ? err.name : typeof err);
9635
+ });
9636
+ return { status: "admitted", sessionID, admittedSeq: 0 };
9637
+ }
9638
+ try {
9639
+ const { admittedSeq: seq, reply } = await runner({ sessionID, text: framed, model });
9640
+ return { status: "replied", sessionID, admittedSeq: seq, reply };
9641
+ } catch (err) {
9642
+ const admitted = err instanceof OpencodeRunError ? err.admitted : false;
9643
+ throw new InboundError(admitted ? "opencode run turn failed after admission (not retried; avoids duplicate)" : "opencode run turn failed before admission (treated as retryable)", { admitted, sessionID, cause: err });
9644
+ }
9645
+ }
9509
9646
  let admittedSeq;
9510
9647
  try {
9511
9648
  ({ admittedSeq } = await this.client.prompt({
@@ -9982,6 +10119,7 @@ async function execFilePromiseLong(cmd, args, opts) {
9982
10119
 
9983
10120
  // src/lib/opencode-session.ts
9984
10121
  var OPENCODE_BIN = process.env["AGT_OPENCODE_BIN"]?.trim() || "opencode";
10122
+ var OPENCODE_RUN_TIMEOUT_MS = Number(process.env["AGT_OPENCODE_RUN_TIMEOUT_MS"]) || 18e4;
9985
10123
  var sessions = /* @__PURE__ */ new Map();
9986
10124
  var bridges = /* @__PURE__ */ new Map();
9987
10125
  function opencodeTmuxSession(codeName) {
@@ -10181,7 +10319,8 @@ async function startOpencodeSession(config) {
10181
10319
  port: null,
10182
10320
  password: null,
10183
10321
  lastFailureTail: "opencode isolation not implemented (ADR-0047)",
10184
- model: null
10322
+ model: null,
10323
+ projectDir: config.projectDir
10185
10324
  };
10186
10325
  sessions.set(codeName, blocked);
10187
10326
  return blocked;
@@ -10197,7 +10336,9 @@ async function startOpencodeSession(config) {
10197
10336
  // ENG-7931: parse the resolved model from the provisioned opencode.json
10198
10337
  // (config.projectDir IS the provision dir the serve reads) so the bridge can
10199
10338
  // pass it explicitly on session-create + prompt.
10200
- model: readOpencodeModelFromConfigDir(config.projectDir)
10339
+ model: readOpencodeModelFromConfigDir(config.projectDir),
10340
+ // ENG-8032: retained so getBridge can drive turns via `opencode run --dir`.
10341
+ projectDir: config.projectDir
10201
10342
  };
10202
10343
  sessions.set(codeName, session);
10203
10344
  try {
@@ -10315,13 +10456,74 @@ function getBridge(codeName, port, password) {
10315
10456
  if (cached && cached.port === port && cached.password === password) return cached.bridge;
10316
10457
  const client = new HttpOpencodeClient({ baseUrl: baseUrlFor(port), password });
10317
10458
  const model = sessions.get(codeName)?.model ?? null;
10459
+ const projectDir = sessions.get(codeName)?.projectDir ?? null;
10318
10460
  const bridge = new OpencodeInboundBridge({
10319
10461
  client,
10320
- sessionDefaults: model ? { model } : void 0
10462
+ sessionDefaults: model ? { model } : void 0,
10463
+ runTurn: projectDir ? makeRunTurn(codeName, port, password, projectDir) : void 0
10321
10464
  });
10322
10465
  bridges.set(codeName, { port, password, bridge });
10323
10466
  return bridge;
10324
10467
  }
10468
+ function makeRunTurn(codeName, port, password, projectDir) {
10469
+ return ({ sessionID, text, model }) => new Promise((resolve, reject) => {
10470
+ const args = buildOpencodeRunArgs({
10471
+ bin: OPENCODE_BIN,
10472
+ serveUrl: baseUrlFor(port),
10473
+ projectDir,
10474
+ password,
10475
+ sessionID,
10476
+ text,
10477
+ model: model ?? null
10478
+ });
10479
+ const child = spawn(OPENCODE_BIN, args, {
10480
+ cwd: projectDir,
10481
+ // Password off argv (would show in `ps`); it rides the env instead.
10482
+ env: { ...process.env, OPENCODE_SERVER_PASSWORD: password },
10483
+ stdio: ["ignore", "pipe", "pipe"]
10484
+ });
10485
+ let stdout = "";
10486
+ let stderr = "";
10487
+ let settled = false;
10488
+ const finish = (fn) => {
10489
+ if (settled) return;
10490
+ settled = true;
10491
+ clearTimeout(timer);
10492
+ fn();
10493
+ };
10494
+ const fail = (message, cause) => reject(new OpencodeRunError(message, runCrossedAdmission(stdout), { cause }));
10495
+ const timer = setTimeout(() => {
10496
+ finish(() => {
10497
+ try {
10498
+ child.kill("SIGKILL");
10499
+ } catch {
10500
+ }
10501
+ fail(`opencode run timed out after ${OPENCODE_RUN_TIMEOUT_MS}ms`);
10502
+ });
10503
+ }, OPENCODE_RUN_TIMEOUT_MS);
10504
+ child.stdout.on("data", (d) => {
10505
+ stdout += d.toString();
10506
+ });
10507
+ child.stderr.on("data", (d) => {
10508
+ stderr += d.toString();
10509
+ });
10510
+ child.on("error", (err) => finish(() => fail(`opencode run spawn failed: ${err instanceof Error ? err.message : err}`, err)));
10511
+ child.on("close", (code) => finish(() => {
10512
+ const runError = parseOpencodeRunError(stdout);
10513
+ if (code !== 0 || runError) {
10514
+ const tail = runError ?? (stderr.trim() || stdout.trim()).slice(-500);
10515
+ fail(`opencode run failed (exit ${code ?? "null"}): ${tail}`);
10516
+ return;
10517
+ }
10518
+ const reply = parseOpencodeRunReply(stdout);
10519
+ const tools = parseRunToolCalls(stdout);
10520
+ if (tools.length > 0) {
10521
+ console.error(`[opencode-run] ${codeName} tools: ${tools.join(", ")}`);
10522
+ }
10523
+ resolve({ admittedSeq: 0, reply });
10524
+ }));
10525
+ });
10526
+ }
10325
10527
  function stopOpencodeSession(codeName, log2) {
10326
10528
  const tmuxSession = opencodeTmuxSession(codeName);
10327
10529
  try {
@@ -12175,4 +12377,4 @@ export {
12175
12377
  stopAllSessionsAndWait,
12176
12378
  getProjectDir
12177
12379
  };
12178
- //# sourceMappingURL=chunk-LAO2CUZU.js.map
12380
+ //# sourceMappingURL=chunk-IJF4W6LC.js.map