llmz 0.9.0 → 1.0.2

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 (238) hide show
  1. package/DOCS.md +232 -1794
  2. package/ERRORS.md +101 -0
  3. package/README.md +96 -582
  4. package/dist/chat/chat.d.ts +63 -0
  5. package/dist/chat/component.d.ts +31 -0
  6. package/dist/chat/component.default.d.ts +58 -0
  7. package/dist/chat/response.d.ts +15 -0
  8. package/dist/compiler/compiler.d.ts +2 -7
  9. package/dist/compiler/plugins/dynamic-code.d.ts +7 -0
  10. package/dist/compiler/plugins/replace-comment.d.ts +2 -3
  11. package/dist/compiler/plugins/return-async.d.ts +5 -4
  12. package/dist/compiler/plugins/termination.d.ts +8 -0
  13. package/dist/compiler/plugins/tool-resolution.d.ts +4 -0
  14. package/dist/compiler/plugins/variable-extraction.d.ts +2 -8
  15. package/dist/component-CMFoCHyu.cjs +649 -0
  16. package/dist/component-DncqP4fB.js +614 -0
  17. package/dist/context.d.ts +71 -378
  18. package/dist/custom-client-C-WXvLD9.js +1655 -0
  19. package/dist/custom-client-Cgt9_0r1.cjs +1732 -0
  20. package/dist/custom-client.d.ts +12 -2
  21. package/dist/errors/catalog.d.ts +294 -0
  22. package/dist/errors/hooks.d.ts +2 -0
  23. package/dist/errors-C6ppQUZX.cjs +893 -0
  24. package/dist/errors-Crk5P8jo.js +636 -0
  25. package/dist/errors.d.ts +24 -36
  26. package/dist/execute-CiYvPs5Q.js +2061 -0
  27. package/dist/execute-DTTfacsi.cjs +2062 -0
  28. package/dist/{exit-DUM96DN1.cjs → exit-BOtKWPuT.cjs} +38 -28
  29. package/dist/{exit-CDdxDBRT.js → exit-DMPwCSba.js} +37 -27
  30. package/dist/exit.d.ts +19 -16
  31. package/dist/index.cjs +177 -1237
  32. package/dist/index.d.ts +25 -28
  33. package/dist/index.js +137 -1213
  34. package/dist/index.workerd.js +8974 -11145
  35. package/dist/inspect.d.ts +18 -4
  36. package/dist/inspection.d.ts +40 -0
  37. package/dist/native-0bq5ATZM.cjs +212 -0
  38. package/dist/native-n_718Z-T.js +177 -0
  39. package/dist/objects.d.ts +2 -57
  40. package/dist/prompts/native.d.ts +2 -0
  41. package/dist/prompts/prompt.d.ts +10 -101
  42. package/dist/quickjs-variant-21IO97PF.cjs +1080 -0
  43. package/dist/quickjs-variant-CtuGagsb.js +985 -0
  44. package/dist/result.d.ts +30 -861
  45. package/dist/runtime/execute.d.ts +3 -2
  46. package/dist/runtime/execution-activity.d.ts +11 -0
  47. package/dist/runtime/execution-diagnostics.d.ts +11 -0
  48. package/dist/runtime/execution-report.d.ts +51 -0
  49. package/dist/runtime/fixtures/chat.d.ts +8 -0
  50. package/dist/runtime/fixtures/long-search.d.ts +1 -1
  51. package/dist/runtime/fixtures/native-client.d.ts +33 -0
  52. package/dist/runtime/fixtures/protocol-languages.d.ts +1 -1
  53. package/dist/runtime/forced-inspection.d.ts +13 -0
  54. package/dist/runtime/forced-inspection.test.d.ts +1 -0
  55. package/dist/runtime/generate.d.ts +23 -20
  56. package/dist/runtime/generate.test.d.ts +1 -0
  57. package/dist/runtime/hook-provenance.test.d.ts +1 -0
  58. package/dist/runtime/inspection-hook.test.d.ts +1 -0
  59. package/dist/runtime/inspection-values.d.ts +14 -0
  60. package/dist/runtime/inspection-values.test.d.ts +1 -0
  61. package/dist/runtime/interruption-control-flow.test.d.ts +1 -0
  62. package/dist/runtime/interruption-settings.test.d.ts +1 -0
  63. package/dist/runtime/javascript-api.d.ts +62 -0
  64. package/dist/runtime/javascript-api.test.d.ts +1 -0
  65. package/dist/runtime/native-review.test.d.ts +1 -0
  66. package/dist/runtime/native-tools.d.ts +18 -0
  67. package/dist/runtime/native-tools.test.d.ts +1 -0
  68. package/dist/runtime/object-memory.test.d.ts +1 -0
  69. package/dist/runtime/single-tool.test.d.ts +1 -0
  70. package/dist/runtime/think-signal.test.d.ts +1 -0
  71. package/dist/runtime/token-budget.d.ts +22 -0
  72. package/dist/runtime/token-budget.test.d.ts +1 -0
  73. package/dist/runtime/tool-wrapper.d.ts +6 -5
  74. package/dist/runtime/traces.test.d.ts +1 -0
  75. package/dist/runtime/truncation.test.d.ts +1 -0
  76. package/dist/runtime/types.d.ts +47 -31
  77. package/dist/runtime/variable-recovery.test.d.ts +1 -0
  78. package/dist/runtime/vm-context.d.ts +6 -1
  79. package/dist/runtime/worker-completion.test.d.ts +1 -0
  80. package/dist/runtime-names.d.ts +4 -0
  81. package/dist/schema-CXlnbb3n.cjs +68 -0
  82. package/dist/schema-GE4ISPCR.js +45 -0
  83. package/dist/schema.d.ts +10 -0
  84. package/dist/schema.test.d.ts +1 -0
  85. package/dist/session/compactor.d.ts +51 -0
  86. package/dist/session/compactor.test.d.ts +1 -0
  87. package/dist/session/history.d.ts +36 -0
  88. package/dist/session/history.test.d.ts +1 -0
  89. package/dist/session/json.d.ts +3 -0
  90. package/dist/session/json.test.d.ts +1 -0
  91. package/dist/session/memory-codec.d.ts +9 -0
  92. package/dist/session/memory-codec.test.d.ts +1 -0
  93. package/dist/session/memory-render.d.ts +15 -0
  94. package/dist/session/memory-render.test.d.ts +1 -0
  95. package/dist/session/memory.d.ts +112 -0
  96. package/dist/session/memory.test.d.ts +1 -0
  97. package/dist/session/messages.d.ts +19 -0
  98. package/dist/session/messages.test.d.ts +1 -0
  99. package/dist/session/serialization.d.ts +36 -0
  100. package/dist/session/serialization.test.d.ts +1 -0
  101. package/dist/session/session-memory.test.d.ts +1 -0
  102. package/dist/session/session.d.ts +121 -0
  103. package/dist/session/session.test.d.ts +1 -0
  104. package/dist/session/speaker.test.d.ts +1 -0
  105. package/dist/{transcript.d.ts → session/transcript.d.ts} +4 -8
  106. package/dist/session/transcript.test.d.ts +1 -0
  107. package/dist/{tool-Bv8N4IPj.js → tool-DstssiAs.js} +144 -92
  108. package/dist/{tool-Dy6AJpJH.cjs → tool-_wK9hQOb.cjs} +146 -94
  109. package/dist/tool.d.ts +25 -17
  110. package/dist/truncate-BEKbdo3t.js +79 -0
  111. package/dist/truncate-uomAMGPs.cjs +102 -0
  112. package/dist/truncate.d.ts +24 -0
  113. package/dist/truncate.test.d.ts +1 -0
  114. package/dist/types.d.ts +33 -9
  115. package/dist/{typings-3lsqCbkn.cjs → typings-BA_XxAcY.cjs} +38 -193
  116. package/dist/{typings-CrBa7Tyy.js → typings-BEVDvtuk.js} +38 -175
  117. package/dist/typings-formatter.d.ts +1 -1
  118. package/dist/typings.d.ts +3 -0
  119. package/dist/{uniq-BYQ7GWwb.js → uniq-DfUeSNaX.js} +2 -2
  120. package/dist/{uniq-G872RWmE.cjs → uniq-DiXgysNV.cjs} +6 -18
  121. package/dist/{_baseIteratee-P_firB7b.js → utils-BOFzb8Ok.js} +1134 -16
  122. package/dist/{_baseIteratee-CF4qP2a8.cjs → utils-CTlsXvdj.cjs} +1281 -84
  123. package/dist/vm/drivers/node.d.ts +1 -1
  124. package/dist/vm/drivers/quickjs.d.ts +1 -1
  125. package/dist/vm/errors.d.ts +4 -4
  126. package/dist/vm/index.d.ts +3 -4
  127. package/dist/vm/instrument.d.ts +14 -6
  128. package/dist/vm/member-proxy.d.ts +4 -0
  129. package/dist/vm/member-proxy.test.d.ts +1 -0
  130. package/dist/vm/memory.test.d.ts +1 -0
  131. package/dist/vm/return-semantics.test.d.ts +1 -0
  132. package/dist/vm/types.d.ts +20 -3
  133. package/dist/{vm-BLsHw1da.js → vm-C7SfutHn.js} +1187 -180
  134. package/dist/{vm-D6s1zF6M.cjs → vm-gmekHc0i.cjs} +1221 -207
  135. package/package.json +13 -6
  136. package/dist/_baseForOwn-BfWDTL8L.cjs +0 -53
  137. package/dist/_baseForOwn-CFhWe_W6.js +0 -48
  138. package/dist/_getPrototype-CG7Dxrrz.js +0 -6
  139. package/dist/_getPrototype-DQDlNVVM.cjs +0 -10
  140. package/dist/_overArg-C5Hy7oCi.cjs +0 -196
  141. package/dist/_overArg-CRYbj1NH.js +0 -155
  142. package/dist/chat.d.ts +0 -401
  143. package/dist/common-BlRFtdf2.js +0 -807
  144. package/dist/common-BnvrDnIT.cjs +0 -860
  145. package/dist/compiler/plugins/track-tool-calls.d.ts +0 -33
  146. package/dist/compiler-C-OI9sim.cjs +0 -547
  147. package/dist/compiler-CW1VjQsn.js +0 -473
  148. package/dist/component-C6Agl2ns.cjs +0 -73
  149. package/dist/component-DGG7d_Mz.js +0 -44
  150. package/dist/component.d.ts +0 -88
  151. package/dist/component.default.d.ts +0 -278
  152. package/dist/custom-client-ChuZ63zp.js +0 -2658
  153. package/dist/custom-client-DAsGRnYc.cjs +0 -2729
  154. package/dist/dual-modes-DDkoCp3R.js +0 -3006
  155. package/dist/dual-modes-DPXiuvNe.cjs +0 -3090
  156. package/dist/errors-C962uJdS.cjs +0 -220
  157. package/dist/errors-Cg1G0Awu.js +0 -161
  158. package/dist/example-format.d.ts +0 -8
  159. package/dist/example.d.ts +0 -45
  160. package/dist/execute-BWcdv9so.js +0 -1059
  161. package/dist/execute-DM2-7y86.cjs +0 -1060
  162. package/dist/exit-parser.d.ts +0 -39
  163. package/dist/handlers.d.ts +0 -10
  164. package/dist/hoist.d.ts +0 -2
  165. package/dist/isEmpty-BhJRCqIF.js +0 -52
  166. package/dist/isEmpty-LY533Wmh.cjs +0 -57
  167. package/dist/isPlainObject-CSxXVKCk.cjs +0 -56
  168. package/dist/isPlainObject-D39AzPO2.js +0 -51
  169. package/dist/jsx-CIgdGGVs.js +0 -52
  170. package/dist/jsx-owqxrquU.cjs +0 -75
  171. package/dist/jsx.d.ts +0 -11
  172. package/dist/message-stream/index.d.ts +0 -9
  173. package/dist/message-stream/instructions.d.ts +0 -30
  174. package/dist/message-stream/normalizer.d.ts +0 -21
  175. package/dist/message-stream/parser.d.ts +0 -89
  176. package/dist/message-stream/registry.d.ts +0 -14
  177. package/dist/message-stream/replayable.d.ts +0 -27
  178. package/dist/message-stream/response-parser.d.ts +0 -24
  179. package/dist/message-stream/sanitize.d.ts +0 -10
  180. package/dist/message-stream/stream.d.ts +0 -54
  181. package/dist/message-stream/types.d.ts +0 -97
  182. package/dist/message-stream/validator.d.ts +0 -23
  183. package/dist/prompts/chat-mode/protocol.d.ts +0 -2
  184. package/dist/prompts/chat-mode/system.d.ts +0 -2
  185. package/dist/prompts/chat-mode/system.md.d.ts +0 -2
  186. package/dist/prompts/chat-mode/user.d.ts +0 -2
  187. package/dist/prompts/chat-mode/user.md.d.ts +0 -2
  188. package/dist/prompts/code-examples.d.ts +0 -2
  189. package/dist/prompts/common.d.ts +0 -7
  190. package/dist/prompts/dual-modes.d.ts +0 -2
  191. package/dist/prompts/execution-history.d.ts +0 -6
  192. package/dist/prompts/execution-state.d.ts +0 -3
  193. package/dist/prompts/protocol-basics.d.ts +0 -5
  194. package/dist/prompts/protocol.d.ts +0 -31
  195. package/dist/prompts/worker-mode/protocol.d.ts +0 -2
  196. package/dist/prompts/worker-mode/system.d.ts +0 -2
  197. package/dist/prompts/worker-mode/system.md.d.ts +0 -2
  198. package/dist/prompts/worker-mode/user.d.ts +0 -2
  199. package/dist/prompts/worker-mode/user.md.d.ts +0 -2
  200. package/dist/quickjs-variant-BYhMBpwU.js +0 -45
  201. package/dist/quickjs-variant-CsIwTVFC.cjs +0 -56
  202. package/dist/rolldown-runtime-EAsCxrDo.js +0 -14
  203. package/dist/runtime/fixtures/qwen-protocol-failures.d.ts +0 -29
  204. package/dist/runtime/interpret-result.d.ts +0 -22
  205. package/dist/snapshots.d.ts +0 -249
  206. package/dist/stack-traces-BIE_5Xwf.js +0 -21
  207. package/dist/stack-traces-ntw_qhoy.cjs +0 -26
  208. package/dist/truncator-CLkouTCO.cjs +0 -276
  209. package/dist/truncator-DZqEqnpD.js +0 -253
  210. package/dist/truncator.d.ts +0 -118
  211. package/dist/utils-3ESwP3yg.cjs +0 -1075
  212. package/dist/utils-UBeAFeEI.js +0 -950
  213. /package/dist/{citations.d.ts → chat/citations.d.ts} +0 -0
  214. /package/dist/{citations.test.d.ts → chat/citations.test.d.ts} +0 -0
  215. /package/dist/{component.default.test.d.ts → chat/component.default.test.d.ts} +0 -0
  216. /package/dist/{compiler/plugins/track-tool-calls.test.d.ts → chat/component.test.d.ts} +0 -0
  217. /package/dist/{example.test.d.ts → chat/response.test.d.ts} +0 -0
  218. /package/dist/{exit-parser.test.d.ts → compiler/plugins/dynamic-code.test.d.ts} +0 -0
  219. /package/dist/{handlers.test.d.ts → compiler/plugins/tool-resolution.test.d.ts} +0 -0
  220. /package/dist/{hoist.test.d.ts → errors/catalog.test.d.ts} +0 -0
  221. /package/dist/{message-stream/instructions.test.d.ts → exit.test.d.ts} +0 -0
  222. /package/dist/{message-stream/normalizer.test.d.ts → inspection.test.d.ts} +0 -0
  223. /package/dist/{message-stream/parser.test.d.ts → prompts/native.test.d.ts} +0 -0
  224. /package/dist/{message-stream/response-parser.test.d.ts → result.test.d.ts} +0 -0
  225. /package/dist/{message-stream/stream.test.d.ts → runtime/chat-completion.test.d.ts} +0 -0
  226. /package/dist/{message-stream/validator.test.d.ts → runtime/chat-delivery.test.d.ts} +0 -0
  227. /package/dist/{prompts/adherence.test.d.ts → runtime/chat-last-speaker.test.d.ts} +0 -0
  228. /package/dist/{prompts/catalogue-examples.test.d.ts → runtime/compatibility-regressions.test.d.ts} +0 -0
  229. /package/dist/{prompts/code-examples.test.d.ts → runtime/context-registration.test.d.ts} +0 -0
  230. /package/dist/{prompts/common.test.d.ts → runtime/empty-completion.test.d.ts} +0 -0
  231. /package/dist/{prompts/concrete-patterns.test.d.ts → runtime/error-recovery.test.d.ts} +0 -0
  232. /package/dist/{prompts/long-search.test.d.ts → runtime/errors.test.d.ts} +0 -0
  233. /package/dist/{prompts/protocol-simple.test.d.ts → runtime/execution-activity.test.d.ts} +0 -0
  234. /package/dist/{prompts/protocol.test.d.ts → runtime/execution-diagnostics.test.d.ts} +0 -0
  235. /package/dist/{prompts/sections.test.d.ts → runtime/execution-report.test.d.ts} +0 -0
  236. /package/dist/runtime/{interpret-result.test.d.ts → execution-safety.test.d.ts} +0 -0
  237. /package/dist/{transcript.test.d.ts → runtime/exit-control-flow.test.d.ts} +0 -0
  238. /package/dist/{truncator.test.d.ts → runtime/fixtures/long-search.test.d.ts} +0 -0
