@integrity-labs/agt-cli 0.28.632 → 0.28.634

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/mcp/index.js CHANGED
@@ -21359,13 +21359,32 @@ function renderWaitingClause(item, nowMs) {
21359
21359
  const ask = item.waiting_on ? `: ${item.waiting_on.length > 80 ? `${item.waiting_on.slice(0, 77)}...` : item.waiting_on}` : "";
21360
21360
  return head ? `${head}${ask}` : "";
21361
21361
  }
21362
- function renderKanbanItemLine(item, nowMs) {
21362
+ var KANBAN_DESCRIPTION_MAX_CHARS = 1200;
21363
+ var TERMINAL_STATUSES_FOR_DESCRIPTION = /* @__PURE__ */ new Set(["done", "failed"]);
21364
+ function truncateByCodePoints(text, max) {
21365
+ const points = Array.from(text);
21366
+ if (points.length <= max) return { shown: text, total: points.length, truncated: false };
21367
+ return { shown: points.slice(0, max).join(""), total: points.length, truncated: true };
21368
+ }
21369
+ function renderDescriptionClause(item) {
21370
+ const text = item.description?.trim();
21371
+ if (!text) return null;
21372
+ if (TERMINAL_STATUSES_FOR_DESCRIPTION.has(item.status)) return null;
21373
+ const { shown, total, truncated } = truncateByCodePoints(text, KANBAN_DESCRIPTION_MAX_CHARS);
21374
+ if (!truncated) return ` ${text}`;
21375
+ return ` ${shown}
21376
+ [description truncated \u2014 showing ${KANBAN_DESCRIPTION_MAX_CHARS} of ${total} characters; open the card in the console for the rest]`;
21377
+ }
21378
+ function renderKanbanItemLine(item, nowMs, suffix = "") {
21363
21379
  const pri = kanbanPriorityLabel(item.priority);
21364
21380
  const est = item.estimated_minutes ? ` ~${item.estimated_minutes}min` : "";
21365
21381
  const del = item.deliverable ? ` \u2192 ${item.deliverable}` : "";
21366
21382
  const res = item.result ? ` \u2713 ${item.result}` : "";
21367
21383
  const wait = renderWaitingClause(item, nowMs);
21368
- return `- [${pri}] ${item.title}${wait}${est}${del}${res} (id: ${item.id})`;
21384
+ const head = `- [${pri}] ${item.title}${wait}${est}${del}${res} (id: ${item.id})${suffix}`;
21385
+ const desc = renderDescriptionClause(item);
21386
+ return desc ? `${head}
21387
+ ${desc}` : head;
21369
21388
  }
21370
21389
  function renderKanbanList(items, nowMs = Date.now()) {
21371
21390
  if (!items.length) return "Board is empty.";
@@ -21390,7 +21409,7 @@ function renderKanbanList(items, nowMs = Date.now()) {
21390
21409
  ## ${BLOCKED_ON_ME_SECTION_HEADING} (${blockedOnMe.length})`);
21391
21410
  lines.push(BLOCKED_ON_ME_SECTION_NOTE);
21392
21411
  for (const item of blockedOnMe) {
21393
- lines.push(`${renderKanbanItemLine(item, nowMs)} [blocking ${item.blocked_agent_label}]`);
21412
+ lines.push(renderKanbanItemLine(item, nowMs, ` [blocking ${item.blocked_agent_label}]`));
21394
21413
  }
21395
21414
  }
21396
21415
  if (humanAssigned.length) {
@@ -21399,7 +21418,7 @@ function renderKanbanList(items, nowMs = Date.now()) {
21399
21418
  lines.push(HUMAN_ASSIGNED_SECTION_NOTE);
21400
21419
  for (const item of humanAssigned) {
21401
21420
  const who = item.assignee_name ? ` [with ${item.assignee_name}]` : "";
21402
- lines.push(`${renderKanbanItemLine(item, nowMs)}${who}`);
21421
+ lines.push(renderKanbanItemLine(item, nowMs, who));
21403
21422
  }
21404
21423
  }
21405
21424
  return lines.join("\n");
@@ -22401,6 +22420,7 @@ server.tool(
22401
22420
  return { content: [{ type: "text", text: renderKanbanList(data.items) }] };
22402
22421
  }
22403
22422
  );
22423
+ var KANBAN_SEARCH_DESCRIPTION_MAX_CHARS = 300;
22404
22424
  server.tool(
22405
22425
  "kanban_search",
22406
22426
  `Search your FULL kanban history by keyword \u2014 including done cards older than 24h that kanban_list omits. Use this BEFORE telling anyone you have "no record" of work they say you did: the board only shows the last 24h of completed cards, so "it's not on my board" does NOT mean you never did it. Each hit includes the card's result (the actual deliverable), so you can recite what you produced. An empty query returns your most recent cards across all statuses.`,
@@ -22440,6 +22460,15 @@ server.tool(
22440
22460
  const via = item.source_integration ? ` via ${item.source_integration}` : "";
22441
22461
  lines.push(`
22442
22462
  - [${item.status}${via}, ${day}] ${item.title} (id: ${item.id})`);
22463
+ const desc = item.description?.trim();
22464
+ if (desc) {
22465
+ const { shown, total, truncated } = truncateByCodePoints(
22466
+ desc,
22467
+ KANBAN_SEARCH_DESCRIPTION_MAX_CHARS
22468
+ );
22469
+ const line = truncated ? `${shown} \u2026(description trimmed at ${KANBAN_SEARCH_DESCRIPTION_MAX_CHARS} of ${total} characters; open the card in the console for the full text)` : desc;
22470
+ lines.push(` ${line}`);
22471
+ }
22443
22472
  if (item.deliverable) lines.push(` \u2192 ${item.deliverable}`);
22444
22473
  if (item.result) {
22445
22474
  const more = item.result_truncated ? " \u2026(result trimmed; open the card in the console for the full text)" : "";
@@ -22878,7 +22907,14 @@ server.tool(
22878
22907
  "Optional: the slug (or UUID) of ANOTHER team in your organization to assign across teams. Omit for a same-team handoff. Requires the org to have cross-team assignment enabled and a peer grant; otherwise the target reads as not-found."
22879
22908
  ),
22880
22909
  title: external_exports.string().describe("Task title (max 200 chars)"),
22881
- description: external_exports.string().optional().describe("Detailed description of what needs doing"),
22910
+ // CS-1589: this is the ONLY field that carries the substance of a handoff
22911
+ // title is a headline, deliverable is an outcome — so say plainly that it
22912
+ // reaches the target and that everything they need has to be in it. The
22913
+ // reported failure was an agent that put a complete brief here, got a clean
22914
+ // success message, and delegated a card the recipient read as two lines.
22915
+ description: external_exports.string().optional().describe(
22916
+ "The BRIEF \u2014 this is what the target actually reads on their board, so put everything they need to do the work here: source data and URLs, constraints, specifications, rules they must follow, and anything they should NOT redo. Title and deliverable are a headline and an outcome; they cannot carry instructions. Long briefs are shown in full up to 1200 characters on their board and visibly marked as trimmed beyond that (the whole text is always kept on the card)."
22917
+ ),
22882
22918
  priority: external_exports.number().int().min(1).max(3).optional().describe("Priority: 1=high, 2=medium (default), 3=low"),
22883
22919
  status: external_exports.enum(["backlog", "todo", "in_progress"]).optional().describe(
22884
22920
  "Which column the card lands in on the recipient's board (default: todo). Use 'backlog' to stage it as not-yet-actionable work the teammate will pull later, 'todo' for ready-to-work, 'in_progress' if they should start immediately."
@@ -37085,7 +37085,9 @@ function readGiveUpSignal(path, now = Date.now()) {
37085
37085
  if (typeof raw.gave_up_at !== "string") return null;
37086
37086
  const t = Date.parse(raw.gave_up_at);
37087
37087
  if (!Number.isFinite(t) || t > now) return null;
37088
- return { atMs: t, reason: raw.reason === "transient_overload" ? "transient_overload" : null };
37088
+ const reason = raw.reason === "transient_overload" ? "transient_overload" : raw.reason === "usage_limit" ? "usage_limit" : null;
37089
+ const hint = typeof raw.resets_hint === "string" && raw.resets_hint.trim().length > 0 ? raw.resets_hint.trim().slice(0, 40) : null;
37090
+ return { atMs: t, reason, resetsHint: hint };
37089
37091
  } catch {
37090
37092
  return null;
37091
37093
  }
@@ -37097,7 +37099,10 @@ function decideGiveUpNotice(input) {
37097
37099
  if (input.lastHandledAtMs != null && input.signalAtMs <= input.lastHandledAtMs) return false;
37098
37100
  return true;
37099
37101
  }
37100
- function giveUpNoticeText(reason = null) {
37102
+ function giveUpNoticeText(reason = null, resetsHint = null) {
37103
+ if (reason === "usage_limit") {
37104
+ return resetsHint ? `\u23F3 I've reached my usage limit for now, so I can't reply until ${resetsHint}. Your message is queued \u2014 I'll pick it up then, no need to resend.` : "\u23F3 I've reached my usage limit for now, so I can't reply just yet. Your message is queued \u2014 I'll pick it up as soon as it lifts, no need to resend.";
37105
+ }
37101
37106
  if (reason === "transient_overload") {
37102
37107
  return "\u26A0\uFE0F I hit a brief overload and couldn\u2019t finish your last message \u2014 please resend it in a moment.";
37103
37108
  }
@@ -42980,7 +42985,7 @@ function armSlackTurnFailureWatch(args) {
42980
42985
  }
42981
42986
  })();
42982
42987
  }
42983
- function postSlackWatchdogGiveUpNotice(channel, threadTs, isThreadReply, reason) {
42988
+ function postSlackWatchdogGiveUpNotice(channel, threadTs, isThreadReply, reason, resetsHint = null) {
42984
42989
  if (!BOT_TOKEN || !channel) return;
42985
42990
  const now = Date.now();
42986
42991
  const conversationKey = isThreadReply ? `${channel}:${threadTs}` : channel;
@@ -42997,7 +43002,7 @@ function postSlackWatchdogGiveUpNotice(channel, threadTs, isThreadReply, reason)
42997
43002
  },
42998
43003
  body: JSON.stringify({
42999
43004
  channel,
43000
- text: giveUpNoticeText(reason),
43005
+ text: giveUpNoticeText(reason, resetsHint),
43001
43006
  // CR on PR #1824: anchor to the originating message even for root
43002
43007
  // messages (threadTs === messageTs is still the conversation target) —
43003
43008
  // a channel-root notice diverges from postUndeliverableNotice and
@@ -43026,7 +43031,8 @@ function checkSlackWatchdogGiveUpNotice() {
43026
43031
  convo.channel,
43027
43032
  convo.threadTs,
43028
43033
  convo.isThreadReply,
43029
- signal?.reason ?? null
43034
+ signal?.reason ?? null,
43035
+ signal?.resetsHint ?? null
43030
43036
  );
43031
43037
  }
43032
43038
  }
@@ -39674,7 +39674,9 @@ function readGiveUpSignal(path, now = Date.now()) {
39674
39674
  if (typeof raw.gave_up_at !== "string") return null;
39675
39675
  const t = Date.parse(raw.gave_up_at);
39676
39676
  if (!Number.isFinite(t) || t > now) return null;
39677
- return { atMs: t, reason: raw.reason === "transient_overload" ? "transient_overload" : null };
39677
+ const reason = raw.reason === "transient_overload" ? "transient_overload" : raw.reason === "usage_limit" ? "usage_limit" : null;
39678
+ const hint = typeof raw.resets_hint === "string" && raw.resets_hint.trim().length > 0 ? raw.resets_hint.trim().slice(0, 40) : null;
39679
+ return { atMs: t, reason, resetsHint: hint };
39678
39680
  } catch {
39679
39681
  return null;
39680
39682
  }
@@ -39686,7 +39688,10 @@ function decideGiveUpNotice(input) {
39686
39688
  if (input.lastHandledAtMs != null && input.signalAtMs <= input.lastHandledAtMs) return false;
39687
39689
  return true;
39688
39690
  }
39689
- function giveUpNoticeText(reason = null) {
39691
+ function giveUpNoticeText(reason = null, resetsHint = null) {
39692
+ if (reason === "usage_limit") {
39693
+ return resetsHint ? `\u23F3 I've reached my usage limit for now, so I can't reply until ${resetsHint}. Your message is queued \u2014 I'll pick it up then, no need to resend.` : "\u23F3 I've reached my usage limit for now, so I can't reply just yet. Your message is queued \u2014 I'll pick it up as soon as it lifts, no need to resend.";
39694
+ }
39690
39695
  if (reason === "transient_overload") {
39691
39696
  return "\u26A0\uFE0F I hit a brief overload and couldn\u2019t finish your last message \u2014 please resend it in a moment.";
39692
39697
  }
@@ -42133,13 +42138,13 @@ function armTelegramTurnFailureWatch(args) {
42133
42138
  }
42134
42139
  })();
42135
42140
  }
42136
- async function notifyWatchdogGiveUp(chatId, reason) {
42141
+ async function notifyWatchdogGiveUp(chatId, reason, resetsHint = null) {
42137
42142
  const now = Date.now();
42138
42143
  if (!telegramUndeliverableNotices.claimThrottleSlot(chatId, now)) return;
42139
42144
  try {
42140
42145
  const resp = await telegramApiCall(
42141
42146
  "sendMessage",
42142
- { chat_id: chatId, text: giveUpNoticeText(reason) },
42147
+ { chat_id: chatId, text: giveUpNoticeText(reason, resetsHint) },
42143
42148
  1e4
42144
42149
  );
42145
42150
  if (!resp.ok) {
@@ -42182,7 +42187,7 @@ function checkWatchdogGiveUpNotice() {
42182
42187
  return;
42183
42188
  }
42184
42189
  for (const chatId of chats) {
42185
- void notifyWatchdogGiveUp(chatId, signal?.reason ?? null);
42190
+ void notifyWatchdogGiveUp(chatId, signal?.reason ?? null, signal?.resetsHint ?? null);
42186
42191
  }
42187
42192
  }
42188
42193
  function __resetGiveUpNoticeStateForTests() {
@@ -43,7 +43,7 @@ import {
43
43
  writeDirectChatSessionState,
44
44
  writeEgressAllowlist,
45
45
  writePersistentClaudeWrapper
46
- } from "./chunk-IT2WYXBM.js";
46
+ } from "./chunk-GNTCOXZG.js";
47
47
  import "./chunk-FKG7DIE2.js";
48
48
  import "./chunk-XWVM4KPK.js";
49
49
  export {
@@ -92,4 +92,4 @@ export {
92
92
  writeEgressAllowlist,
93
93
  writePersistentClaudeWrapper
94
94
  };
95
- //# sourceMappingURL=persistent-session-YER3H6R6.js.map
95
+ //# sourceMappingURL=persistent-session-ORYBOIBQ.js.map
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  paneLogPath
3
- } from "./chunk-IT2WYXBM.js";
3
+ } from "./chunk-GNTCOXZG.js";
4
4
  import "./chunk-FKG7DIE2.js";
5
5
  import "./chunk-XWVM4KPK.js";
6
6
 
@@ -712,4 +712,4 @@ export {
712
712
  readAndResetSlackReplyBindingClassifications,
713
713
  readAndResetSlackReplyTargetClassifications
714
714
  };
715
- //# sourceMappingURL=responsiveness-probe-MWZBEJOS.js.map
715
+ //# sourceMappingURL=responsiveness-probe-WYCKY2BJ.js.map
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@integrity-labs/agt-cli",
3
- "version": "0.28.632",
3
+ "version": "0.28.634",
4
4
  "description": "Augmented Team CLI — agent provisioning and management",
5
5
  "type": "module",
6
6
  "engines": {