@cabane/companion 0.6.219 → 0.6.221

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/cli.js CHANGED
@@ -2572,7 +2572,7 @@ var init_transcript_sink = __esm({
2572
2572
  });
2573
2573
 
2574
2574
  // packages/agent-runtime/src/turn-control/descriptions.ts
2575
- var MAX_ASK_QUESTION_BYTES, MAX_ASK_HEADLINE_BYTES, MAX_ASK_ITEMS, EXCHANGE_KINDS, APPROVAL_OPTIONS, REQUEST_OPTIONS, MAX_REQUEST_BODY_BYTES, MAX_ASK_OPTION_BYTES, ASK_OPTION_NOT_A_STRING, MIN_ASK_OPTIONS, MAX_ASK_OPTIONS, ASK_TARGET_PATTERN, ASK_TARGET_INVALID, MAX_WAKE_NOTE_BYTES, MAX_WITHDRAW_REASON_BYTES, MAX_SKIP_REASON_BYTES, TURN_CONTROL_MCP_SERVER, TURN_CONTROL_TOOLS, TURN_CONTROL_TOOL_DESCRIPTIONS, TURN_CONTROL_FIELD_DESCRIPTIONS;
2575
+ var MAX_ASK_QUESTION_BYTES, MAX_ASK_HEADLINE_BYTES, MAX_ASK_ITEMS, EXCHANGE_KINDS, APPROVAL_OPTIONS, REQUEST_OPTIONS, EXCHANGE_EXPECTS, REQUEST_RESULT_OPTIONS, MAX_EXCHANGE_FILES, MAX_REQUEST_BODY_BYTES, MAX_ASK_OPTION_BYTES, ASK_OPTION_NOT_A_STRING, MIN_ASK_OPTIONS, MAX_ASK_OPTIONS, ASK_TARGET_PATTERN, ASK_TARGET_INVALID, MAX_WAKE_NOTE_BYTES, MAX_WITHDRAW_REASON_BYTES, MAX_SKIP_REASON_BYTES, TURN_CONTROL_MCP_SERVER, TURN_CONTROL_TOOLS, TURN_CONTROL_TOOL_DESCRIPTIONS, TURN_CONTROL_FIELD_DESCRIPTIONS;
2576
2576
  var init_descriptions = __esm({
2577
2577
  "packages/agent-runtime/src/turn-control/descriptions.ts"() {
2578
2578
  "use strict";
@@ -2582,6 +2582,9 @@ var init_descriptions = __esm({
2582
2582
  EXCHANGE_KINDS = ["question", "approval", "request"];
2583
2583
  APPROVAL_OPTIONS = ["Yes", "No"];
2584
2584
  REQUEST_OPTIONS = ["Done", "Couldn't"];
2585
+ EXCHANGE_EXPECTS = ["confirmation", "result"];
2586
+ REQUEST_RESULT_OPTIONS = ["Couldn't"];
2587
+ MAX_EXCHANGE_FILES = 5;
2585
2588
  MAX_REQUEST_BODY_BYTES = 2e3;
2586
2589
  MAX_ASK_OPTION_BYTES = 200;
2587
2590
  ASK_OPTION_NOT_A_STRING = "An ask option is a plain string label.";
@@ -2605,7 +2608,7 @@ var init_descriptions = __esm({
2605
2608
  answer: `Call this just before you write your answer: the text you write next is what the conversation keeps as your message. Call it once.`,
2606
2609
  open_exchange: `Put something in front of one person that comes back with a recorded outcome, then end your turn; don't wait for it. \`targetUserId\` is a person on your roster, by their \`@handle\`; to bring in an agent, name them with \`@handle\` in your reply.
2607
2610
  - \`kind\`: \`question\` for a choice among courses of action (two included) or free text; \`approval\` for a yes/no on one action you propose; \`request\` for something only the person can do, reported back.
2608
- - A question is one item (\`headline\`, optional \`question\` body, \`options\`) or \`questions\`, 1\u2013${MAX_ASK_ITEMS} items; never both. An approval or request is \`headline\` and an optional \`question\` body only: its answers are fixed (${APPROVAL_OPTIONS.join(" / ")}; ${REQUEST_OPTIONS.join(" / ")}, output in the note or attachments). A request's body carries the steps and may hold a list and code blocks; every other body is a sentence or two of framing, inline Markdown only.
2611
+ - A question is one item (\`headline\`, optional \`question\` body, \`options\`) or \`questions\`, 1\u2013${MAX_ASK_ITEMS} items; never both. An approval or request is \`headline\` and an optional \`question\` body only: its answers are fixed (${APPROVAL_OPTIONS.join(" / ")}; a request's set by \`expects\`). A request's body carries the steps and may hold a list and code blocks; every other body is a sentence or two of framing, inline Markdown only.
2609
2612
  - Decisions that arise together go in ONE call, in the order you want them answered. A second call is a separate exchange, never an edit.
2610
2613
  - Voice, in headline, body and options: "I" for yourself, never your own name; name everyone else who decides or acts, as on your roster. Never "you", "your", "we", "us", "our" or their contractions, nor "he", "she" or "they" for a named actor. A quotation stays accurate: say who said it.
2611
2614
  - It must stand alone, since it can arrive first: the reply carries the findings, the exchange the question; don't repeat the reply in it.
@@ -2621,9 +2624,11 @@ var init_descriptions = __esm({
2621
2624
  answer: {},
2622
2625
  open_exchange: {
2623
2626
  targetUserId: "The person: their `@handle` from your turn context's roster (preferred), or their user id.",
2624
- kind: `What the exchange is for; default \`question\`. \`question\`: the person picks among courses of action or types an answer. \`approval\`: a yes/no on one proposed action \u2014 the person answers ${APPROVAL_OPTIONS.join(" or ")}. \`request\`: something only the person can do \u2014 they report ${REQUEST_OPTIONS.join(" or ")}.`,
2627
+ kind: `What the exchange is for; default \`question\`. \`question\`: the person picks among courses of action or types an answer. \`approval\`: a yes/no on one proposed action \u2014 the person answers ${APPROVAL_OPTIONS.join(" or ")}. \`request\`: something only the person can do; set \`expects\`.`,
2628
+ expects: `A request only, and set it every time: \`confirmation\` when you only need to hear it's done (they answer ${REQUEST_OPTIONS.join(" or ")}), \`result\` when you need something back (they type it, or answer ${REQUEST_RESULT_OPTIONS.join("")}). Default \`result\`. Refused on a question or approval.`,
2625
2629
  question: `The body beneath the headline \u2014 for a question or approval one or two sentences of framing, NOT a report (up to ${MAX_ASK_QUESTION_BYTES} characters, inline markdown only); for a request the steps, with lists and code blocks allowed (up to ${MAX_REQUEST_BODY_BYTES} characters). With \`questions\`, leave it out.`,
2626
2630
  headline: `ONE clear, capitalized sentence, up to ${MAX_ASK_HEADLINE_BYTES} characters: for a question or approval, the question ending in \`?\` ("Should Ledger deploy once Mia approves?"); for a request, what to do ("Run these and send me the output"). What the person reads first in For you. Required for an approval or request.`,
2631
+ files: `1\u2013${MAX_EXCHANGE_FILES} workspace paths, drawn as file chips above the body; the person must be able to read each.`,
2627
2632
  options: `A question's single form only: ${MIN_ASK_OPTIONS}\u2013${MAX_ASK_OPTIONS} suggested one-click answers, up to ${MAX_ASK_OPTION_BYTES} characters each. Each option must make sense on its own. Refused on an approval or request.`,
2628
2633
  questions: `A question only, MULTI form: 1\u2013${MAX_ASK_ITEMS} items at once, when a plan ends with several bounded decisions. Provide EITHER this or \`question\`/\`headline\`/\`options\`, not both.`,
2629
2634
  "questions.headline": `The one-sentence question ("Should Ledger deploy once Mia approves?") \u2014 required for each item, up to ${MAX_ASK_HEADLINE_BYTES} characters.`,
@@ -6235,6 +6240,7 @@ function createTurnControlMcpServer(acts, skipState) {
6235
6240
  {
6236
6241
  targetUserId: z15.string().regex(ASK_TARGET_PATTERN, { error: ASK_TARGET_INVALID }).describe(TURN_CONTROL_FIELD_DESCRIPTIONS.open_exchange.targetUserId),
6237
6242
  kind: z15.enum(EXCHANGE_KINDS).optional().describe(TURN_CONTROL_FIELD_DESCRIPTIONS.open_exchange.kind),
6243
+ expects: z15.enum(EXCHANGE_EXPECTS).optional().describe(TURN_CONTROL_FIELD_DESCRIPTIONS.open_exchange.expects),
6238
6244
  // The request's cap; the server holds every other kind to its own.
6239
6245
  question: z15.string().min(1).max(MAX_REQUEST_BODY_BYTES).optional().describe(TURN_CONTROL_FIELD_DESCRIPTIONS.open_exchange.question),
6240
6246
  headline: z15.string().min(1).max(MAX_ASK_HEADLINE_BYTES).optional().describe(TURN_CONTROL_FIELD_DESCRIPTIONS.open_exchange.headline),
@@ -6248,6 +6254,7 @@ function createTurnControlMcpServer(acts, skipState) {
6248
6254
  ).min(MIN_ASK_OPTIONS).max(MAX_ASK_OPTIONS).optional().describe(TURN_CONTROL_FIELD_DESCRIPTIONS.open_exchange["questions.options"])
6249
6255
  })
6250
6256
  ).min(1).max(MAX_ASK_ITEMS).optional().describe(TURN_CONTROL_FIELD_DESCRIPTIONS.open_exchange.questions),
6257
+ files: z15.array(z15.string().min(1).max(1024)).optional().describe(TURN_CONTROL_FIELD_DESCRIPTIONS.open_exchange.files),
6251
6258
  replaces: z15.object({
6252
6259
  askId: z15.string().uuid().describe(TURN_CONTROL_FIELD_DESCRIPTIONS.open_exchange["replaces.askId"]),
6253
6260
  reason: z15.string().min(1).max(MAX_WITHDRAW_REASON_BYTES).describe(TURN_CONTROL_FIELD_DESCRIPTIONS.open_exchange["replaces.reason"])
@@ -6265,10 +6272,12 @@ function createTurnControlMcpServer(acts, skipState) {
6265
6272
  ask: {
6266
6273
  targetUserId: args.targetUserId,
6267
6274
  kind,
6275
+ ...args.expects ? { expects: args.expects } : {},
6268
6276
  ...args.headline ? { headline: args.headline } : {},
6269
6277
  ...args.question ? { question: args.question } : {},
6270
6278
  ...args.options ? { options: args.options } : {},
6271
- ...args.questions ? { questions: args.questions } : {}
6279
+ ...args.questions ? { questions: args.questions } : {},
6280
+ ...args.files ? { files: args.files } : {}
6272
6281
  }
6273
6282
  });
6274
6283
  }
@@ -6292,12 +6301,18 @@ function createTurnControlMcpServer(acts, skipState) {
6292
6301
  headline: q.headline,
6293
6302
  ...q.body ? { body: q.body } : {},
6294
6303
  ...q.options && q.options.length > 0 ? { options: q.options } : {}
6295
- }))
6304
+ })),
6305
+ // Forwarded so the server refuses it on a question, as it does an
6306
+ // approval's, rather than dropping it here unseen.
6307
+ ...args.expects ? { expects: args.expects } : {},
6308
+ ...args.files ? { files: args.files } : {}
6296
6309
  } : {
6297
6310
  targetUserId: args.targetUserId,
6311
+ ...args.expects ? { expects: args.expects } : {},
6298
6312
  ...args.question ? { question: args.question } : {},
6299
6313
  ...args.headline ? { headline: args.headline } : {},
6300
- ...args.options && args.options.length > 0 ? { options: args.options } : {}
6314
+ ...args.options && args.options.length > 0 ? { options: args.options } : {},
6315
+ ...args.files ? { files: args.files } : {}
6301
6316
  }
