llmz 1.0.1 → 1.0.3

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 (55) hide show
  1. package/DOCS.md +8 -4
  2. package/ERRORS.md +5 -2
  3. package/dist/{component-BpMVZYOa.cjs → component-CMFoCHyu.cjs} +3 -3
  4. package/dist/{component-C27qu6Zv.js → component-DncqP4fB.js} +3 -3
  5. package/dist/context.d.ts +1 -1
  6. package/dist/{custom-client-MytucGI-.cjs → custom-client-BwRYQ4Oa.cjs} +37 -13
  7. package/dist/{custom-client-BDkgBR2w.js → custom-client-JcdoH-47.js} +37 -13
  8. package/dist/errors/catalog.d.ts +7 -0
  9. package/dist/{errors-IhnTKUp7.cjs → errors-C6ppQUZX.cjs} +22 -0
  10. package/dist/{errors-H4JJFH3S.js → errors-Crk5P8jo.js} +17 -1
  11. package/dist/errors.d.ts +6 -0
  12. package/dist/{execute-DLas4V2n.cjs → execute-DJBNrA2H.cjs} +209 -79
  13. package/dist/{execute-BYI_U5sR.js → execute-DoN74Exa.js} +209 -79
  14. package/dist/{exit-BUgJ5qi5.cjs → exit-BOtKWPuT.cjs} +2 -2
  15. package/dist/{exit-CPNk3vbz.js → exit-DMPwCSba.js} +2 -2
  16. package/dist/index.cjs +18 -17
  17. package/dist/index.d.ts +1 -1
  18. package/dist/index.js +18 -18
  19. package/dist/index.workerd.js +404 -88
  20. package/dist/inspection.d.ts +2 -0
  21. package/dist/{native-DvTH9vFe.js → native-BGW5kBlv.js} +136 -10
  22. package/dist/{native-Bm6L9zOb.cjs → native-sbuzbLbY.cjs} +136 -10
  23. package/dist/prompts/native-examples.d.ts +10 -0
  24. package/dist/prompts/native-examples.test.d.ts +1 -0
  25. package/dist/prompts/reasoning.d.ts +2 -0
  26. package/dist/prompts/reasoning.test.d.ts +1 -0
  27. package/dist/{quickjs-variant-DJwYDSsb.cjs → quickjs-variant-21IO97PF.cjs} +15 -8
  28. package/dist/{quickjs-variant-DlPi9-Sx.js → quickjs-variant-CtuGagsb.js} +10 -9
  29. package/dist/runtime/chat-completion.test.d.ts +1 -0
  30. package/dist/runtime/chat-last-speaker.test.d.ts +1 -0
  31. package/dist/runtime/empty-completion.test.d.ts +1 -0
  32. package/dist/runtime/execution-report.d.ts +3 -0
  33. package/dist/runtime/forced-inspection.d.ts +13 -0
  34. package/dist/runtime/forced-inspection.test.d.ts +1 -0
  35. package/dist/runtime/javascript-api.d.ts +3 -0
  36. package/dist/runtime/think-signal.test.d.ts +1 -0
  37. package/dist/runtime/tool-wrapper.d.ts +4 -2
  38. package/dist/runtime/types.d.ts +8 -0
  39. package/dist/{schema-DBkjo0b7.cjs → schema-CXlnbb3n.cjs} +1 -1
  40. package/dist/{schema-Aer_W7Al.js → schema-GE4ISPCR.js} +1 -1
  41. package/dist/session/messages.d.ts +2 -0
  42. package/dist/session/serialization.d.ts +2 -0
  43. package/dist/session/session.d.ts +4 -0
  44. package/dist/session/speaker.test.d.ts +1 -0
  45. package/dist/{tool--gK91eez.js → tool-DstssiAs.js} +4 -4
  46. package/dist/{tool-Da_F-N-5.cjs → tool-_wK9hQOb.cjs} +4 -4
  47. package/dist/{truncate-BSoH2-nY.js → truncate-BEKbdo3t.js} +1 -1
  48. package/dist/{truncate-nV3Mxr6-.cjs → truncate-uomAMGPs.cjs} +1 -1
  49. package/dist/types.d.ts +6 -0
  50. package/dist/{typings-C1ihexWE.cjs → typings-BA_XxAcY.cjs} +1 -1
  51. package/dist/{typings-D9_aC8aq.js → typings-BEVDvtuk.js} +1 -1
  52. package/dist/vm/types.d.ts +2 -0
  53. package/dist/{vm-8jxt8PTK.js → vm-C7SfutHn.js} +28 -3
  54. package/dist/{vm-XuVPuW3Y.cjs → vm-gmekHc0i.cjs} +28 -2
  55. package/package.json +2 -1
@@ -1,13 +1,13 @@
1
1
  import { g as baseIsEqual, o as init, r as getErrorMessage, u as stripInvalidIdentifiers } from "./utils-BOFzb8Ok.js";