package/dist/index.cjs CHANGED
@@ -1,200 +1,18 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
- const require_dual_modes = require("./dual-modes-DPXiuvNe.cjs");
3
- const require_common = require("./common-BnvrDnIT.cjs");
4
- const require_custom_client = require("./custom-client-DAsGRnYc.cjs");
5
- const require_utils = require("./utils-3ESwP3yg.cjs");
6
- const require_tool = require("./tool-Dy6AJpJH.cjs");
7
- const require_errors = require("./errors-C962uJdS.cjs");
8
- const require_typings = require("./typings-3lsqCbkn.cjs");
9
- const require_exit = require("./exit-DUM96DN1.cjs");
10
- const require_component = require("./component-C6Agl2ns.cjs");
11
- const require_truncator = require("./truncator-CLkouTCO.cjs");
12
- const require_quickjs_variant = require("./quickjs-variant-CsIwTVFC.cjs");
2
+ const require_utils = require("./utils-CTlsXvdj.cjs");
3
+ const require_errors = require("./errors-C6ppQUZX.cjs");
4
+ const require_component = require("./component-CMFoCHyu.cjs");
5
+ const require_tool = require("./tool-_wK9hQOb.cjs");
6
+ const require_exit = require("./exit-BOtKWPuT.cjs");
7
+ const require_truncate = require("./truncate-uomAMGPs.cjs");
8
+ const require_quickjs_variant = require("./quickjs-variant-21IO97PF.cjs");
9
+ const require_typings = require("./typings-BA_XxAcY.cjs");
10
+ const require_custom_client = require("./custom-client-Cgt9_0r1.cjs");
13
11
  let _bpinternal_zui = require("@bpinternal/zui");
14
12
  //#region package.json