6302
6317
  });
6303
6318
  },
package/dist/runtime.js CHANGED
@@ -2939,6 +2939,8 @@ var MAX_ASK_HEADLINE_BYTES = 120;
2939
2939
  var MAX_ASK_ITEMS = 20;
2940
2940
  var APPROVAL_OPTIONS = ["Yes", "No"];
2941
2941
  var REQUEST_OPTIONS = ["Done", "Couldn't"];
2942
+ var REQUEST_RESULT_OPTIONS = ["Couldn't"];
2943
+ var MAX_EXCHANGE_FILES = 5;
2942
2944
  var MAX_REQUEST_BODY_BYTES = 2e3;
2943
2945
  var MAX_ASK_OPTION_BYTES = 200;
2944
2946
  var MIN_ASK_OPTIONS = 2;
@@ -2959,7 +2961,7 @@ var TURN_CONTROL_TOOL_DESCRIPTIONS = {
2959
2961
  answer: `Call this just before you write your answer: the text you write next is what the conversation keeps as your message. Call it once.`,
2960
2962
  open_exchange: `Put something in front of one person that comes back with a recorded outcome, then end your turn; don't wait for it. \`targetUserId\` is a person on your roster, by their \`@handle\`; to bring in an agent, name them with \`@handle\` in your reply.
2961
2963
  - \`kind\`: \`question\` for a choice among courses of action (two included) or free text; \`approval\` for a yes/no on one action you propose; \`request\` for something only the person can do, reported back.
2962
- - A question is one item (\`headline\`, optional \`question\` body, \`options\`) or \`questions\`, 1\u2013${MAX_ASK_ITEMS} items; never both. An approval or request is \`headline\` and an optional \`question\` body only: its answers are fixed (${APPROVAL_OPTIONS.join(" / ")}; ${REQUEST_OPTIONS.join(" / ")}, output in the note or attachments). A request's body carries the steps and may hold a list and code blocks; every other body is a sentence or two of framing, inline Markdown only.
2964
+ - A question is one item (\`headline\`, optional \`question\` body, \`options\`) or \`questions\`, 1\u2013${MAX_ASK_ITEMS} items; never both. An approval or request is \`headline\` and an optional \`question\` body only: its answers are fixed (${APPROVAL_OPTIONS.join(" / ")}; a request's set by \`expects\`). A request's body carries the steps and may hold a list and code blocks; every other body is a sentence or two of framing, inline Markdown only.
2963
2965
  - Decisions that arise together go in ONE call, in the order you want them answered. A second call is a separate exchange, never an edit.
2964
2966
  - Voice, in headline, body and options: "I" for yourself, never your own name; name everyone else who decides or acts, as on your roster. Never "you", "your", "we", "us", "our" or their contractions, nor "he", "she" or "they" for a named actor. A quotation stays accurate: say who said it.
2965
2967
  - It must stand alone, since it can arrive first: the reply carries the findings, the exchange the question; don't repeat the reply in it.
@@ -2975,9 +2977,11 @@ var TURN_CONTROL_FIELD_DESCRIPTIONS = {
2975
2977
  answer: {},
2976
2978
  open_exchange: {
2977
2979
  targetUserId: "The person: their `@handle` from your turn context's roster (preferred), or their user id.",
2978
- kind: `What the exchange is for; default \`question\`. \`question\`: the person picks among courses of action or types an answer. \`approval\`: a yes/no on one proposed action \u2014 the person answers ${APPROVAL_OPTIONS.join(" or ")}. \`request\`: something only the person can do \u2014 they report ${REQUEST_OPTIONS.join(" or ")}.`,
2980
+ kind: `What the exchange is for; default \`question\`. \`question\`: the person picks among courses of action or types an answer. \`approval\`: a yes/no on one proposed action \u2014 the person answers ${APPROVAL_OPTIONS.join(" or ")}. \`request\`: something only the person can do; set \`expects\`.`,
2981
+ expects: `A request only, and set it every time: \`confirmation\` when you only need to hear it's done (they answer ${REQUEST_OPTIONS.join(" or ")}), \`result\` when you need something back (they type it, or answer ${REQUEST_RESULT_OPTIONS.join("")}). Default \`result\`. Refused on a question or approval.`,
2979
2982
  question: `The body beneath the headline \u2014 for a question or approval one or two sentences of framing, NOT a report (up to ${MAX_ASK_QUESTION_BYTES} characters, inline markdown only); for a request the steps, with lists and code blocks allowed (up to ${MAX_REQUEST_BODY_BYTES} characters). With \`questions\`, leave it out.`,
2980
2983
  headline: `ONE clear, capitalized sentence, up to ${MAX_ASK_HEADLINE_BYTES} characters: for a question or approval, the question ending in \`?\` ("Should Ledger deploy once Mia approves?"); for a request, what to do ("Run these and send me the output"). What the person reads first in For you. Required for an approval or request.`,
2984
+ files: `1\u2013${MAX_EXCHANGE_FILES} workspace paths, drawn as file chips above the body; the person must be able to read each.`,
2981
2985
  options: `A question's single form only: ${MIN_ASK_OPTIONS}\u2013${MAX_ASK_OPTIONS} suggested one-click answers, up to ${MAX_ASK_OPTION_BYTES} characters each. Each option must make sense on its own. Refused on an approval or request.`,
2982
2986
  questions: `A question only, MULTI form: 1\u2013${MAX_ASK_ITEMS} items at once, when a plan ends with several bounded decisions. Provide EITHER this or \`question\`/\`headline\`/\`options\`, not both.`,
2983
2987
  "questions.headline": `The one-sentence question ("Should Ledger deploy once Mia approves?") \u2014 required for each item, up to ${MAX_ASK_HEADLINE_BYTES} characters.`,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cabane/companion",
3
- "version": "0.6.219",
3
+ "version": "0.6.221",
4
4
  "type": "module",
5
5
  "description": "The Cabane Companion (headless): connect an agent on your machine to your Cabane workspace as a responder — drive work against your own codebase, files, and MCP servers without putting any of it in Cabane.",
6
6
  "license": "UNLICENSED",