2
- import { A as MemoryValueError, B as UnknownToolError, F as TokenOverflowError, H as isLLMzError, I as ToolExecutionError, M as ObjectPropertyError, O as LoopExceededError, P as SessionStateError, R as UnknownComponentError, V as isCriticalError, a as cleanStackTrace, b as InvalidConfigurationError, f as DeliveryError, g as HostOperationError, h as HookError, j as NativeProtocolError, k as MemoryCapacityError, l as CognitiveError, m as ExitInputError, n as ThinkSignal, o as AssignmentError, p as ExecutionAbortedError, r as VMSignal, s as CodeExecutionError, t as Signals, u as CompactionError, v as InvalidCodeError, z as UnknownExitError } from "./errors-H4JJFH3S.js";
3
- import { a as isAnyComponent } from "./component-C27qu6Zv.js";
4
- import { n as parseSchemaSync } from "./schema-Aer_W7Al.js";
5
- import { t as DEFAULT_TOOL_RESULT_MAX_TOKENS } from "./truncate-BSoH2-nY.js";
6
- import { a as cloneMemoryValue, f as createInspector, h as resolveInspectionBudget, m as limitInspectionOutput } from "./quickjs-variant-DlPi9-Sx.js";
7
- import { n as schemaToTypeScript } from "./typings-D9_aC8aq.js";
8
- import { a as Context, d as prepareAutoCompaction, f as countNativeRequestTokens, i as SuccessExecutionResult, n as ErrorExecutionResult, p as resolveTokenBudget, s as ListenExit, t as _CustomModelClient, u as stableJSON } from "./custom-client-BDkgBR2w.js";
9
- import { a as validateNativeToolCalls, i as getRunJavaScriptTool, r as WORKER_RESPONSE_INSTRUCTION } from "./native-DvTH9vFe.js";
10
- import { a as compile, i as VM_TERMINATION, n as VM_ON_ERROR, r as VM_PROGRAM_COMPLETE, runAsyncFunction, t as withMissingMember } from "./vm-8jxt8PTK.js";
2
+ import { A as MemoryValueError, B as UnknownExitError, F as SessionStateError, H as isCriticalError, I as TokenOverflowError, L as ToolExecutionError, M as NativeProtocolError, N as ObjectPropertyError, O as LoopExceededError, U as isLLMzError, V as UnknownToolError, a as cleanStackTrace, b as InvalidConfigurationError, f as DeliveryError, g as HostOperationError, h as HookError, j as MissingChatResponseError, k as MemoryCapacityError, l as CognitiveError, m as ExitInputError, n as ThinkSignal, o as AssignmentError, p as ExecutionAbortedError, r as VMSignal, s as CodeExecutionError, t as Signals, u as CompactionError, v as InvalidCodeError, z as UnknownComponentError } from "./errors-Crk5P8jo.js";
3
+ import { a as isAnyComponent } from "./component-DncqP4fB.js";
4
+ import { n as parseSchemaSync } from "./schema-GE4ISPCR.js";
5
+ import { i as unwrapTruncated, n as isTruncated, t as DEFAULT_TOOL_RESULT_MAX_TOKENS } from "./truncate-BEKbdo3t.js";
6
+ import { a as cloneMemoryValue, f as createInspector, g as resolveInspectionBudget, h as limitInspectionOutput, p as snapshotInspectionValue } from "./quickjs-variant-CtuGagsb.js";
7
+ import { n as schemaToTypeScript } from "./typings-BEVDvtuk.js";
8
+ import { a as Context, d as prepareAutoCompaction, f as countNativeRequestTokens, i as SuccessExecutionResult, n as ErrorExecutionResult, p as resolveTokenBudget, s as ListenExit, t as _CustomModelClient, u as stableJSON } from "./custom-client-JcdoH-47.js";
9
+ import { a as validateNativeToolCalls, i as getRunJavaScriptTool, r as WORKER_RESPONSE_INSTRUCTION } from "./native-BGW5kBlv.js";
10
+ import { a as VM_TERMINATION, i as VM_PROGRAM_COMPLETE, n as VM_CALL_SITE, o as compile, r as VM_ON_ERROR, runAsyncFunction, t as withMissingMember } from "./vm-C7SfutHn.js";
11
11
  import { z } from "@bpinternal/zui";
12
12
  import { ulid } from "ulid";
13
13
  import { Cognitive } from "@botpress/cognitive";
@@ -208,10 +208,7 @@ function errorPreview(value, inspector, identity) {
208
208
  //#region src/runtime/execution-diagnostics.ts
209
209
  /** XML-style boundaries keep diagnostic text separate from recovery instructions. */
210
210
  function reportSection(name, content, maxTokens = 2e3, options = {}) {
211
- const escape = (value) => value.replace(/&/g, "&amp;").replace(/</g, "&lt;");
212
- const heading = options.heading ? `${escape(options.heading)}\n` : "";
213
- const body = limitInspectionOutput(content, maxTokens, false, options.preserve ?? "top");
214
- return `<${name}>\n${heading}${/[<&]|\]\]>/.test(body) ? `<![CDATA[\n${body.replaceAll("]]>", "]]]]><![CDATA[>")}\n]]>` : body}\n</${name}>`;
211
+ return `<${name}>\n${options.heading ? `${options.heading}\n` : ""}${limitInspectionOutput(content, maxTokens, false, options.preserve ?? "top")}\n</${name}>`;
215
212
  }
216
213
  /** Show the specific failure and guest source, never the host's implementation stack. */
217
214
  function renderExecutionDiagnostics(error, message, inspector, identity) {
@@ -252,11 +249,58 @@ function renderSourceTrace(stack, inspector, identity) {
252
249
  }), 1e3);
253
250
  }
254
251
  //#endregion