15
- var version = "0.9.0";
16
- //#endregion
17
- //#region src/hoist.ts
18
- /**
19
- * Hoists object types (`{ ... }`) that appear more than once in a block of
20
- * typings into named `type` aliases, replacing every occurrence with a
21
- * reference. Runs repeatedly until a fixpoint so nested duplicates converge.
22
- */
23
- /** Prints a node tree back to text, preserving line structure (formatTypings normalizes later) */
24
- function printNodes(nodes) {
25
- let out = "";
26
- let afterLineComment = false;
27
- const emit = (n) => {
28
- const newlines = Math.min(n.nl ?? 0, 2);
29
- if (newlines > 0) out += "\n".repeat(newlines);
30
- else if (afterLineComment) out += "\n";
31
- else if (out.length && !out.endsWith("\n")) out += " ";
32
- afterLineComment = false;
33
- if (require_typings.isGroup(n)) {
34
- out += n.open;
35
- for (const child of n.children) emit(child);
36
- if (afterLineComment) {
37
- out += "\n";
38
- afterLineComment = false;
39
- }
40
- out += n.close;
41
- } else {
42
- out += n.text;
43
- afterLineComment = n.kind === "line-comment";
44
- }
45
- };
46
- for (const n of nodes) emit(n);
47
- return out;
48
- }
49
- /** Canonical structural key of a type literal: comments and separators ignored */
50
- function keyOf(group) {
51
- const parts = [];
52
- const visit = (n) => {
53
- if (require_typings.isGroup(n)) {
54
- parts.push(n.open);
55
- n.children.forEach(visit);
56
- parts.push(n.close);
57
- } else if (n.kind === "word" || n.kind === "string" || n.kind === "punct" && n.text !== ";" && n.text !== ",") parts.push(n.text);
58
- };
59
- visit(group);
60
- return parts.join(" ");
61
- }
62
- const prevMeaningful = (siblings, index) => {
63
- for (let i = index - 1; i >= 0; i--) {
64
- const n = siblings[i];
65
- if (require_typings.isGroup(n) || n.kind !== "block-comment" && n.kind !== "line-comment") return n;
66
- }
67
- };
68
- const asName = (text) => require_utils.upperFirst(text.replace(/['"]/g, "").replace(/[^A-Za-z0-9_$]/g, ""));
69
- /** The naming segment for a `{`/`<` group from its surrounding tokens (`key:`, `fn(...)`, `): `, `=>`) */
70
- function segmentsAt(siblings, index) {
71
- const prev = prevMeaningful(siblings, index);
72
- if (!prev || require_typings.isGroup(prev)) return [];
73
- if (require_typings.isPunct(prev, "=>")) return ["Output"];
74
- if (require_typings.isPunct(prev, ":") || require_typings.isPunct(prev, "<")) {
75
- var _kind;
76
- let i = siblings.indexOf(prev) - 1;
77
- while (i >= 0 && !require_typings.isGroup(siblings[i]) && ((_kind = siblings[i].kind) === null || _kind === void 0 ? void 0 : _kind.includes("comment"))) i--;
78
- let q = siblings[i];
79
- if (q && !require_typings.isGroup(q) && q.kind === "punct" && q.text === "?") q = siblings[--i];
80
- if (q && require_typings.isGroup(q) && q.open === "(") {
81
- const fnWord = prevMeaningful(siblings, i);
82
- return fnWord && !require_typings.isGroup(fnWord) && fnWord.kind === "word" ? [asName(fnWord.text), "Output"] : ["Output"];
83
- }
84
- if (q && !require_typings.isGroup(q) && (q.kind === "word" || q.kind === "string")) return [asName(q.text)];
85
- }
86
- return [];
87
- }
88
- /**
89
- * Visits every hoistable `{ ... }` type literal with its naming path. Value
90
- * objects (after `=`) are skipped — except `type X = { ... }` alias bodies,
91
- * which are visited with their alias name so they can act as the canonical
92
- * definition.
93
- */
94
- function walkLiterals(siblings, path, visit) {
95
- for (let i = 0; i < siblings.length; i++) {
96
- var _prevMeaningful;
97
- const node = siblings[i];
98
- if (!require_typings.isGroup(node)) continue;
99
- if (node.open === "(") {
100
- const fnWord = prevMeaningful(siblings, i);
101
- const fnName = fnWord && !require_typings.isGroup(fnWord) && fnWord.kind === "word" ? [asName(fnWord.text)] : [];
102
- walkLiterals(node.children, [...path, ...fnName], visit);
103
- continue;
104
- }
105
- if (node.open === "<" || node.open === "[") {
106
- walkLiterals(node.children, [...path, ...segmentsAt(siblings, i)], visit);
107
- continue;
108
- }
109
- const prev = prevMeaningful(siblings, i);
110
- if (prev && require_typings.isPunct(prev, "=")) {
111
- const eqIdx = siblings.indexOf(prev);
112
- const nameTok = siblings[eqIdx - 1];
113
- const typeTok = siblings[eqIdx - 2];
114
- if (!(nameTok && typeTok && !require_typings.isGroup(nameTok) && !require_typings.isGroup(typeTok) && nameTok.kind === "word" && typeTok.kind === "word" && typeTok.text === "type")) continue;
115
- const aliasName = nameTok.text;
116
- visit({
117
- siblings,
118
- index: i,
119
- group: node,
120
- path: [aliasName],
121
- aliasName
122
- });
123
- if (siblings[i] === node) walkLiterals(node.children, [aliasName], visit);
124
- continue;
125
- }
126
- const namespaceLike = prev && !require_typings.isGroup(prev) && prev.kind === "word" && ((_prevMeaningful = prevMeaningful(siblings, siblings.indexOf(prev))) === null || _prevMeaningful === void 0 ? void 0 : _prevMeaningful.kind) === "word" && ["namespace", "module"].includes(prevMeaningful(siblings, siblings.indexOf(prev)).text);
127
- const segments = segmentsAt(siblings, i);
128
- const newPath = [...path, ...segments];
129
- if (!namespaceLike) visit({
130
- siblings,
131
- index: i,
132
- group: node,
133
- path: newPath
134
- });
135
- if (siblings[i] === node) walkLiterals(node.children, namespaceLike ? [...path, asName(prev.text)] : newPath, visit);
136
- }
137
- }
138
- function extractAndHoistTypes(code) {
139
- const top = require_typings.parse(require_typings.tokenize(code));
140
- const counts = /* @__PURE__ */ new Map();
141
- const aliasByKey = /* @__PURE__ */ new Map();
142
- const usedNames = /* @__PURE__ */ new Set();
143
- walkLiterals(top, [], ({ group, path, aliasName }) => {
144
- const key = keyOf(group);
145
- counts.set(key, (counts.get(key) ?? 0) + 1);
146
- if (aliasName && !aliasByKey.has(key)) aliasByKey.set(key, aliasName);
147
- for (const segment of path) usedNames.add(segment);
148
- if (aliasName) usedNames.add(aliasName);
149
- });
150
- const uniqueName = (base) => {
151
- let name = base;
152
- let counter = 1;
153
- while (usedNames.has(name)) name = `${base}${counter++}`;
154
- usedNames.add(name);
155
- return name;
156
- };
157
- const newAliases = [];
158
- walkLiterals(top, [], ({ siblings, index, group, aliasName, path }) => {
159
- const key = keyOf(group);
160
- if ((counts.get(key) ?? 0) < 2 || aliasName) return;
161
- let name = aliasByKey.get(key);
162
- if (!name) {
163
- const deduped = [...new Set(path)];
164
- name = uniqueName(deduped.length ? deduped.join("") : "UnnamedType");
165
- aliasByKey.set(key, name);
166
- newAliases.push(`type ${name} = ${printNodes([{
167
- ...group,
168
- nl: 0
169
- }])}`);
170
- }
171
- siblings[index] = {
172
- kind: "word",
173
- text: name,
174
- nl: group.nl
175
- };
176
- });
177
- const body = printNodes(top);
178
- return newAliases.length ? `${newAliases.join("\n")}\n${body}` : body;
179
- }
180
- async function hoistTypings(code, formatOptions) {
181
- formatOptions ??= {};
182
- formatOptions.throwOnError ??= true;
183
- for (let i = 1; i <= 5; i++) try {
184
- const initialCode = code;
185
- code = extractAndHoistTypes(code);
186
- if (initialCode === code) break;
187
- } catch (err) {
188
- console.error(err);
189
- if (formatOptions.throwOnError) throw new require_errors.CodeFormattingError(err instanceof Error ? err.message : String(err ?? "Unknown Error"), code);
190
- break;
191
- }
192
- return require_typings.formatTypings(code, formatOptions);
193
- }
13
+ var version = "1.0.2";
194
14
  //#endregion
195
15
  //#region src/objects.ts
196
- /** How many lines of code an object needs to have before we insert a comment for end tag */
197
- const LARGE_OBJECT_LINES_OF_CODE = 10;
198
16
  /**
199
17
  * ObjectInstance creates stateful, namespace-scoped objects for LLMz agents.
200
18
  *
@@ -373,25 +191,6 @@ const LARGE_OBJECT_LINES_OF_CODE = 10;
373
191
  * })
374
192
  * ```
375
193
  *
376
- * ## TypeScript Integration
377
- *
378
- * Objects generate TypeScript namespace declarations:
379
- *
380
- * ```typescript
381
- * // Generated types for the LLM context:
382
- * export namespace user {
383
- * const name: Writable<string | null> = null
384
- * const age: Writable<number | null> = null
385
- * const id: Readonly<string> = "user_123"
386
- * }
387
- *
388
- * export namespace fs {
389
- * function readFile(args: { path: string }): Promise<string>
390
- * function writeFile(args: { path: string, content: string }): Promise<void>
391
- * }
392
- * ```
393
- *
394
- * @see {@link https://github.com/botpress/botpress/blob/master/packages/llmz/examples/09_chat_variables/index.ts} Example usage
395
194
  */
396
195
  var ObjectInstance = class {
397
196
  name;
@@ -457,18 +256,19 @@ var ObjectInstance = class {
457
256
  */
458
257
  constructor(props) {
459
258
  var _props$properties;
460
- if (!require_utils.isValidIdentifier(props.name)) throw new Error(`Invalid name for tool ${props.name}. A tool name must start with a letter and contain only letters, numbers, and underscores. It must be 1-50 characters long.`);
461
- if (props.description !== void 0 && typeof props.description !== "string") throw new Error(`Invalid description for tool ${props.name}. Expected a string, but got type "${typeof props.description}"`);
462
- if (props.metadata !== void 0 && typeof props.metadata !== "object") throw new Error(`Invalid metadata for tool ${props.name}. Expected an object, but got type "${typeof props.metadata}"`);
463
- if (props.properties !== void 0 && !Array.isArray(props.properties)) throw new Error(`Invalid properties for tool ${props.name}. Expected an array, but got type "${typeof props.properties}"`);
464
- if (props.tools !== void 0 && !Array.isArray(props.tools)) throw new Error(`Invalid tools for tool ${props.name}. Expected an array, but got type "${typeof props.tools}"`);
259
+ if (!props || typeof props !== "object" || Array.isArray(props)) throw new require_errors.InvalidObjectError("Object definition must be an object.");
260
+ if (!require_utils.isValidIdentifier(props.name)) throw new require_errors.InvalidObjectError(`Invalid name for tool ${props.name}. A tool name must start with a letter and contain only letters, numbers, and underscores. It must be 1-50 characters long.`);
261
+ if (props.description !== void 0 && typeof props.description !== "string") throw new require_errors.InvalidObjectError(`Invalid description for tool ${props.name}. Expected a string, but got type "${typeof props.description}"`);
262
+ if (props.metadata !== void 0 && typeof props.metadata !== "object") throw new require_errors.InvalidObjectError(`Invalid metadata for tool ${props.name}. Expected an object, but got type "${typeof props.metadata}"`);
263
+ if (props.properties !== void 0 && !Array.isArray(props.properties)) throw new require_errors.InvalidObjectError(`Invalid properties for tool ${props.name}. Expected an array, but got type "${typeof props.properties}"`);
264
+ if (props.tools !== void 0 && !Array.isArray(props.tools)) throw new require_errors.InvalidObjectError(`Invalid tools for tool ${props.name}. Expected an array, but got type "${typeof props.tools}"`);
465
265
  if ((_props$properties = props.properties) === null || _props$properties === void 0 ? void 0 : _props$properties.length) {
466
- if (props.properties.length > 100) throw new Error(`Too many properties for tool ${props.name}. Expected at most 100 properties, but got ${props.properties.length}`);
266
+ if (props.properties.length > 100) throw new require_errors.InvalidObjectError(`Too many properties for tool ${props.name}. Expected at most 100 properties, but got ${props.properties.length}`);
467
267
  for (const prop of props.properties) {
468
- if (props.properties.filter((p) => p.name === prop.name).length > 1) throw new Error(`Duplicate property name "${prop.name}" in tool ${props.name}`);
469
- if (!require_utils.isValidIdentifier(prop.name)) throw new Error(`Invalid name for property ${prop.name}. A property name must start with a letter and contain only letters, numbers, and underscores. It must be 1-50 characters long.`);
470
- if (prop.description !== void 0 && typeof prop.description !== "string") throw new Error(`Invalid description for property ${prop.name}. Expected a string, but got type "${typeof prop.description}"`);
471
- if (props.description && props.description.length >= 5e3) throw new Error(`Description for property ${prop.name} is too long. Expected at most 5000 characters, but got ${props.description.length}`);
268
+ if (props.properties.filter((p) => p.name === prop.name).length > 1) throw new require_errors.InvalidObjectError(`Duplicate property name "${prop.name}" in tool ${props.name}`);
269
+ if (!require_utils.isValidIdentifier(prop.name)) throw new require_errors.InvalidObjectError(`Invalid name for property ${prop.name}. A property name must start with a letter and contain only letters, numbers, and underscores. It must be 1-50 characters long.`);
270
+ if (prop.description !== void 0 && typeof prop.description !== "string") throw new require_errors.InvalidObjectError(`Invalid description for property ${prop.name}. Expected a string, but got type "${typeof prop.description}"`);
271
+ if (props.description && props.description.length >= 5e3) throw new require_errors.InvalidObjectError(`Description for property ${prop.name} is too long. Expected at most 5000 characters, but got ${props.description.length}`);
472
272
  if (typeof prop.writable !== "boolean") prop.writable = false;
473
273
  }
474
274
  }
@@ -478,45 +278,17 @@ var ObjectInstance = class {
478
278
  this.properties = props.properties;
479
279
  this.tools = require_tool.Tool.withUniqueNames(props.tools ?? []);
480
280
  }
481
- /**
482
- * Generates TypeScript namespace declarations for this object.
483
- *
484
- * This method creates TypeScript definitions that are included in the LLM context
485
- * to help it understand the available properties and tools. Properties become
486
- * const declarations with appropriate Readonly/Writable types, and tools become
487
- * function signatures.
488
- *
489
- * @returns Promise resolving to TypeScript namespace declaration
490
- *
491
- * @example
492
- * ```typescript
493
- * const obj = new ObjectInstance({
494
- * name: 'user',
495
- * properties: [
496
- * { name: 'name', value: 'John', writable: true },
497
- * { name: 'id', value: 123, writable: false },
498
- * ],
499
- * tools: [
500
- * new Tool({
501
- * name: 'save',
502
- * input: z.object({ data: z.string() }),
503
- * handler: async ({ data }) => { /* ... *\/ },
504
- * }),
505
- * ],
506
- * })
507
- *
508
- * const typings = await obj.getTypings()
509
- * console.log(typings)
510
- * // Output:
511
- * // export namespace user {
512
- * // const name: Writable<string> = "John"
513
- * // const id: Readonly<number> = 123
514
- * // function save(args: { data: string }): Promise<void>
515
- * // }
516
- * ```
517
- */
518
- async getTypings() {
519
- return getObjectTypings(this).withProperties().withTools().build();
281
+ /** Callable API only. Property values, schemas, and access rules belong in Memory. */
282
+ async getToolTypings() {
283
+ var _this$description;
284
+ const declarations = [];
285
+ for (const tool of this.tools ?? []) {
286
+ const declaration = await tool.getTypings();
287
+ declarations.push(declaration.replace("declare function ", "function "));
288
+ }
289
+ const description = ((_this$description = this.description) === null || _this$description === void 0 ? void 0 : _this$description.trim()) ? require_utils.getMultilineComment(this.description) : "";
290
+ const body = declarations.join("\n\n");
291
+ return require_typings.formatTypings(`${description}\nexport namespace ${this.name} {\n${body}\n}`, { throwOnError: false });
520
292
  }
521
293
  /**
522
294
  * Converts this ObjectInstance to its JSON representation.
@@ -537,123 +309,36 @@ var ObjectInstance = class {
537
309
  };
538
310
  }
539
311
  };
312
+ //#endregion
313
+ //#region src/chat/chat.ts
540
314
  /**
541
- * Creates a TypeScript namespace builder for an ObjectInstance.
542
- *
543
- * This function provides a fluent API for generating TypeScript declarations
544
- * that include properties, tools, or both. It's used internally by ObjectInstance.getTypings().
545
- *
546
- * @param obj - The ObjectInstance to generate typings for
547
- * @returns A builder object with methods to configure and build the namespace
548
- * @internal
549
- */
550
- function getObjectTypings(obj) {
551
- let includeProperties = false;
552
- let includeTools = false;
553
- let hoisting = false;
554
- const typings = [];
555
- const addProperties = async () => {
556
- var _obj$properties;
557
- if (includeProperties && ((_obj$properties = obj.properties) === null || _obj$properties === void 0 ? void 0 : _obj$properties.length)) {
558
- typings.push("");
559
- typings.push("// ---------------- //");
560
- typings.push("// Properties //");
561
- typings.push("// ---------------- //");
562
- typings.push("");
563
- for (const prop of obj.properties ?? []) {
564
- const description = prop.description ?? "";
565
- if (description === null || description === void 0 ? void 0 : description.trim().length) typings.push(require_utils.getMultilineComment(description));
566
- let type = "unknown";
567
- if (prop.type) type = await require_typings.getTypings(prop.type, {});
568
- else if (prop.value !== void 0) type = typeof prop.value;
569
- type = prop.writable ? `Writable<${type}>` : `Readonly<${type}>`;
570
- const value = embedPropertyValue(prop);
571
- typings.push(`const ${prop.name}: ${type} = ${value}`);
572
- }
573
- }
574
- };
575
- const addTools = async () => {
576
- var _obj$tools;
577
- if (includeTools && ((_obj$tools = obj.tools) === null || _obj$tools === void 0 ? void 0 : _obj$tools.length)) {
578
- typings.push("");
579
- typings.push("// ---------------- //");
580
- typings.push("// Tools //");
581
- typings.push("// ---------------- //");
582
- typings.push("");
583
- for (const tool of obj.tools) {
584
- const fnType = _bpinternal_zui.z.function(tool.zInput, tool.zOutput).title(tool.name).describe(tool.description ?? "");
585
- let temp = await require_typings.getTypings(fnType, { declaration: true });
586
- temp = temp.replace("declare function ", "function ");
587
- typings.push(temp);
588
- }
589
- }
590
- };
591
- const finalize = async () => {
592
- var _obj$description;
593
- let closingBracket = "";
594
- if (typings.length >= LARGE_OBJECT_LINES_OF_CODE) closingBracket = ` // end namespace "${obj.name}"`;
595
- let body = typings.join("\n");
596
- if (hoisting) body = await hoistTypings(body, { throwOnError: false });
597
- typings.push("}" + closingBracket);
598
- let header = "";
599
- if ((_obj$description = obj.description) === null || _obj$description === void 0 ? void 0 : _obj$description.trim().length) header = require_utils.getMultilineComment(obj.description);
600
- return require_typings.formatTypings(`${header}
601
- export namespace ${obj.name} {
602
- ${body}
603
- } ${closingBracket}`.trim(), { throwOnError: false });
604
- };
605
- const api = {
606
- withProperties: () => {
607
- includeProperties = true;
608
- return api;
609
- },
610
- withTools: () => {
611
- includeTools = true;
612
- return api;
613
- },
614
- withHoisting: () => {
615
- hoisting = true;
616
- return api;
617
- },
618
- async build() {
619
- await addProperties();
620
- await addTools();
621
- return finalize();
622
- }
623
- };
624
- return api;
625
- }
626
- /**
627
- * Converts a property value to its TypeScript literal representation.
315
+ * Connects native assistant replies and rich components to the host application.
628
316
  *
629
- * This function handles the serialization of various JavaScript types into
630
- * TypeScript code that can be embedded in generated namespace declarations.
631
- * It supports primitives, objects, arrays, dates, regex, and other common types.
317
+ * `response` controls how all assistant text is written. It does not create a
318
+ * JavaScript method or synthesize audio. `components` registers only rich UI
319
+ * methods such as chat.buttons or chat.image.
632
320
  *
633
- * @param property - The ObjectProperty containing the value to embed
634
- * @returns String representation of the value for use in TypeScript code
635
- * @internal
321
+ * Streamed deltas are provisional. After successful generation, the response
322
+ * handler receives the complete text with the same message ID. Each component
323
+ * owns its delivery handler. Without response callbacks, text remains available
324
+ * in the native session history.
636
325
  */
637
- function embedPropertyValue(property) {
638
- if (typeof property.value === "string") return require_utils.escapeString(property.value);
639
- if (Number.isNaN(property.value)) return "NaN";
640
- if (typeof property.value === "number" && Number.isInteger(property.value)) return property.value.toString();
641
- if (typeof property.value === "boolean") return property.value.toString();
642
- if (Array.isArray(property.value) || typeof property.value === "object") return JSON.stringify(property.value);
643
- if (property.value instanceof Date) return `new Date('${property.value.toISOString()}')`;
644
- if (property.value instanceof RegExp) return `new RegExp(${require_utils.escapeString(property.value.source)}, ${require_utils.escapeString(property.value.flags)})`;
645
- if (property.value === null) return "null";
646
- if (property.value === void 0) return "undefined";
647
- if (typeof property.value === "function") return "function() {}";
648
- if (typeof property.value === "symbol") return "Symbol()";
649
- if (typeof property.value === "bigint") return `${property.value}n`;
650
- if (property.value instanceof Error) return `Error(${require_utils.escapeString(property.value.message)})`;
651
- if (property.value instanceof Map) return `new Map(${JSON.stringify(Array.from(property.value.entries()))})`;
652
- if (property.value instanceof Set) return `new Set(${JSON.stringify(Array.from(property.value.values()))})`;
653
- return "unknown";
654
- }
326
+ var Chat = class {
327
+ components;
328
+ response;
329
+ constructor(props = {}) {
330
+ if (!props || typeof props !== "object" || Array.isArray(props)) throw new require_errors.InvalidConfigurationError("Chat configuration must be an object.");
331
+ if ("handler" in props || "onMessageDelta" in props) throw new require_errors.InvalidConfigurationError("Use response.handler and response.onDelta for text, and component handlers for rich messages.");
332
+ const unknown = Object.keys(props).find((key) => !["components", "response"].includes(key));
333
+ if (unknown) throw new require_errors.InvalidConfigurationError(`Unknown Chat option: ${unknown}.`);
334
+ this.components = props.components ?? [];
335
+ this.response = props.response === void 0 ? "markdown" : props.response;
336
+ }
337
+ /** Called after an execution completes or fails. */
338
+ onExecutionDone(_result) {}
339
+ };
655
340
  //#endregion
656
- //#region src/citations.ts
341
+ //#region src/chat/citations.ts
657
342
  /** These are all single-token symbols that are very rare in natural texts, making them suitable for usage within GPT Prompts. */
658
343
  const RARE_SYMBOLS = {
659
344
  ARROW_UP: "↑",
@@ -792,854 +477,95 @@ var CitationsManager = class {
792
477
  }
793
478
  };
794
479
  //#endregion
795
- //#region src/component.default.ts
796
- const Button = new require_component.Component({
797
- type: "leaf",
798
- description: "A button component that can perform actions when clicked",
799
- name: "Button",
800
- aliases: ["btn"],
801
- generation: {
802
- usage: "Offer quick actions or choices after a message. It is common to send several buttons together: write one separate ■send=button block per choice in the SAME response. Each button has its own props and no body. Send all the choices before the final exit; do not wait for a user reply between buttons.",
803
- examples: [
804
- { props: {
805
- action: "say",
806
- label: "Track my order"
807
- } },
808
- { props: {
809
- action: "url",
810
- label: "View guide",
811
- url: "https://example.com/guide"
812
- } },
813
- { props: {
814
- action: "postback",
815
- label: "Choose Standard",
816
- value: "plan_standard"
817
- } },
818
- [
819
- { props: {
820
- action: "say",
821
- label: "Track my order"
822
- } },
823
- { props: {
824
- action: "say",
825
- label: "Return an item"
826
- } },
827
- { props: {
828
- action: "say",
829
- label: "Contact support"
830
- } }
831
- ]
832
- ]
833
- },
834
- leaf: { props: _bpinternal_zui.z.object({
835
- action: _bpinternal_zui.z.enum([
836
- "say",
837
- "url",
838
- "postback"
839
- ]).default("say").describe("The action to perform when the button is clicked. Can be \"say\", \"url\", or \"postback\""),
840
- label: _bpinternal_zui.z.string().describe("The text displayed on the button (min 1 character, max 250 characters)"),
841
- value: _bpinternal_zui.z.string().optional().describe("The postback value to send when the button is clicked. Required if action is \"postback\""),
842
- url: _bpinternal_zui.z.string().optional().describe("The URL to open when the button is clicked. Required if action is \"url\"")
843
- }) }
844
- });
845
- const Image = new require_component.Component({
846
- type: "leaf",
847
- name: "Image",
848
- description: "Displays an image from a URL.",
849
- aliases: [],
850
- generation: {
851
- usage: "Use a known image URL from the user or tool results; never invent an image URL. No body.",
852
- examples: [{ props: {
853
- url: "https://example.com/trail.jpg",
854
- alt: "Forest trail beside a lake"
855
- } }]
856
- },
857
- leaf: { props: _bpinternal_zui.z.object({
858
- url: _bpinternal_zui.z.string().describe("The URL of the image (must be valid)"),
859
- alt: _bpinternal_zui.z.string().optional().describe("Alternative text describing the image")
860
- }) }
861
- });
862
- const File = new require_component.Component({
863
- type: "leaf",
864
- name: "File",
865
- description: "Sends a downloadable file to the user.",
866
- aliases: [],
867
- generation: { examples: [{ props: {
868
- url: "https://example.com/report.pdf",
869
- name: "Report.pdf"
870
- } }] },
871
- leaf: { props: _bpinternal_zui.z.object({
872
- url: _bpinternal_zui.z.string().describe("The URL of the file (must be valid)"),
873
- name: _bpinternal_zui.z.string().optional().describe("The display name of the file")
874
- }) }
875
- });
876
- const Video = new require_component.Component({
877
- type: "leaf",
878
- name: "Video",
879
- description: "Embeds a video from a URL.",
880
- aliases: [],
881
- generation: { examples: [{ props: {
882
- url: "https://example.com/intro.mp4",
883
- title: "Welcome"
884
- } }] },
885
- leaf: { props: _bpinternal_zui.z.object({
886
- url: _bpinternal_zui.z.string().describe("The URL of the video (must be valid)"),
887
- title: _bpinternal_zui.z.string().optional().describe("Title for the video")
888
- }) }
889
- });
890
- const Audio = new require_component.Component({
891
- type: "leaf",
892
- name: "Audio",
893
- description: "Plays an audio clip from a URL.",
894
- aliases: [],
895
- generation: { examples: [{ props: {
896
- url: "https://example.com/audio.mp3",
897
- title: "Sample"
898
- } }] },
899
- leaf: { props: _bpinternal_zui.z.object({
900
- url: _bpinternal_zui.z.string().describe("The URL of the audio clip (must be valid)"),
901
- title: _bpinternal_zui.z.string().optional().describe("Title for the audio clip")
902
- }) }
903
- });
904
- const Card = new require_component.Component({
905
- type: "container",
906
- name: "Card",
907
- description: "A card with a title, optional subtitle, and Markdown body.",
908
- aliases: [],
909
- generation: {
910
- usage: "Present one item. The block body is Markdown, not nested component blocks or JSX.",
911
- examples: [{
912
- props: {
913
- title: "Standard plan",
914
- subtitle: "$20/month"
915
- },
916
- body: "Includes 5 projects and email support."
917
- }]
918
- },
919
- container: {
920
- props: _bpinternal_zui.z.object({
921
- title: _bpinternal_zui.z.string().min(1).max(250).describe("Title text (1–250 characters)"),
922
- subtitle: _bpinternal_zui.z.string().optional().describe("Optional subtitle for the card")
923
- }),
924
- children: [{
925
- description: "Image (optional, max 1)",
926
- component: Image.definition
927
- }, {
928
- description: "Button (optional, up to 5)",
929
- component: Button.definition
930
- }]
931
- }
932
- });
933
- const carouselProps = _bpinternal_zui.z.object({ cards: _bpinternal_zui.z.array(Card.definition.container.props.extend({
934
- body: _bpinternal_zui.z.string().optional().describe("Markdown text for this card"),
935
- image: Image.definition.leaf.props.optional().describe("Optional image for this card; use a known URL"),
936
- buttons: _bpinternal_zui.z.array(Button.definition.leaf.props).max(5).optional().describe("Up to 5 actions for this card")
937
- })).min(1).max(10).describe("1–10 cards, in display order. Each card has its own title, optional subtitle, body, image, and buttons") });
938
- var CarouselComponent = class extends require_component.Component {
939
- render(props, children = []) {
940
- if (!("cards" in props) && children.length && children.every((child) => require_component.isComponent(child, Card))) return super.render(props, children);
941
- const { cards } = carouselProps.parse(props);
942
- const renderedCards = cards.map(({ body, image, buttons, ...cardProps }) => Card.render(cardProps, [
943
- ...body ? [body] : [],
944
- ...image ? [Image.render(image)] : [],
945
- ...(buttons ?? []).map((button) => Button.render(button))
946
- ]));
947
- return super.render({}, renderedCards);
948
- }
949
- };
480
+ //#region src/chat/component.default.ts
481
+ const buttonProps = _bpinternal_zui.z.object({
482
+ action: _bpinternal_zui.z.enum([
483
+ "say",
484
+ "url",
485
+ "postback"
486
+ ]).default("say").describe("The action to perform when the button is clicked: say, url, or postback"),
487
+ label: _bpinternal_zui.z.string().min(1).max(250).describe("The text displayed on the button (1–250 characters)"),
488
+ value: _bpinternal_zui.z.string().optional().describe("The postback value. Required when action is postback"),
489
+ url: _bpinternal_zui.z.string().optional().describe("The URL to open. Required when action is url")
490
+ }).strict();
491
+ const imageProps = _bpinternal_zui.z.object({
492
+ url: _bpinternal_zui.z.string().describe("The URL of the image (must be valid)"),
493
+ alt: _bpinternal_zui.z.string().optional().describe("Alternative text describing the image")
494
+ }).strict();
495
+ const cardProps = _bpinternal_zui.z.object({
496
+ title: _bpinternal_zui.z.string().min(1).max(250).describe("Title text (1–250 characters)"),
497
+ subtitle: _bpinternal_zui.z.string().optional().describe("Optional subtitle for the card"),
498
+ text: _bpinternal_zui.z.string().optional().describe("Optional Markdown text for the card"),
499
+ image: imageProps.optional().describe("Optional image for the card; use a known URL"),
500
+ buttons: _bpinternal_zui.z.array(buttonProps).max(5).optional().describe("Up to 5 actions for the card")
501
+ }).strict();
950
502
  const DefaultComponents = {
951
- Button,
952
- Image,
953
- File,
954
- Video,
955
- Audio,
956
- Card,
957
- Carousel: new CarouselComponent({
958
- type: "container",
959
- name: "Carousel",
960
- description: "Displays a horizontally scrollable collection of cards, each with its own content and actions.",
961
- aliases: [],
962
- body: false,
963
- generation: {
964
- usage: "Use for several comparable items. Put ALL cards in the cards array of ONE send block. Each card can include title, subtitle, body, image {url, alt?}, and buttons [{action, label, value?, url?}]. Do not write a Markdown list or separate Card blocks; those do not form a carousel.",
965
- examples: [{ props: { cards: [{
966
- title: "Standard plan",
967
- subtitle: "$20/month",
968
- body: "5 projects and email support.",
969
- image: {
970
- url: "https://example.com/standard.jpg",
971
- alt: "Standard plan"
972
- },
973
- buttons: [{
974
- action: "postback",
975
- label: "Choose Standard",
976
- value: "plan_standard"
977
- }]
978
- }, {
979
- title: "Team plan",
980
- subtitle: "$50/month",
981
- body: "20 projects and priority support.",
982
- image: {
983
- url: "https://example.com/team.jpg",
984
- alt: "Team plan"
985
- },
986
- buttons: [{
987
- action: "postback",
988
- label: "Choose Team",
989
- value: "plan_team"
990
- }]
991
- }] } }]
992
- },
993
- container: {
994
- props: carouselProps,
995
- children: [{
996
- description: "Card component (required, 1–10 allowed)",
997
- component: Card.definition
998
- }]
999
- }
503
+ Buttons: new require_component.Component({
504
+ name: "buttons",
505
+ description: "Offer quick actions or choices after a message. Buttons appear together in array order.",
506
+ props: _bpinternal_zui.z.array(buttonProps).min(1)
1000
507
  }),
1001
- Text: new require_component.Component({
1002
- type: "default",
1003
- name: "Message",
1004
- aliases: ["Text", "Markdown"],
1005
- description: "A Markdown-formatted text message. Long answers are written the same way: plain Markdown prose.",
1006
- generation: { examples: [{ body: `To reset your password:
1007
-
1008
- 1. Open the sign-in page and select **Forgot password?**
1009
- 2. Enter the email address you use for your account.
1010
- 3. Open the reset link in your email and choose a new password.
1011
-
1012
- If the email does not arrive, check your spam folder. If you sign in through your organization, use its password reset process.` }, { body: "How do you currently manage board meetings?" }] },
1013
- default: {
1014
- props: _bpinternal_zui.z.object({}),
1015
- children: []
1016
- }
508
+ Image: new require_component.Component({
509
+ name: "image",
510
+ description: "Display an image using a known URL from the user or tool results; never invent an image URL.",
511
+ props: imageProps
1017
512
  }),
1018
- Speech: new require_component.Component({
1019
- type: "default",
1020
- name: "Speech",
1021
- aliases: ["speak", "spoken"],
1022
- description: "A message spoken aloud to the user via text-to-speech.",
1023
- body: {
1024
- format: "text",
1025
- description: "Plain conversational prose only, written to be read aloud: no Markdown, no links or URLs, no emojis, no code, no bullet points, tables or headings. Write everything the way it should be pronounced — spell out numbers, dates, units and abbreviations (e.g. \"June third at three thirty PM\", not \"06/03 @ 3:30pm\")."
1026
- },
1027
- generation: {
1028
- usage: "Use when the reply will be played back as audio (voice conversations).",
1029
- examples: [{ body: "Sure! Your order shipped this morning and should arrive on Tuesday, June third, around noon." }]
1030
- },
1031
- default: {
1032
- props: _bpinternal_zui.z.object({}),
1033
- children: []
1034
- }
513
+ File: new require_component.Component({
514
+ name: "file",
515
+ description: "Send a downloadable file to the user.",
516
+ props: _bpinternal_zui.z.object({
517
+ url: _bpinternal_zui.z.string().describe("The URL of the file (must be valid)"),
518
+ name: _bpinternal_zui.z.string().optional().describe("The display name of the file")
519
+ }).strict()
520
+ }),
521
+ Video: new require_component.Component({
522
+ name: "video",
523
+ description: "Embed a video from a URL.",
524
+ props: _bpinternal_zui.z.object({
525
+ url: _bpinternal_zui.z.string().describe("The URL of the video (must be valid)"),
526
+ title: _bpinternal_zui.z.string().optional().describe("Title for the video")
527
+ }).strict()
528
+ }),
529
+ Audio: new require_component.Component({
530
+ name: "audio",
531
+ description: "Play an audio clip from a URL.",
532
+ props: _bpinternal_zui.z.object({
533
+ url: _bpinternal_zui.z.string().describe("The URL of the audio clip (must be valid)"),
534
+ title: _bpinternal_zui.z.string().optional().describe("Title for the audio clip")
535
+ }).strict()
536
+ }),
537
+ Card: new require_component.Component({
538
+ name: "card",
539
+ description: "Present one item with a title, optional subtitle, Markdown text, image, and buttons.",
540
+ props: cardProps
541
+ }),
542
+ Carousel: new require_component.Component({
543
+ name: "carousel",
544
+ description: "Display several comparable items as a horizontally scrollable collection of cards.",
545
+ props: _bpinternal_zui.z.object({ cards: _bpinternal_zui.z.array(cardProps).min(1).max(10).describe("1–10 cards in display order, each with its own content and actions") }).strict()
1035
546
  })
1036
547
  };
1037
548
  //#endregion
1038
- //#region src/chat.ts
1039
- /**
1040
- * Base class for implementing chat interfaces in LLMz agents.
1041
- *
1042
- * The Chat class provides the foundation for interactive conversational agents by defining
1043
- * how agents communicate with users. It manages the conversation transcript, available UI
1044
- * components, and message handling. This is the bridge between the agent's generated code
1045
- * and your user interface.
1046
- *
1047
- * ## Key Concepts
1048
- *
1049
- * **Handler Function**: The core method that receives agent messages (rendered components)
1050
- * and displays them to the user. This is called every time the agent wants to communicate.
1051
- *
1052
- * **Transcript**: An up-to-date conversation history that is evaluated at each iteration.
1053
- * The transcript must reflect the complete conversation state as the agent uses it to
1054
- * understand context and generate appropriate responses.
1055
- *
1056
- * **Components**: The UI elements available to the agent for creating rich interactive
1057
- * experiences (text, buttons, images, cards, etc.).
1058
- *
1059
- * ## Implementation Requirements
1060
- *
1061
- * To create a functional chat interface, you must:
1062
- * 1. Implement the MessageHandler to display agent messages to users
1063
- * 2. Maintain an accurate transcript of the conversation
1064
- * 3. Provide the available UI components (typically includes DefaultComponents)
1065
- * 4. Optional: Override onExecutionDone() to handle execution completion
1066
- *
1067
- * ## Basic Implementation
1068
- *
1069
- * ```typescript
1070
- * import { Chat, DefaultComponents, isComponent } from 'llmz'
1071
- *
1072
- * class MyChat extends Chat {
1073
- * private messages: Array<{role: 'user' | 'assistant', content: string}> = []
1074
- *
1075
- * constructor() {
1076
- * super({
1077
- * // Handle agent messages - this is called for every agent output
1078
- * handler: async (input) => {
1079
- * if (isComponent(input, DefaultComponents.Text)) {
1080
- * const text = input.children.join('')
1081
- * console.log('Agent:', text)
1082
- * this.messages.push({ role: 'assistant', content: text })
1083
- * } else if (isComponent(input, DefaultComponents.Button)) {
1084
- * console.log('Button:', input.props.label)
1085
- * }
1086
- * },
1087
- *
1088
- * // Provide available components - agent can use these in generated code
1089
- * components: [DefaultComponents.Text, DefaultComponents.Button],
1090
- *
1091
- * // Return current transcript - evaluated at each iteration
1092
- * transcript: () => this.messages,
1093
- * })
1094
- * }
1095
- *
1096
- * // Add user message to transcript
1097
- * addUserMessage(content: string) {
1098
- * this.messages.push({ role: 'user', content })
1099
- * }
1100
- * }
1101
- *
1102
- * // Usage
1103
- * const chat = new MyChat()
1104
- * chat.addUserMessage('Hello!')
1105
- *
1106
- * const result = await execute({
1107
- * instructions: 'You are a helpful assistant',
1108
- * chat, // Enable chat mode
1109
- * client,
1110
- * })
1111
- * ```
1112
- *
1113
- * ## Advanced Implementation (CLIChat Example)
1114
- *
1115
- * ```typescript
1116
- * import { Chat, DefaultComponents, ListenExit } from 'llmz'
1117
- *
1118
- * class CLIChat extends Chat {
1119
- * public transcript: Array<{role: 'user' | 'assistant', content: string}> = []
1120
- * private buttons: string[] = []
1121
- * public result?: ExecutionResult
1122
- *
1123
- * constructor() {
1124
- * super({
1125
- * // Dynamic component list with custom renderers
1126
- * components: () => [
1127
- * DefaultComponents.Text,
1128
- * DefaultComponents.Button,
1129
- * ...this.customComponents
1130
- * ],
1131
- *
1132
- * // Dynamic transcript access
1133
- * transcript: () => this.transcript,
1134
- *
1135
- * // Sophisticated message handling
1136
- * handler: async (input) => {
1137
- * if (isComponent(input, DefaultComponents.Text)) {
1138
- * const text = input.children.join('')
1139
- * console.log('🤖 Agent:', text)
1140
- * this.transcript.push({ role: 'assistant', content: text })
1141
- * } else if (isComponent(input, DefaultComponents.Button)) {
1142
- * this.buttons.push(input.props.label)
1143
- * }
1144
- * },
1145
- * })
1146
- * }
1147
- *
1148
- * // Handle execution completion
1149
- * onExecutionDone(result: ExecutionResult) {
1150
- * this.result = result
1151
- * }
1152
- *
1153
- * // Check if agent is waiting for user input
1154
- * isWaitingForInput(): boolean {
1155
- * return this.result?.is(ListenExit) ?? false
1156
- * }
1157
- *
1158
- * // Conversation loop
1159
- * async iterate(): Promise<boolean> {
1160
- * if (this.isWaitingForInput()) {
1161
- * const userInput = await this.promptUser()
1162
- * this.transcript.push({ role: 'user', content: userInput })
1163
- * return true // Continue conversation
1164
- * }
1165
- * return false // End conversation
1166
- * }
1167
- * }
1168
- * ```
1169
- *
1170
- * ## Component System
1171
- *
1172
- * The agent generates JSX code using available components:
1173
- *
1174
- * ```typescript
1175
- * // Agent generates this TSX code:
1176
- * yield <Text>Welcome! Choose an option:</Text>
1177
- * yield <Button action="postback" label="Get Help" value="help" />
1178
- * yield <Button action="postback" label="Contact Sales" value="sales" />
1179
- *
1180
- * // Your handler receives these as RenderedComponent objects
1181
- * ```
1182
- *
1183
- * ## Transcript Management
1184
- *
1185
- * The transcript is critical for agent context and must be kept up-to-date:
1186
- *
1187
- * ```typescript
1188
- * // ❌ Bad - static transcript
1189
- * transcript: [{ role: 'user', content: 'Hello' }]
1190
- *
1191
- * // ✅ Good - dynamic transcript that reflects current state
1192
- * transcript: () => this.messages
1193
- *
1194
- * // The transcript is evaluated at each iteration, so the agent
1195
- * // always sees the current conversation state
1196
- * ```
1197
- *
1198
- * ## Custom Components
1199
- *
1200
- * Extend the UI with custom components for your specific use case:
1201
- *
1202
- * ```typescript
1203
- * import { Component } from 'llmz'
1204
- *
1205
- * const ProductCard = new Component({
1206
- * type: 'leaf',
1207
- * name: 'ProductCard',
1208
- * leaf: {
1209
- * props: z.object({
1210
- * name: z.string(),
1211
- * price: z.number(),
1212
- * imageUrl: z.string(),
1213
- * })
1214
- * }
1215
- * })
1216
- *
1217
- * class ShoppingChat extends Chat {
1218
- * constructor() {
1219
- * super({
1220
- * components: [
1221
- * ...DefaultComponents,
1222
- * ProductCard, // Add custom component
1223
- * ],
1224
- * handler: async (input) => {
1225
- * if (isComponent(input, ProductCard)) {
1226
- * // Handle custom component rendering
1227
- * this.renderProduct(input.props)
1228
- * }
1229
- * // ... handle other components
1230
- * },
1231
- * })
1232
- * }
1233
- * }
1234
- * ```
1235
- *
1236
- * @see {@link DefaultComponents} For standard UI components
1237
- * @see {@link https://github.com/botpress/botpress/blob/master/packages/llmz/examples/utils/cli-chat.ts} Complete CLIChat implementation
1238
- */
1239
- var Chat = class {
1240
- handler;
1241
- onMessageDelta;
1242
- transcript;
1243
- components;
1244
- /**
1245
- * Creates a new Chat instance.
1246
- *
1247
- * @param props - Chat configuration
1248
- * @param props.handler - Function to handle agent messages (called for every agent output)
1249
- * @param props.components - Available UI components (static array or dynamic function)
1250
- * @param props.transcript - Conversation history (static array or dynamic function, defaults to empty)
1251
- *
1252
- * @example
1253
- * ```typescript
1254
- * // Basic chat with static configuration
1255
- * const chat = new Chat({
1256
- * handler: async (input) => {
1257
- * if (isComponent(input, DefaultComponents.Text)) {
1258
- * console.log('Agent:', input.children.join(''))
1259
- * }
1260
- * },
1261
- * components: [DefaultComponents.Text, DefaultComponents.Button],
1262
- * transcript: [
1263
- * { role: 'user', content: 'Hello', timestamp: Date.now() }
1264
- * ],
1265
- * })
1266
- * ```
1267
- *
1268
- * @example
1269
- * ```typescript
1270
- * // Dynamic chat with functions for real-time updates
1271
- * class MyChat extends Chat {
1272
- * private messages: Transcript.Message[] = []
1273
- *
1274
- * constructor() {
1275
- * super({
1276
- * handler: (input) => this.handleMessage(input),
1277
- *
1278
- * // Dynamic components - can change during execution
1279
- * components: () => [
1280
- * DefaultComponents.Text,
1281
- * DefaultComponents.Button,
1282
- * ...this.getCustomComponents()
1283
- * ],
1284
- *
1285
- * // Dynamic transcript - always reflects current state
1286
- * transcript: () => this.messages,
1287
- * })
1288
- * }
1289
- * }
1290
- * ```
1291
- */
1292
- constructor(props) {
1293
- this.handler = props.handler;
1294
- this.onMessageDelta = props.onMessageDelta;
1295
- this.components = props.components;
1296
- this.transcript = props.transcript || [];
1297
- }
1298
- /**
1299
- * Called when an execution cycle completes, regardless of the outcome.
1300
- *
1301
- * Override this method to handle execution results, manage conversation flow,
1302
- * or perform cleanup tasks. This is called after each `execute()` call completes,
1303
- * whether it succeeds, fails, or is interrupted.
1304
- *
1305
- * @param result - The execution result containing status, iterations, and exit information
1306
- *
1307
- * @example
1308
- * ```typescript
1309
- * class MyChat extends Chat {
1310
- * public result?: ExecutionResult
1311
- *
1312
- * onExecutionDone(result: ExecutionResult) {
1313
- * // Store result for conversation flow control
1314
- * this.result = result
1315
- *
1316
- * // Handle different result types
1317
- * if (result.isSuccess()) {
1318
- * console.log('✅ Execution completed successfully')
1319
- * console.log('Exit:', result.output.exit_name)
1320
- * } else if (result.isError()) {
1321
- * console.error('❌ Execution failed:', result.output.error)
1322
- * } else if (result.isInterrupted()) {
1323
- * console.log('⏸️ Execution interrupted (partial result)')
1324
- * }
1325
- * }
1326
- *
1327
- * // Use stored result for conversation flow
1328
- * isWaitingForInput(): boolean {
1329
- * return this.result?.is(ListenExit) ?? false
1330
- * }
1331
- * }
1332
- * ```
1333
- *
1334
- * @example
1335
- * ```typescript
1336
- * // CLIChat implementation example
1337
- * class CLIChat extends Chat {
1338
- * public status?: IterationStatus
1339
- * public result?: ExecutionResult
1340
- *
1341
- * onExecutionDone(result: ExecutionResult) {
1342
- * this.result = result
1343
- * this.status = result.iterations.at(-1)?.status
1344
- * }
1345
- *
1346
- * // Check if agent exited with specific exit type
1347
- * hasExitedWith<R>(exit: Exit<R>): boolean {
1348
- * return this.status?.type === 'exit_success' &&
1349
- * this.status.exit_success.exit_name === exit.name
1350
- * }
1351
- * }
1352
- * ```
1353
- */
1354
- onExecutionDone(_result) {}
1355
- };
1356
- //#endregion
1357
- //#region src/message-stream/replayable.ts
1358
- /**
1359
- * Wraps an async iterable so it can be iterated multiple times: chunks pulled
1360
- * from the source are cached, and every iteration replays the cache before
1361
- * pulling new chunks. Concurrent iterations are safe — pulls on the underlying
1362
- * source are serialized. If the source fails, the failure is cached too:
1363
- * every iteration replays the chunks received before the failure, then
1364
- * rethrows the source error.
1365
- */
1366
- var ReplayableAsyncIterable = class {
1367
- _source;
1368
- _chunks = [];
1369
- _done = false;
1370
- _failed = false;
1371
- _error;
1372
- _lock = Promise.resolve();
1373
- constructor(source) {
1374
- this._source = source[Symbol.asyncIterator]();
1375
- }
1376
- /** True once the underlying source has been fully consumed (or has failed). */
1377
- get done() {
1378
- return this._done;
1379
- }
1380
- /** The chunks pulled from the source so far. */
1381
- get chunks() {
1382
- return [...this._chunks];
1383
- }
1384
- async *[Symbol.asyncIterator]() {
1385
- let index = 0;
1386
- while (true) if (index < this._chunks.length) yield this._chunks[index++];
1387
- else if (this._failed) throw this._error;
1388
- else if (this._done) return;
1389
- else await this._pull();
1390
- }
1391
- /** Consumes the entire source and returns all chunks. */
1392
- async collect() {
1393
- for await (const _ of this);
1394
- return this.chunks;
1395
- }
1396
- _pull() {
1397
- const next = this._lock.then(async () => {
1398
- if (this._done) return;
1399
- let result;
1400
- try {
1401
- result = await this._source.next();
1402
- } catch (thrown) {
1403
- this._done = true;
1404
- this._failed = true;
1405
- this._error = thrown;
1406
- throw thrown;
1407
- }
1408
- if (result.done) this._done = true;
1409
- else this._chunks.push(result.value);
1410
- });
1411
- this._lock = next.catch(() => {});
1412
- return next;
1413
- }
1414
- };
1415
- /** Drains a string iterable into a single string. */
1416
- const collectText = async (iterable) => {
1417
- let text = "";
1418
- for await (const chunk of iterable) text += chunk;
1419
- return text;
1420
- };
1421
- //#endregion
1422
- //#region src/message-stream/stream.ts
1423
- var BaseResponse = class {
1424
- action;
1425
- item;
1426
- constructor(action, item) {
1427
- this.action = action;
1428
- this.item = item;
1429
- }
1430
- get diagnostics() {
1431
- return this.item.diagnostics;
1432
- }
1433
- };
1434
- /** `■send=<component> { props? }` followed by an optional streaming body. */
1435
- var SendResponse = class extends BaseResponse {
1436
- content;
1437
- constructor(item, content) {
1438
- super("send", item);
1439
- this.content = content;
1440
- }
1441
- get component() {
1442
- return this.item.name;
1443
- }
1444
- get props() {
1445
- return this.item.props;
1446
- }
1447
- static formatToText(component, props, body) {
1448
- const header = `■send=${component}${props && Object.keys(props).length ? ` ${JSON.stringify(props)}` : ""}`;
1449
- return body ? `${header}\n${body}` : header;
1450
- }
1451
- };
1452
- /** `■run` followed by streaming code. */
1453
- var RunResponse = class extends BaseResponse {
1454
- code;
1455
- constructor(item, code) {
1456
- super("run", item);
1457
- this.code = code;
1458
- }
1459
- static formatToText(code) {
1460
- return `■run\n${code}`;
1461
- }
1462
- };
1463
- /** `■next=<name> { props? }` — hands control to an exit (e.g. listen) with optional props. */
1464
- var NextResponse = class extends BaseResponse {
1465
- constructor(item) {
1466
- super("next", item);
1467
- }
1468
- get name() {
1469
- return this.item.name;
1470
- }
1471
- get props() {
1472
- return this.item.props;
1473
- }
1474
- static formatToText(name, props) {
1475
- return `■next=${name}${props && Object.keys(props).length ? ` ${JSON.stringify(props)}` : ""}`;
1476
- }
1477
- };
1478
- /**
1479
- * Pulls transport chunks through the parser on demand and hands out events one
1480
- * at a time. Shared by the main response loop and by body streams; pulls are
1481
- * serialized so interleaved consumers cannot race the source iterator.
1482
- */
1483
- var EventPump = class {
1484
- _iterator;
1485
- _parser;
1486
- _queue = [];
1487
- _sourceDone = false;
1488
- _lock = Promise.resolve();
1489
- constructor(stream, parser) {
1490
- this._iterator = stream[Symbol.asyncIterator]();
1491
- this._parser = parser;
1492
- }
1493
- next() {
1494
- const next = this._lock.then(() => this._next());
1495
- this._lock = next.catch(() => {});
1496
- return next;
1497
- }
1498
- unshift(event) {
1499
- this._queue.unshift(event);
1500
- }
1501
- async _next() {
1502
- while (this._queue.length === 0) {
1503
- if (this._sourceDone) return;
1504
- let result;
1505
- try {
1506
- result = await this._iterator.next();
1507
- } catch {
1508
- this._sourceDone = true;
1509
- this._queue.push(...this._parser.finish("interrupted"));
1510
- continue;
1511
- }
1512
- if (result.done) {
1513
- this._sourceDone = true;
1514
- this._queue.push(...this._parser.finish());
1515
- } else this._queue.push(...this._parser.push(result.value));
1516
- }
1517
- return this._queue.shift();
1518
- }
1519
- };
1520
- /**
1521
- * Parses a raw LLM text stream into typed responses.
1522
- *
1523
- * `send` and `run` responses are yielded as soon as their header is parsed —
1524
- * while their body is still streaming — with the body exposed as a replayable
1525
- * async iterable. `next` responses are yielded once complete.
1526
- *
1527
- * The body streams are pull-based: consuming them drives the underlying
1528
- * transport. Requesting the next response first drains the previous body into
1529
- * its replay cache, so it can always be read later.
1530
- */
1531
- function parseStream(stream, options) {
1532
- return parseResponses(stream, options);
1533
- }
1534
- /** Parses a complete text (convenience wrapper over {@link parseStream}). */
1535
- function parseText(text, options) {
1536
- return parseResponses((async function* () {
1537
- yield text;
1538
- })(), options);
1539
- }
1540
- async function* parseResponses(stream, options) {
1541
- const pump = new EventPump(stream, new require_common.StreamingMessageParser(options));
1542
- let activeBody;
1543
- while (true) {
1544
- if (activeBody) {
1545
- await activeBody.collect();
1546
- activeBody = void 0;
1547
- }
1548
- const event = await pump.next();
1549
- if (!event) return;
1550
- if (event.type === "item-ready" && (event.item.kind === "send" || event.item.kind === "run")) {
1551
- const body = new ReplayableAsyncIterable(bodyStream(pump, event.item.id));
1552
- activeBody = body;
1553
- yield event.item.kind === "send" ? new SendResponse(event.item, body) : new RunResponse(event.item, body);
1554
- continue;
1555
- }
1556
- if (event.type === "item-complete" && event.item.kind === "next") {
1557
- yield new NextResponse(event.item);
1558
- continue;
1559
- }
1560
- }
1561
- }
1562
- async function* bodyStream(pump, itemId) {
1563
- while (true) {
1564
- const event = await pump.next();
1565
- if (!event) return;
1566
- if (event.type === "body-delta" && event.itemId === itemId) {
1567
- yield event.delta;
1568
- continue;
1569
- }
1570
- if (event.type === "body-start" && event.itemId === itemId) continue;
1571
- if (event.type === "diagnostic") continue;
1572
- if (event.type === "item-complete" && event.item.id === itemId) return;
1573
- pump.unshift(event);
1574
- return;
1575
- }
1576
- }
1577
- //#endregion
1578
- //#region src/message-stream/normalizer.ts
1579
- const EMPTY_PROPS_SCHEMA = {
1580
- type: "object",
1581
- properties: {},
1582
- additionalProperties: false
1583
- };
1584
- const normalizeComponentName = (name) => name.trim().toLowerCase();
1585
- function normalizeComponentDefinition(definition) {
1586
- const name = normalizeComponentName(definition.name ?? "");
1587
- if (!require_common.NAME_REGEX.test(name)) throw new Error(`Invalid component name "${definition.name}". Component names must be lowercase ([a-z][a-z0-9_-]*).`);
1588
- return {
1589
- name,
1590
- description: definition.description,
1591
- propsJsonSchema: normalizePropsSchema(definition.props, name),
1592
- body: definition.body ? {
1593
- format: definition.body.type,
1594
- description: definition.body.description,
1595
- required: definition.body.required ?? false
1596
- } : void 0,
1597
- generation: definition.generation
1598
- };
1599
- }
1600
- function normalizePropsSchema(props, name) {
1601
- if (props === void 0) return EMPTY_PROPS_SCHEMA;
1602
- if (require_utils.isZuiSchema(props)) try {
1603
- return _bpinternal_zui.transforms.toJSONSchema(props);
1604
- } catch {
1605
- return _bpinternal_zui.transforms.toJSONSchemaLegacy(props);
1606
- }
1607
- if (require_utils.isJsonSchema(props)) return props;
1608
- throw new Error(`Invalid props schema for "${name}". Expected a ZUI/Zod object schema or a JSON schema, but got type "${typeof props}".`);
1609
- }
1610
- //#endregion
1611
- //#region src/message-stream/sanitize.ts
1612
- /**
1613
- * The protocol has no escaping mechanism by design. Any untrusted text that is
1614
- * inserted into model context (user messages, tool results, documents) must be
1615
- * sanitized so it cannot inject protocol blocks.
1616
- */
1617
- const sanitizeMessageText = (value, options = {}) => value.replaceAll("■", options.markerReplacement ?? "▪");
1618
- //#endregion
1619
549
  //#region src/index.ts
1620
550
  const utils = {
1621
551
  toValidObjectName: require_utils.toValidObjectName,
1622
- toValidFunctionName: require_utils.toValidFunctionName,
1623
- wrapContent: require_truncator.wrapContent,
1624
- truncateWrappedContent: require_truncator.truncateWrappedContent,
1625
- stripTruncationTags: require_truncator.stripTruncationTags
552
+ toValidFunctionName: require_utils.toValidFunctionName
1626
553
  };
1627
554
  /**
1628
555
  * Executes an LLMz agent in either Chat Mode or Worker Mode.
1629
556
  *
1630
- * LLMz is a code-first AI agent framework that generates and runs TypeScript code
1631
- * in a sandbox rather than using traditional JSON tool calling. This enables complex
1632
- * logic, multi-tool orchestration, and native LLM thinking via comments and code structure.
557
+ * LLMz generates and runs JavaScript in a sandbox through the native run_javascript
558
+ * tool. Assistant text streams normally; JavaScript returns decisions to present
559
+ * rich messages, inspect results, or complete through a typed exit.
1633
560
  *
1634
561
  * @param props - Configuration object for the execution
1635
562
  * @param props.client - Botpress Client or Cognitive Client instance for LLM generation
1636
563
  * @param props.instructions - System prompt/instructions for the LLM (static string or dynamic function)
1637
- * @param props.examples - Optional labeled few-shot examples (static array or dynamic function)
1638
564
  * @param props.chat - Optional Chat instance to enable Chat Mode with user interaction
1639
565
  * @param props.tools - Array of Tool instances available to the agent (static or dynamic)
1640
566
  * @param props.objects - Array of ObjectInstance for namespaced tools and variables (static or dynamic)
1641
567
  * @param props.exits - Array of Exit definitions for structured completion (static or dynamic)
1642
- * @param props.snapshot - Optional Snapshot to resume paused execution
568
+ * @param props.session - Conversation state; append input before execution and persist it between executions
1643
569
  * @param props.signal - Optional AbortSignal to cancel execution
1644
570
  * @param props.model - Optional model name (or array or models to use as fallback) (static or dynamic function)
1645
571
  * @param props.temperature - Optional temperature value (static or dynamic function)
@@ -1683,7 +609,7 @@ const utils = {
1683
609
  * // With dynamic instructions and hooks
1684
610
  * const result = await execute({
1685
611
  * client: cognitiveClient,
1686
- * instructions: (ctx) => `Process ${ctx.variables.dataCount} records`,
612
+ * instructions: (ctx) => `Process ${ctx.session.memory.variables.dataCount} records`,
1687
613
  * tools: async (ctx) => await getContextualTools(ctx),
1688
614
  * model: 'best',
1689
615
  * temperature: 0.1,
@@ -1693,7 +619,7 @@ const utils = {
1693
619
  * })
1694
620
  */
1695
621
  const execute = async (props) => {
1696
- const { executeContext } = await Promise.resolve().then(() => require("./execute-DM2-7y86.cjs"));
622
+ const { executeContext } = await Promise.resolve().then(() => require("./execute-DTTfacsi.cjs"));
1697
623
  return executeContext(props);
1698
624
  };
1699
625
  /**
@@ -1702,68 +628,82 @@ const execute = async (props) => {
1702
628
  * It's recommended to call this function at the beginning of your application without awaiting it (void init())
1703
629
  */
1704
630
  const init = async () => {
1705
- await Promise.resolve().then(() => require("./execute-DM2-7y86.cjs"));
1706
- await Promise.resolve().then(() => require("./component-C6Agl2ns.cjs")).then((n) => n.component_exports);
1707
- await Promise.resolve().then(() => require("./tool-Dy6AJpJH.cjs")).then((n) => n.tool_exports);
1708
- await Promise.resolve().then(() => require("./exit-DUM96DN1.cjs")).then((n) => n.exit_exports);
1709
- await Promise.resolve().then(() => require("./jsx-owqxrquU.cjs")).then((n) => n.jsx_exports);
1710
- await Promise.resolve().then(() => require("./vm-D6s1zF6M.cjs"));
1711
- await Promise.resolve().then(() => require("./utils-3ESwP3yg.cjs")).then((n) => n.utils_exports);
1712
- await Promise.resolve().then(() => require("./truncator-CLkouTCO.cjs")).then((n) => n.truncator_exports);
1713
- await Promise.resolve().then(() => require("./typings-3lsqCbkn.cjs")).then((n) => n.typings_exports);
1714
- await Promise.resolve().then(() => require("./dual-modes-DPXiuvNe.cjs")).then((n) => n.dual_modes_exports);
631
+ await Promise.resolve().then(() => require("./execute-DTTfacsi.cjs"));
632
+ await Promise.resolve().then(() => require("./component-CMFoCHyu.cjs")).then((n) => n.component_exports);
633
+ await Promise.resolve().then(() => require("./tool-_wK9hQOb.cjs")).then((n) => n.tool_exports);
634
+ await Promise.resolve().then(() => require("./exit-BOtKWPuT.cjs")).then((n) => n.exit_exports);
635
+ await Promise.resolve().then(() => require("./vm-gmekHc0i.cjs"));
636
+ await Promise.resolve().then(() => require("./utils-CTlsXvdj.cjs")).then((n) => n.utils_exports);
637
+ await Promise.resolve().then(() => require("./typings-BA_XxAcY.cjs")).then((n) => n.typings_exports);
638
+ await Promise.resolve().then(() => require("./native-0bq5ATZM.cjs")).then((n) => n.native_exports);
1715
639
  };
1716
640
  //#endregion
1717
- exports.BaseResponse = BaseResponse;
641
+ exports.AssignmentError = require_errors.AssignmentError;
1718
642
  exports.Chat = Chat;
1719
643
  exports.CitationsManager = CitationsManager;
644
+ exports.CodeExecutionError = require_errors.CodeExecutionError;
645
+ exports.CodeFormattingError = require_errors.CodeFormattingError;
646
+ exports.CognitiveError = require_errors.CognitiveError;
647
+ exports.CompactionError = require_errors.CompactionError;
1720
648
  exports.Component = require_component.Component;
1721
- exports.ComponentRegistry = require_dual_modes.ComponentRegistry;
649
+ exports.ComponentInputError = require_errors.ComponentInputError;
1722
650
  exports.DefaultComponents = DefaultComponents;
1723
651
  exports.DefaultExit = require_custom_client.DefaultExit;
652
+ exports.DeliveryError = require_errors.DeliveryError;
1724
653
  exports.ErrorExecutionResult = require_custom_client.ErrorExecutionResult;
1725
- exports.Example = require_dual_modes.Example;
654
+ exports.ExecutionAbortedError = require_errors.ExecutionAbortedError;
1726
655
  exports.ExecutionResult = require_custom_client.ExecutionResult;
1727
656
  exports.Exit = require_exit.Exit;
657
+ exports.ExitInputError = require_errors.ExitInputError;
658
+ exports.HookError = require_errors.HookError;
659
+ exports.HostOperationError = require_errors.HostOperationError;
660
+ exports.InternalError = require_errors.InternalError;
661
+ exports.InvalidCodeError = require_errors.InvalidCodeError;
662
+ exports.InvalidComponentError = require_errors.InvalidComponentError;
663
+ exports.InvalidConfigurationError = require_errors.InvalidConfigurationError;
664
+ exports.InvalidEventError = require_errors.InvalidEventError;
665
+ exports.InvalidExitError = require_errors.InvalidExitError;
666
+ exports.InvalidMessageError = require_errors.InvalidMessageError;
667
+ exports.InvalidObjectError = require_errors.InvalidObjectError;
668
+ exports.InvalidSessionError = require_errors.InvalidSessionError;
669
+ exports.InvalidToolError = require_errors.InvalidToolError;
670
+ exports.LLMzError = require_errors.LLMzError;
1728
671
  exports.ListenExit = require_custom_client.ListenExit;
1729
672
  exports.LoopExceededError = require_errors.LoopExceededError;
1730
- exports.MARKER = require_common.MARKER;
1731
- exports.NAME_REGEX = require_common.NAME_REGEX;
1732
- exports.NextResponse = NextResponse;
673
+ exports.Memory = require_quickjs_variant.Memory;
674
+ exports.MemoryCapacityError = require_errors.MemoryCapacityError;
675
+ exports.MemoryValueError = require_errors.MemoryValueError;
676
+ exports.MissingChatResponseError = require_errors.MissingChatResponseError;
677
+ exports.NativeProtocolError = require_errors.NativeProtocolError;
1733
678
  exports.ObjectInstance = ObjectInstance;
1734
- exports.PartialExecutionResult = require_custom_client.PartialExecutionResult;
1735
- exports.ReplayableAsyncIterable = ReplayableAsyncIterable;
1736
- exports.RunResponse = RunResponse;
1737
- exports.SendResponse = SendResponse;
1738
- exports.Snapshot = require_custom_client.Snapshot;
1739
- exports.SnapshotSignal = require_errors.SnapshotSignal;
1740
- exports.StreamingMessageParser = require_common.StreamingMessageParser;
679
+ exports.ObjectPropertyError = require_errors.ObjectPropertyError;
680
+ exports.ReservedIdentifierError = require_errors.ReservedIdentifierError;
681
+ exports.Session = require_custom_client.Session;
682
+ exports.SessionStateError = require_errors.SessionStateError;
1741
683
  exports.SuccessExecutionResult = require_custom_client.SuccessExecutionResult;
1742
- exports.ThinkExit = require_custom_client.ThinkExit;
1743
684
  exports.ThinkSignal = require_errors.ThinkSignal;
685
+ exports.TokenOverflowError = require_errors.TokenOverflowError;
1744
686
  exports.Tool = require_tool.Tool;
687
+ exports.ToolExecutionError = require_errors.ToolExecutionError;
688
+ exports.ToolInputError = require_errors.ToolInputError;
689
+ exports.UnknownComponentError = require_errors.UnknownComponentError;
690
+ exports.UnknownExitError = require_errors.UnknownExitError;
691
+ exports.UnknownToolError = require_errors.UnknownToolError;
1745
692
  exports._CustomModelClient = require_custom_client._CustomModelClient;
1746
693
  exports.assertValidComponent = require_component.assertValidComponent;
1747
- exports.collectText = collectText;
1748
694
  exports.configureQuickJS = require_quickjs_variant.configureQuickJS;
1749
695
  exports.configureTokenizer = require_utils.configureTokenizer;
696
+ exports.createInspector = require_quickjs_variant.createInspector;
1750
697
  exports.execute = execute;
1751
- exports.generateInstructions = require_dual_modes.generateInstructions;
1752
698
  exports.getValue = require_custom_client.getValue;
1753
699
  exports.init = init;
700
+ exports.inspect = require_quickjs_variant.inspect;
1754
701
  exports.isAnyComponent = require_component.isAnyComponent;
1755
702
  exports.isComponent = require_component.isComponent;
1756
- exports.normalizeComponentDefinition = normalizeComponentDefinition;
1757
- exports.normalizeComponentName = normalizeComponentName;
1758
- exports.normalizePropsSchema = normalizePropsSchema;
1759
- exports.parseExit = require_custom_client.parseExit;
1760
- exports.parseStream = parseStream;
1761
- exports.parseText = parseText;
1762
- exports.sanitizeMessageText = sanitizeMessageText;
1763
- exports.tryParseJson = require_common.tryParseJson;
703
+ exports.isCriticalError = require_errors.isCriticalError;
704
+ exports.isLLMzError = require_errors.isLLMzError;
705
+ exports.truncate = require_truncate.truncate;
1764
706
  exports.utils = utils;
1765
- exports.validateComponent = require_dual_modes.validateComponent;
1766
- exports.validateProps = require_dual_modes.validateProps;
1767
707
  Object.defineProperty(exports, "version", {
1768
708
  enumerable: true,
1769
709
  get: function() {