252
+ //#region src/runtime/forced-inspection.ts
253
+ /** Keep attribution and content together, using the same display budgets as inspect(). */
254
+ function renderForcedInspection(inspections, inspector, identity, maxTokens, policies) {
255
+ return [
256
+ "<forced_inspection>",
257
+ "Forced inspection: the tools listed below completed successfully and requested review of their results.",
258
+ "This is the equivalent of an inspect() call. Do not repeat these tool calls; use the results below and retained variables.",
259
+ "No exit was applied. Review the evidence before continuing or completing the task.",
260
+ "",
261
+ "Tools requesting inspection (lines refer to the executed JavaScript):",
262
+ ...inspections.map((entry) => {
263
+ const entryIdentity = {
264
+ ...identity,
265
+ tool: entry.tool
266
+ };
267
+ const name = inspector(entry.tool, {
268
+ purpose: "name",
269
+ maxTokens: 80,
270
+ identity: entryIdentity
271
+ });
272
+ const reason = inspector(entry.reason, {
273
+ purpose: "error",
274
+ maxTokens: 1e3,
275
+ identity: entryIdentity
276
+ });
277
+ const budget = resolveInspectionBudget(entry.value, {
278
+ tokens: maxTokens,
279
+ policies
280
+ });
281
+ const result = inspector(entry.value, {
282
+ purpose: "result",
283
+ maxTokens,
284
+ policies,
285
+ identity: entryIdentity
286
+ });
287
+ return [
288
+ `<tool name="${name}" line="${entry.line ?? "unknown"}">`,
289
+ `<reason>${reason}</reason>`,
290
+ reportSection("result", result, budget.tokens, { preserve: budget.preserve }),
291
+ "</tool>"
292
+ ].join("\n");
293
+ }),
294
+ "</forced_inspection>"
295
+ ].join("\n");
296
+ }
297
+ //#endregion
255
298
  //#region src/runtime/execution-report.ts
256
299
  const MAX_REPORTED_CHANGES = 40;
257
300
  const MAX_OVERRIDE_SOURCE_LENGTH = 3e3;
258
301
  /** Format one settled outcome; execution is responsible for deciding what happened. */
259
302
  function renderExecutionReport({ outcome, activity, memory, source, requiresExit = false, iteration, identity = { iteration }, inspector = createInspector(), maxTokens = DEFAULT_TOOL_RESULT_MAX_TOKENS, policies }) {
303
+ var _outcome$forcedInspec, _outcome$forcedInspec2;
260
304
  const detail = (value) => inspector(value, {
261
305
  purpose: "error",
262
306
  maxTokens: 1e3,
@@ -283,6 +327,13 @@ function renderExecutionReport({ outcome, activity, memory, source, requiresExit
283
327
  });
284
328
  };
285
329
  const sections = [renderStatus(outcome, memory)];
330
+ if (outcome.type === "inspect" && ((_outcome$forcedInspec = outcome.forcedInspections) === null || _outcome$forcedInspec === void 0 ? void 0 : _outcome$forcedInspec.length)) {
331
+ sections.push(renderForcedInspection(outcome.forcedInspections, inspector, identity, maxTokens, policies));
332
+ if (outcome.downstreamError) {
333
+ sections.push(...renderExecutionDiagnostics(outcome.downstreamError, getErrorMessage(outcome.downstreamError), inspector, identity));
334
+ sections.push(reportSection("recovery", "A later operation failed. The tool results above were successfully retrieved; inspect them and repair only the failed work. Do not repeat successful calls."));
335
+ }
336
+ }
286
337
  if (outcome.type === "error") {
287
338
  sections.push(...renderExecutionDiagnostics(outcome.error, outcome.message, inspector, identity));
288
339
  sections.push(reportSection("recovery", [
@@ -315,7 +366,7 @@ function renderExecutionReport({ outcome, activity, memory, source, requiresExit
315
366
  if (memory.unavailable.length > failures.length) entries.push(`- ${memory.unavailable.length - failures.length} additional values could not be retained.`);
316
367
  sections.push(reportSection("memory_errors", `Memory errors\n${entries.join("\n")}`));
317
368
  }
318
- if (outcome.type === "inspect") {
369
+ if (outcome.type === "inspect" && ((_outcome$forcedInspec2 = outcome.forcedInspections) === null || _outcome$forcedInspec2 === void 0 ? void 0 : _outcome$forcedInspec2.length) && (!outcome.explicit || outcome.forcedInspections.some((entry) => isEqual(entry.value, outcome.value)))) {} else if (outcome.type === "inspect") {
319
370
  const heading = outcome.explicit ? "inspect() result" : "Result";
320
371
  sections.push(outcome.available ? resultSection("result", heading, outcome.value) : reportSection("result", "Unavailable; see memory errors above.", maxTokens, { heading }));
321
372
  } else if (outcome.type === "exit") sections.push(resultSection("completion", `Completion\nExit "${outcome.name}" completed.`, outcome.value === void 0 ? "" : outcome.value));
@@ -363,6 +414,12 @@ function renderChanges(label, changes, name) {
363
414
  return lines.join("\n");
364
415
  }
365
416
  //#endregion
417
+ //#region src/prompts/reasoning.ts
418
+ /** Supplement explicit reasoning disablement consistently across providers and fallbacks. */
419
+ function getReasoningHint(reasoningEffort) {
420
+ return reasoningEffort === "none" ? "/no_think" : void 0;
421
+ }
422
+ //#endregion
366
423
  //#region src/runtime/generate.ts
367
424
  const STREAM_IDLE_TIMEOUT = 18e4;
368
425
  const STATIC_TOKEN_PARTS = [
@@ -459,7 +516,13 @@ async function prepareNativeRequest({ iteration, ctx, cognitive, controller, met
459
516
  const model = models[0];
460
517
  const { limit, output: reserve } = resolveTokenBudget(models, ctx.maxTokens);
461
518
  const tools = [getRunJavaScriptTool(!!ctx.chat)];
462
- const system = [iteration.systemMessage];
519
+ const systemMessage = structuredClone(iteration.systemMessage);
520
+ const reasoningHint = getReasoningHint(iteration.reasoningEffort);
521
+ if (reasoningHint) systemMessage.content = typeof systemMessage.content === "string" ? `${systemMessage.content}\n\n${reasoningHint}` : [...systemMessage.content ?? [], {
522
+ type: "text",
523
+ text: reasoningHint
524
+ }];
525
+ const system = [systemMessage];
463
526
  const budgetInstruction = getBudgetInstruction(ctx, iteration);
464
527
  const budget = `\n\nExecution budget: response ${ctx.iterations.length} of ${ctx.loop}. ${budgetInstruction}`;
465
528
  const buildMessages = (retainedIds, summary) => {
@@ -851,6 +914,7 @@ const isRecord = (value) => value !== null && typeof value === "object" && !Arra
851
914
  function createJavaScriptApi({ iteration, components, exits, deliver, signal, onError }) {
852
915
  const decisions = /* @__PURE__ */ new Map();
853
916
  const pending = /* @__PURE__ */ new Set();
917
+ const inspections = [];
854
918
  let open = true;
855
919
  let outstanding = [];
856
920
  let delivery;
@@ -987,6 +1051,10 @@ function createJavaScriptApi({ iteration, components, exits, deliver, signal, on
987
1051
  isReceipt: (value) => resolve(value) !== void 0,
988
1052
  getTerminalOutcome: () => terminalOutcome,
989
1053
  getInterruption: () => interruption,
1054
+ requestInspection: (inspection) => {
1055
+ inspections.push(inspection);
1056
+ },
1057
+ getForcedInspections: () => inspections,
990
1058
  throwIfTerminated,
991
1059
  track,
992
1060
  assertOpen,
@@ -1014,8 +1082,8 @@ const finalizeIteration = async ({ iteration, status, controller, onIterationEnd
1014
1082
  //#endregion
1015
1083
  //#region src/runtime/tool-wrapper.ts
1016
1084
  const SLOW_TOOL_WARNING = ms("15s");
1017
- function wrapTool({ tool, object, iteration, beforeHook, afterHook, onTruncation, onResult, controller }) {
1018
- return async function(input) {
1085
+ function wrapTool({ tool, object, iteration, beforeHook, afterHook, onTruncation, onResult, controller, onThink }) {
1086
+ return async function(input, line) {
1019
1087
  controller.signal.throwIfAborted();
1020
1088
  const toolCallId = `tcall_${ulid()}`;
1021
1089
  const originalInput = input;
@@ -1034,7 +1102,7 @@ function wrapTool({ tool, object, iteration, beforeHook, afterHook, onTruncation
1034
1102
  let output;
1035
1103
  let error;
1036
1104
  let success = true;
1037
- let signalToThrow;
1105
+ const inspections = [];
1038
1106
  const pushToolCallTrace = () => {
1039
1107
  iteration.recordTrace({
1040
1108
  type: "tool_call",
@@ -1050,32 +1118,21 @@ function wrapTool({ tool, object, iteration, beforeHook, afterHook, onTruncation
1050
1118
  success
1051
1119
  });
1052
1120
  };
1053
- const handleSignals = async (err) => {
1054
- if (output === err) return true;
1055
- if (ThinkSignal.is(err)) {
1056
- signalToThrow = err;
1057
- iteration.recordTrace({
1058
- type: "think_signal",
1059
- started_at: Date.now(),
1060
- line: 0,
1061
- ended_at: Date.now()
1062
- });
1063
- success = true;
1064
- output = err;
1065
- const afterRes = await callHook(() => afterHook === null || afterHook === void 0 ? void 0 : afterHook({
1066
- iteration,
1067
- tool,
1068
- input: originalInput,
1069
- output,
1070
- controller,
1071
- object,
1072
- toolCallId,
1073
- nativeCallId: iteration.nativeCallId
1074
- }));
1075
- if (typeof (afterRes === null || afterRes === void 0 ? void 0 : afterRes.output) !== "undefined") output = afterRes.output;
1076
- return true;
1077
- }
1078
- return false;
1121
+ const unwrapSignal = (value) => {
1122
+ if (!ThinkSignal.is(value)) return value;
1123
+ const context = value.context;
1124
+ const output = unwrapTruncated(context);
1125
+ if (isTruncated(context)) onTruncation === null || onTruncation === void 0 || onTruncation(output, context.$$truncate);
1126
+ const inspection = {
1127
+ tool: object ? `${object}.${tool.name}` : tool.name,
1128
+ toolCallId,
1129
+ line,
1130
+ reason: value.reason,
1131
+ value: output,
1132
+ metadata: value.metadata
1133
+ };
1134
+ inspections.push(inspection);
1135
+ return output;
1079
1136
  };
1080
1137
  try {
1081
1138
  const beforeRes = await callHook(() => beforeHook === null || beforeHook === void 0 ? void 0 : beforeHook({
@@ -1087,18 +1144,25 @@ function wrapTool({ tool, object, iteration, beforeHook, afterHook, onTruncation
1087
1144
  toolCallId,
1088
1145
  nativeCallId: iteration.nativeCallId
1089
1146
  }));
1147
+ if (ThinkSignal.is(beforeRes)) throw new HookError("Tool hooks cannot request inspection with ThinkSignal. Return it from the tool handler instead.");
1090
1148
  if (typeof (beforeRes === null || beforeRes === void 0 ? void 0 : beforeRes.input) !== "undefined") effectiveInput = beforeRes.input;
1091
1149
  controller.signal.throwIfAborted();
1092
- output = await tool.execute(effectiveInput, {
1093
- callId: toolCallId,
1094
- iterationId: iteration.id,
1095
- nativeCallId: iteration.nativeCallId,
1096
- onTruncation,
1097
- onInput: (parsed) => {
1098
- controller.signal.throwIfAborted();
1099
- if (effectiveInput === originalInput) reportedInput = parsed;
1100
- }
1101
- });
1150
+ try {
1151
+ output = await tool.execute(effectiveInput, {
1152
+ callId: toolCallId,
1153
+ iterationId: iteration.id,
1154
+ nativeCallId: iteration.nativeCallId,
1155
+ onTruncation,
1156
+ onInput: (parsed) => {
1157
+ controller.signal.throwIfAborted();
1158
+ if (effectiveInput === originalInput) reportedInput = parsed;
1159
+ }
1160
+ });
1161
+ } catch (error) {
1162
+ if (!ThinkSignal.is(error)) throw error;
1163
+ output = error;
1164
+ }
1165
+ output = unwrapSignal(output);
1102
1166
  const afterRes = await callHook(() => afterHook === null || afterHook === void 0 ? void 0 : afterHook({
1103
1167
  iteration,
1104
1168
  tool,
@@ -1109,19 +1173,39 @@ function wrapTool({ tool, object, iteration, beforeHook, afterHook, onTruncation
1109
1173
  toolCallId,
1110
1174
  nativeCallId: iteration.nativeCallId
1111
1175
  }));
1176
+ if (ThinkSignal.is(afterRes) || ThinkSignal.is(afterRes === null || afterRes === void 0 ? void 0 : afterRes.output)) throw new HookError("Tool hooks cannot request inspection with ThinkSignal. Return it from the tool handler instead.");
1112
1177
  if (typeof (afterRes === null || afterRes === void 0 ? void 0 : afterRes.output) !== "undefined") output = afterRes.output;
1178
+ controller.signal.throwIfAborted();
1113
1179
  } catch (err) {
1114
- if (!await handleSignals(err)) {
1115
- success = false;
1116
- error = isLLMzError(err) ? err : new ToolExecutionError(tool.name, err);
1117
- iteration.recordError(error);
1118
- }
1180
+ success = false;
1181
+ output = void 0;
1182
+ if (ThinkSignal.is(err)) error = new HookError("Tool hooks cannot request inspection with ThinkSignal. Return it from the tool handler instead.");
1183
+ else error = isLLMzError(err) ? err : new ToolExecutionError(tool.name, err);
1184
+ iteration.recordError(error);
1119
1185
  } finally {
1120
1186
  clearTimeout(alertSlowTool);
1187
+ for (const inspection of success ? inspections : []) {
1188
+ const value = snapshotInspectionValue(output);
1189
+ onThink === null || onThink === void 0 || onThink({
1190
+ ...inspection,
1191
+ value
1192
+ });
1193
+ iteration.recordTrace({
1194
+ type: "think_signal",
1195
+ started_at: Date.now(),
1196
+ ended_at: Date.now(),
1197
+ line: line ?? 0,
1198
+ tool_name: tool.name,
1199
+ tool_call_id: toolCallId,
1200
+ object,
1201
+ reason: inspection.reason,
1202
+ context: value,
1203
+ metadata: inspection.metadata
1204
+ });
1205
+ }
1121
1206
  pushToolCallTrace();
1122
1207
  }
1123
1208
  if (!success) throw error;
1124
- if (signalToThrow) throw signalToThrow;
1125
1209
  onResult === null || onResult === void 0 || onResult(output);
1126
1210
  return output;
1127
1211
  };
@@ -1212,9 +1296,14 @@ const buildVMContext = ({ ctx, iteration, controller, onBeforeTool, onAfterTool,
1212
1296
  afterHook: onAfterTool,
1213
1297
  onTruncation,
1214
1298
  onResult: onToolResult,
1215
- controller
1299
+ controller,
1300
+ onThink: javascriptApi === null || javascriptApi === void 0 ? void 0 : javascriptApi.requestInspection
1216
1301
  });
1217
- instance[tool.name] = javascriptApi ? (input) => javascriptApi.track(() => wrapped(input)) : wrapped;
1302
+ instance[tool.name] = javascriptApi ? (input) => {
1303
+ var _vmContext$VM_CALL_SI;
1304
+ const line = (_vmContext$VM_CALL_SI = vmContext[VM_CALL_SITE]) === null || _vmContext$VM_CALL_SI === void 0 ? void 0 : _vmContext$VM_CALL_SI.call(vmContext);
1305
+ return javascriptApi.track(() => wrapped(input, line));
1306
+ } : wrapped;
1218
1307
  }
1219
1308
  vmContext[obj.name] = withMissingMember(instance, (name) => {
1220
1309
  const error = new UnknownToolError(`${obj.name}.${name}`, (obj.tools ?? []).map((tool) => `${obj.name}.${tool.name}`));
@@ -1230,9 +1319,14 @@ const buildVMContext = ({ ctx, iteration, controller, onBeforeTool, onAfterTool,
1230
1319
  afterHook: onAfterTool,
1231
1320
  onTruncation,
1232
1321
  onResult: onToolResult,
1233
- controller
1322
+ controller,
1323
+ onThink: javascriptApi === null || javascriptApi === void 0 ? void 0 : javascriptApi.requestInspection
1234
1324
  });
1235
- const callable = javascriptApi ? (input) => javascriptApi.track(() => wrapped(input)) : wrapped;
1325
+ const callable = javascriptApi ? (input) => {
1326
+ var _vmContext$VM_CALL_SI2;
1327
+ const line = (_vmContext$VM_CALL_SI2 = vmContext[VM_CALL_SITE]) === null || _vmContext$VM_CALL_SI2 === void 0 ? void 0 : _vmContext$VM_CALL_SI2.call(vmContext);
1328
+ return javascriptApi.track(() => wrapped(input, line));
1329
+ } : wrapped;
1236
1330
  for (const key of [tool.name, ...tool.aliases ?? []]) vmContext[key] = callable;
1237
1331
  }
1238
1332
  return vmContext;
@@ -1272,9 +1366,10 @@ async function executeContextInternal(props) {
1272
1366
  });
1273
1367
  let release;
1274
1368
  try {
1275
- var _ctx$iterations$at;
1369
+ var _props$options8, _ctx$iterations$at;
1276
1370
  if ("snapshot" in props) throw new InvalidConfigurationError("Snapshots and external pause/resume are no longer supported. Use a session for conversation history and memory.");
1277
1371
  if ("messages" in props) throw new InvalidConfigurationError("Append input with session.append(message) before calling execute(). execute.messages is no longer supported.");
1372
+ if (((_props$options8 = props.options) === null || _props$options8 === void 0 ? void 0 : _props$options8.requireChatResponse) !== void 0 && typeof props.options.requireChatResponse !== "boolean") throw new InvalidConfigurationError("Invalid requireChatResponse. Expected a boolean.");
1278
1373
  release = ctx.session.acquire();
1279
1374
  prepareSession(ctx);
1280
1375
  const client = props.client ?? new Client();
@@ -1457,20 +1552,21 @@ async function rejectNativeBatch({ ctx, iteration }, generated, errors) {
1457
1552
  }, generated.toolCalls.some((call) => call.name !== "run_javascript") ? new UnknownToolError(generated.toolCalls.find((call) => call.name !== "run_javascript").name, ["run_javascript"], message) : new NativeProtocolError(message));
1458
1553
  }
1459
1554
  async function deliverAssistantText(state, generated) {
1555
+ var _iteration$response4;
1460
1556
  const { ctx, iteration } = state;
1461
- if (!generated.output.trim() || !ctx.chat) return;
1557
+ if (!generated.output.trim() || !ctx.chat || !((_iteration$response4 = iteration.response) === null || _iteration$response4 === void 0 ? void 0 : _iteration$response4.handler)) return;
1462
1558
  const startedAt = Date.now();
1463
1559
  const message = {
1464
1560
  type: "text",
1465
1561
  text: generated.output
1466
1562
  };
1467
1563
  try {
1468
- var _iteration$response4, _iteration$response4$;
1469
- await ((_iteration$response4 = iteration.response) === null || _iteration$response4 === void 0 || (_iteration$response4$ = _iteration$response4.handler) === null || _iteration$response4$ === void 0 ? void 0 : _iteration$response4$.call(_iteration$response4, generated.output.trim(), generated.messageMetadata));
1564
+ await iteration.response.handler(generated.output.trim(), generated.messageMetadata);
1470
1565
  } catch (cause) {
1471
1566
  if (isCriticalError(cause)) throw cause;
1472
1567
  throw new DeliveryError(`Assistant response delivery failed: ${getErrorMessage(cause)}`, { cause });
1473
1568
  }
1569
+ ctx.session.recordAssistantDelivery(iteration.id);
1474
1570
  iteration.recordTrace({
1475
1571
  type: "message_delivery",
1476
1572
  value: message,
@@ -1508,6 +1604,31 @@ async function settleJavaScriptCall(state, execution) {
1508
1604
  inspected: (outcome === null || outcome === void 0 ? void 0 : outcome.type) === "inspect"
1509
1605
  };
1510
1606
  if ((outcome === null || outcome === void 0 ? void 0 : outcome.type) === "inspect" && result.success) result.return_value = outcome.value;
1607
+ const forcedInspections = api.getForcedInspections();
1608
+ if (forcedInspections.length && !controller.signal.aborted && !isCriticalError(result.error)) {
1609
+ if (!result.success && result.error) {
1610
+ iteration.recordError(result.error);
1611
+ state.capture.downstreamError = result.error;
1612
+ }
1613
+ state.capture.forcedInspections = forcedInspections;
1614
+ let value = forcedInspections.length === 1 ? forcedInspections[0].value : forcedInspections.map((entry) => entry.value);
1615
+ if ((outcome === null || outcome === void 0 ? void 0 : outcome.type) === "inspect") value = outcome.value;
1616
+ state.capture.result = {
1617
+ ...result,
1618
+ success: true,
1619
+ signal: void 0,
1620
+ return_value: value
1621
+ };
1622
+ iteration.end({
1623
+ type: "thinking_requested",
1624
+ thinking_requested: {
1625
+ reason: "Tools completed successfully and requested forced inspection.",
1626
+ variables: value,
1627
+ metadata: forcedInspections.length === 1 ? forcedInspections[0].metadata : void 0
1628
+ }
1629
+ });
1630
+ return;
1631
+ }
1511
1632
  if ((outcome === null || outcome === void 0 ? void 0 : outcome.type) === "exit") {
1512
1633
  await completeJavaScriptExit(state, result, outcome);
1513
1634
  return;
@@ -1567,11 +1688,11 @@ function containsDecision(value, api, seen = /* @__PURE__ */ new Set()) {
1567
1688
  return Object.values(value).some((nested) => containsDecision(nested, api, seen));
1568
1689
  }
1569
1690
  async function completeJavaScriptExit(state, result, outcome) {
1570
- const { iteration, controller, props } = state;
1691
+ const { iteration, controller } = state;
1571
1692
  state.memory = commitMemory(state, result, false);
1572
1693
  try {
1573
1694
  controller.signal.throwIfAborted();
1574
- await applyNativeExit(iteration, outcome.exit, outcome.value, controller, props.onExit);
1695
+ await applyNativeExit(state, outcome.exit, outcome.value);
1575
1696
  } catch (error) {
1576
1697
  endFailedIteration(iteration, controller, error);
1577
1698
  }
@@ -1603,6 +1724,7 @@ async function deliverJavaScriptMessages({ ctx, iteration, controller }, message
1603
1724
  });
1604
1725
  throw isCriticalError(error) ? error : new DeliveryError(`Delivery ${message.id} failed: ${getErrorMessage(error)}. Its external outcome is uncertain. Later messages were skipped; earlier acknowledged messages remain delivered.`, { cause: error });
1605
1726
  }
1727
+ ctx.session.recordAssistantDelivery(iteration.id);
1606
1728
  iteration.recordTrace({
1607
1729
  type: "message_delivery",
1608
1730
  value: message.component,
@@ -1615,9 +1737,9 @@ async function deliverJavaScriptMessages({ ctx, iteration, controller }, message
1615
1737
  }
1616
1738
  }
1617
1739
  async function finishNativeResponse(state, generated) {
1618
- const { ctx, iteration, controller, props } = state;
1619
- if (!generated.toolCalls.length && generated.output.trim() && ctx.chat) {
1620
- await applyNativeExit(iteration, ListenExit, {}, controller, props.onExit);
1740
+ const { ctx, iteration } = state;
1741
+ if (!generated.toolCalls.length && ctx.chat && (generated.output.trim() || generated.metadata.stopReason === "stop")) {
1742
+ await applyNativeExit(state, ListenExit, {});
1621
1743
  if (!iteration.hasExited()) ctx.session.appendContext(ctx.inspector(iteration.error ?? "Completion rejected.", {
1622
1744
  purpose: "error",
1623
1745
  maxTokens: 200
@@ -1716,7 +1838,9 @@ function getExecutionOutcome(state, memory) {
1716
1838
  type: "inspect",
1717
1839
  value: (capture === null || capture === void 0 ? void 0 : capture.result.success) ? capture.result.return_value : void 0,
1718
1840
  available: memory.resultAvailable,
1719
- explicit: (capture === null || capture === void 0 ? void 0 : capture.inspected) ?? false
1841
+ explicit: (capture === null || capture === void 0 ? void 0 : capture.inspected) ?? false,
1842
+ forcedInspections: capture === null || capture === void 0 ? void 0 : capture.forcedInspections,
1843
+ downstreamError: capture === null || capture === void 0 ? void 0 : capture.downstreamError
1720
1844
  };
1721
1845
  }
1722
1846
  return {
@@ -1808,12 +1932,18 @@ function getIterationResult(state) {
1808
1932
  }
1809
1933
  if (iteration.status.type === "aborted") return new ErrorExecutionResult(ctx, iteration.error);
1810
1934
  }
1811
- async function applyNativeExit(iteration, exit, value, controller, onExit) {
1935
+ async function applyNativeExit(state, exit, value) {
1936
+ const { ctx, iteration, controller, props } = state;
1812
1937
  try {
1813
- await callHook(() => onExit === null || onExit === void 0 ? void 0 : onExit({
1814
- exit,
1815
- result: value
1816
- }, controller));
1938
+ var _props$options9;
1939
+ if (ctx.chat && exit === ListenExit && ((_props$options9 = props.options) === null || _props$options9 === void 0 ? void 0 : _props$options9.requireChatResponse) !== false && ctx.session.lastSpeaker !== "assistant") throw new MissingChatResponseError("The assistant has not delivered a message since the last user message. Send a response using the inspected results before waiting for the user. Do not repeat completed tool calls.");
1940
+ await callHook(() => {
1941
+ var _props$onExit;
1942
+ return (_props$onExit = props.onExit) === null || _props$onExit === void 0 ? void 0 : _props$onExit.call(props, {
1943
+ exit,
1944
+ result: value
1945
+ }, controller);
1946
+ });
1817
1947
  controller.signal.throwIfAborted();
1818
1948
  iteration.end({
1819
1949
  type: "exit_success",
@@ -1,7 +1,7 @@
1
1
  const require_utils = require("./utils-CTlsXvdj.cjs");
2
- const require_errors = require("./errors-IhnTKUp7.cjs");
2
+ const require_errors = require("./errors-C6ppQUZX.cjs");
3
3
  const require_uniq = require("./uniq-DiXgysNV.cjs");
4
- const require_schema = require("./schema-DBkjo0b7.cjs");
4
+ const require_schema = require("./schema-CXlnbb3n.cjs");
5
5
  //#region src/exit.ts
6
6
  var exit_exports = /* @__PURE__ */ require_utils.__exportAll({ Exit: () => Exit });
7
7
  /**
@@ -1,7 +1,7 @@
1
1
  import { Y as __exportAll, c as isValidIdentifier, l as isZuiSchema, n as fromJSONSchemaCompat, s as isJsonSchema } from "./utils-BOFzb8Ok.js";
2
- import { S as InvalidExitError } from "./errors-H4JJFH3S.js";
2
+ import { S as InvalidExitError } from "./errors-Crk5P8jo.js";
3
3
  import { t as uniq } from "./uniq-DfUeSNaX.js";
4
- import { i as toModelSchema } from "./schema-Aer_W7Al.js";
4
+ import { i as toModelSchema } from "./schema-GE4ISPCR.js";
5
5
  //#region src/exit.ts
6
6
  var exit_exports = /* @__PURE__ */ __exportAll({ Exit: () => Exit });
7
7
  /**
package/dist/index.cjs CHANGED
@@ -1,16 +1,16 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
2
  const require_utils = require("./utils-CTlsXvdj.cjs");
3
- const require_errors = require("./errors-IhnTKUp7.cjs");
4
- const require_component = require("./component-BpMVZYOa.cjs");
5
- const require_tool = require("./tool-Da_F-N-5.cjs");
6
- const require_exit = require("./exit-BUgJ5qi5.cjs");
7
- const require_truncate = require("./truncate-nV3Mxr6-.cjs");
8
- const require_quickjs_variant = require("./quickjs-variant-DJwYDSsb.cjs");
9
- const require_typings = require("./typings-C1ihexWE.cjs");
10
- const require_custom_client = require("./custom-client-MytucGI-.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-BwRYQ4Oa.cjs");
11
11
  let _bpinternal_zui = require("@bpinternal/zui");
12
12
  //#region package.json
13
- var version = "1.0.1";
13
+ var version = "1.0.3";
14
14
  //#endregion
15
15
  //#region src/objects.ts
16
16
  /**
@@ -619,7 +619,7 @@ const utils = {
619
619
  * })
620
620
  */
621
621
  const execute = async (props) => {
622
- const { executeContext } = await Promise.resolve().then(() => require("./execute-DLas4V2n.cjs"));
622
+ const { executeContext } = await Promise.resolve().then(() => require("./execute-DJBNrA2H.cjs"));
623
623
  return executeContext(props);
624
624
  };
625
625
  /**
@@ -628,14 +628,14 @@ const execute = async (props) => {
628
628
  * It's recommended to call this function at the beginning of your application without awaiting it (void init())
629
629
  */
630
630
  const init = async () => {
631
- await Promise.resolve().then(() => require("./execute-DLas4V2n.cjs"));
632
- await Promise.resolve().then(() => require("./component-BpMVZYOa.cjs")).then((n) => n.component_exports);
633
- await Promise.resolve().then(() => require("./tool-Da_F-N-5.cjs")).then((n) => n.tool_exports);
634
- await Promise.resolve().then(() => require("./exit-BUgJ5qi5.cjs")).then((n) => n.exit_exports);
635
- await Promise.resolve().then(() => require("./vm-XuVPuW3Y.cjs"));
631
+ await Promise.resolve().then(() => require("./execute-DJBNrA2H.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
636
  await Promise.resolve().then(() => require("./utils-CTlsXvdj.cjs")).then((n) => n.utils_exports);
637
- await Promise.resolve().then(() => require("./typings-C1ihexWE.cjs")).then((n) => n.typings_exports);
638
- await Promise.resolve().then(() => require("./native-Bm6L9zOb.cjs")).then((n) => n.native_exports);
637
+ await Promise.resolve().then(() => require("./typings-BA_XxAcY.cjs")).then((n) => n.typings_exports);
638
+ await Promise.resolve().then(() => require("./native-sbuzbLbY.cjs")).then((n) => n.native_exports);
639
639
  };
640
640
  //#endregion
641
641
  exports.AssignmentError = require_errors.AssignmentError;
@@ -673,6 +673,7 @@ exports.LoopExceededError = require_errors.LoopExceededError;
673
673
  exports.Memory = require_quickjs_variant.Memory;
674
674
  exports.MemoryCapacityError = require_errors.MemoryCapacityError;
675
675
  exports.MemoryValueError = require_errors.MemoryValueError;
676
+ exports.MissingChatResponseError = require_errors.MissingChatResponseError;
676
677
  exports.NativeProtocolError = require_errors.NativeProtocolError;
677
678
  exports.ObjectInstance = ObjectInstance;
678
679
  exports.ObjectPropertyError = require_errors.ObjectPropertyError;
package/dist/index.d.ts CHANGED
@@ -1,6 +1,6 @@
1
1
  export { version } from '../package.json';
2
2
  export { ThinkSignal, type ErrorDetails } from './errors.js';
3
- export { AssignmentError, CodeExecutionError, CodeFormattingError, CognitiveError, CompactionError, ComponentInputError, DeliveryError, ExecutionAbortedError, ExitInputError, HookError, HostOperationError, InternalError, InvalidCodeError, InvalidComponentError, InvalidConfigurationError, InvalidEventError, InvalidExitError, InvalidMessageError, InvalidObjectError, InvalidSessionError, InvalidToolError, isCriticalError, isLLMzError, LLMzError, LoopExceededError, MemoryCapacityError, MemoryValueError, NativeProtocolError, ObjectPropertyError, ReservedIdentifierError, SessionStateError, TokenOverflowError, ToolExecutionError, ToolInputError, UnknownComponentError, UnknownExitError, UnknownToolError, type ErrorCode, type LLMzFailure, type ToolInputIssue, type ValidationIssue, } from './errors/catalog.js';
3
+ export { AssignmentError, CodeExecutionError, CodeFormattingError, CognitiveError, CompactionError, ComponentInputError, DeliveryError, MissingChatResponseError, ExecutionAbortedError, ExitInputError, HookError, HostOperationError, InternalError, InvalidCodeError, InvalidComponentError, InvalidConfigurationError, InvalidEventError, InvalidExitError, InvalidMessageError, InvalidObjectError, InvalidSessionError, InvalidToolError, isCriticalError, isLLMzError, LLMzError, LoopExceededError, MemoryCapacityError, MemoryValueError, NativeProtocolError, ObjectPropertyError, ReservedIdentifierError, SessionStateError, TokenOverflowError, ToolExecutionError, ToolInputError, UnknownComponentError, UnknownExitError, UnknownToolError, type ErrorCode, type LLMzFailure, type ToolInputIssue, type ValidationIssue, } from './errors/catalog.js';
4
4
  export { Exit, type ExitResult } from './exit.js';
5
5
  export { inspect, type InspectOptions } from './inspect.js';
6
6
  export { createInspector, type InspectEvent, type InspectionIdentity, type InspectionPurpose, type Inspector, type OnInspect, } from './inspection.js';