zeitlich 0.2.28 → 0.2.30

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 (144) hide show
  1. package/README.md +121 -13
  2. package/dist/{activities-3xj_fEJK.d.ts → activities-BeveyY9b.d.cts} +2 -3
  3. package/dist/{activities-BzYq6jf7.d.cts → activities-NT3rcw66.d.ts} +2 -3
  4. package/dist/adapters/sandbox/bedrock/index.cjs.map +1 -1
  5. package/dist/adapters/sandbox/bedrock/index.d.cts +3 -3
  6. package/dist/adapters/sandbox/bedrock/index.d.ts +3 -3
  7. package/dist/adapters/sandbox/bedrock/index.js.map +1 -1
  8. package/dist/adapters/sandbox/bedrock/workflow.d.cts +2 -2
  9. package/dist/adapters/sandbox/bedrock/workflow.d.ts +2 -2
  10. package/dist/adapters/sandbox/daytona/index.cjs.map +1 -1
  11. package/dist/adapters/sandbox/daytona/index.d.cts +1 -1
  12. package/dist/adapters/sandbox/daytona/index.d.ts +1 -1
  13. package/dist/adapters/sandbox/daytona/index.js.map +1 -1
  14. package/dist/adapters/sandbox/daytona/workflow.d.cts +1 -1
  15. package/dist/adapters/sandbox/daytona/workflow.d.ts +1 -1
  16. package/dist/adapters/sandbox/e2b/index.cjs.map +1 -1
  17. package/dist/adapters/sandbox/e2b/index.d.cts +1 -1
  18. package/dist/adapters/sandbox/e2b/index.d.ts +1 -1
  19. package/dist/adapters/sandbox/e2b/index.js.map +1 -1
  20. package/dist/adapters/sandbox/e2b/workflow.d.cts +1 -1
  21. package/dist/adapters/sandbox/e2b/workflow.d.ts +1 -1
  22. package/dist/adapters/sandbox/inmemory/index.cjs.map +1 -1
  23. package/dist/adapters/sandbox/inmemory/index.d.cts +1 -1
  24. package/dist/adapters/sandbox/inmemory/index.d.ts +1 -1
  25. package/dist/adapters/sandbox/inmemory/index.js.map +1 -1
  26. package/dist/adapters/sandbox/inmemory/workflow.d.cts +1 -1
  27. package/dist/adapters/sandbox/inmemory/workflow.d.ts +1 -1
  28. package/dist/adapters/thread/anthropic/index.cjs +0 -1
  29. package/dist/adapters/thread/anthropic/index.cjs.map +1 -1
  30. package/dist/adapters/thread/anthropic/index.d.cts +6 -7
  31. package/dist/adapters/thread/anthropic/index.d.ts +6 -7
  32. package/dist/adapters/thread/anthropic/index.js +0 -1
  33. package/dist/adapters/thread/anthropic/index.js.map +1 -1
  34. package/dist/adapters/thread/anthropic/workflow.d.cts +5 -6
  35. package/dist/adapters/thread/anthropic/workflow.d.ts +5 -6
  36. package/dist/adapters/thread/google-genai/index.cjs +0 -1
  37. package/dist/adapters/thread/google-genai/index.cjs.map +1 -1
  38. package/dist/adapters/thread/google-genai/index.d.cts +6 -7
  39. package/dist/adapters/thread/google-genai/index.d.ts +6 -7
  40. package/dist/adapters/thread/google-genai/index.js +0 -1
  41. package/dist/adapters/thread/google-genai/index.js.map +1 -1
  42. package/dist/adapters/thread/google-genai/workflow.d.cts +5 -6
  43. package/dist/adapters/thread/google-genai/workflow.d.ts +5 -6
  44. package/dist/adapters/thread/langchain/index.cjs +0 -1
  45. package/dist/adapters/thread/langchain/index.cjs.map +1 -1
  46. package/dist/adapters/thread/langchain/index.d.cts +6 -7
  47. package/dist/adapters/thread/langchain/index.d.ts +6 -7
  48. package/dist/adapters/thread/langchain/index.js +0 -1
  49. package/dist/adapters/thread/langchain/index.js.map +1 -1
  50. package/dist/adapters/thread/langchain/workflow.d.cts +5 -6
  51. package/dist/adapters/thread/langchain/workflow.d.ts +5 -6
  52. package/dist/index.cjs +558 -50
  53. package/dist/index.cjs.map +1 -1
  54. package/dist/index.d.cts +136 -22
  55. package/dist/index.d.ts +136 -22
  56. package/dist/index.js +554 -52
  57. package/dist/index.js.map +1 -1
  58. package/dist/{proxy-7e7v8ccg.d.ts → proxy-BgswT47M.d.ts} +1 -1
  59. package/dist/{proxy-CsB8r0RR.d.cts → proxy-OJihshQF.d.cts} +1 -1
  60. package/dist/{thread-manager-D8C5QvLi.d.ts → thread-manager-BS477gj8.d.ts} +1 -1
  61. package/dist/{thread-manager-DdVFl1IY.d.cts → thread-manager-DH0zv05W.d.cts} +1 -1
  62. package/dist/{thread-manager-B5qA4v7V.d.ts → thread-manager-iUplxEZt.d.ts} +1 -1
  63. package/dist/{thread-manager-DFJ3sKKU.d.cts → thread-manager-lfN0V-gH.d.cts} +1 -1
  64. package/dist/{types-ChAMwU3q.d.cts → types-AujBIMMn.d.cts} +5 -8
  65. package/dist/{types-ChAMwU3q.d.ts → types-AujBIMMn.d.ts} +5 -8
  66. package/dist/{types-BZ75HpYd.d.ts → types-CCIc7Eam.d.ts} +1 -1
  67. package/dist/types-D90Q5aOh.d.ts +1212 -0
  68. package/dist/{types-BdCdR41N.d.ts → types-DBk-C8zM.d.ts} +1 -1
  69. package/dist/{types-ZHs2v9Ap.d.cts → types-DUvEZSDe.d.cts} +1 -1
  70. package/dist/types-DVdT5ybA.d.cts +1212 -0
  71. package/dist/{types-HbjqzyJH.d.cts → types-DgIVPOa1.d.cts} +1 -1
  72. package/dist/workflow-Cj4DxGdM.d.cts +750 -0
  73. package/dist/workflow-CzrBdCcJ.d.ts +750 -0
  74. package/dist/workflow.cjs +194 -40
  75. package/dist/workflow.cjs.map +1 -1
  76. package/dist/workflow.d.cts +5 -579
  77. package/dist/workflow.d.ts +5 -579
  78. package/dist/workflow.js +193 -42
  79. package/dist/workflow.js.map +1 -1
  80. package/package.json +3 -23
  81. package/src/adapters/thread/anthropic/thread-manager.ts +6 -6
  82. package/src/adapters/thread/google-genai/thread-manager.ts +6 -6
  83. package/src/adapters/thread/langchain/thread-manager.ts +6 -6
  84. package/src/index.ts +8 -0
  85. package/src/lib/lifecycle.ts +8 -3
  86. package/src/lib/observability/hooks.ts +117 -0
  87. package/src/lib/observability/index.ts +13 -0
  88. package/src/lib/observability/sinks.ts +88 -0
  89. package/src/lib/sandbox/index.ts +2 -4
  90. package/src/lib/sandbox/manager.ts +131 -16
  91. package/src/lib/sandbox/sandbox.test.ts +136 -16
  92. package/src/lib/sandbox/types.ts +6 -5
  93. package/src/lib/session/session-edge-cases.integration.test.ts +1 -0
  94. package/src/lib/session/session.integration.test.ts +7 -39
  95. package/src/lib/session/session.ts +119 -42
  96. package/src/lib/session/types.ts +39 -9
  97. package/src/lib/state/manager.integration.test.ts +1 -0
  98. package/src/lib/state/types.ts +9 -6
  99. package/src/lib/subagent/handler.ts +35 -12
  100. package/src/lib/subagent/register.ts +11 -12
  101. package/src/lib/subagent/subagent.integration.test.ts +1 -0
  102. package/src/lib/tool-router/router-edge-cases.integration.test.ts +2 -0
  103. package/src/lib/tool-router/router.integration.test.ts +2 -0
  104. package/src/lib/tool-router/router.ts +24 -2
  105. package/src/lib/types.ts +2 -0
  106. package/src/{adapters/sandbox/virtual → lib/virtual-fs}/filesystem.ts +4 -4
  107. package/src/lib/virtual-fs/index.ts +18 -0
  108. package/src/lib/virtual-fs/manager.ts +48 -0
  109. package/src/lib/virtual-fs/proxy.ts +45 -0
  110. package/src/{adapters/sandbox/virtual → lib/virtual-fs}/types.ts +41 -37
  111. package/src/{adapters/sandbox/virtual/virtual-sandbox.test.ts → lib/virtual-fs/virtual-fs.test.ts} +15 -130
  112. package/src/lib/virtual-fs/with-virtual-fs.ts +94 -0
  113. package/src/tools/bash/bash.test.ts +2 -1
  114. package/src/workflow.ts +25 -8
  115. package/tsup.config.ts +0 -2
  116. package/dist/adapters/sandbox/virtual/index.cjs +0 -487
  117. package/dist/adapters/sandbox/virtual/index.cjs.map +0 -1
  118. package/dist/adapters/sandbox/virtual/index.d.cts +0 -90
  119. package/dist/adapters/sandbox/virtual/index.d.ts +0 -90
  120. package/dist/adapters/sandbox/virtual/index.js +0 -479
  121. package/dist/adapters/sandbox/virtual/index.js.map +0 -1
  122. package/dist/adapters/sandbox/virtual/workflow.cjs +0 -33
  123. package/dist/adapters/sandbox/virtual/workflow.cjs.map +0 -1
  124. package/dist/adapters/sandbox/virtual/workflow.d.cts +0 -28
  125. package/dist/adapters/sandbox/virtual/workflow.d.ts +0 -28
  126. package/dist/adapters/sandbox/virtual/workflow.js +0 -31
  127. package/dist/adapters/sandbox/virtual/workflow.js.map +0 -1
  128. package/dist/queries-DVnukByF.d.cts +0 -44
  129. package/dist/queries-kjlvsUfz.d.ts +0 -44
  130. package/dist/types-BclYm5Ic.d.cts +0 -581
  131. package/dist/types-BclYm5Ic.d.ts +0 -581
  132. package/dist/types-BgsAwN3L.d.cts +0 -125
  133. package/dist/types-BtqbM1bO.d.ts +0 -490
  134. package/dist/types-BuCEZ4dF.d.cts +0 -490
  135. package/dist/types-yU5AINiP.d.ts +0 -125
  136. package/src/adapters/sandbox/virtual/index.ts +0 -92
  137. package/src/adapters/sandbox/virtual/provider.ts +0 -121
  138. package/src/adapters/sandbox/virtual/proxy.ts +0 -53
  139. package/src/adapters/sandbox/virtual/with-virtual-sandbox.ts +0 -97
  140. package/src/lib/.env +0 -1
  141. package/src/tools/bash/.env +0 -1
  142. /package/src/{adapters/sandbox/virtual → lib/virtual-fs}/mutations.ts +0 -0
  143. /package/src/{adapters/sandbox/virtual → lib/virtual-fs}/queries.ts +0 -0
  144. /package/src/{adapters/sandbox/virtual → lib/virtual-fs}/tree.ts +0 -0
package/dist/index.js CHANGED
@@ -1,4 +1,4 @@
1
- import { defineSignal, uuid4, setHandler, defineUpdate, ApplicationFailure, condition, defineQuery, workflowInfo, getExternalWorkflowHandle, log, startChild } from '@temporalio/workflow';
1
+ import { defineSignal, uuid4, setHandler, defineUpdate, ApplicationFailure, log, condition, defineQuery, proxySinks, workflowInfo, proxyActivities, getExternalWorkflowHandle, startChild } from '@temporalio/workflow';
2
2
  import z14, { z } from 'zod';
3
3
  import { randomUUID, randomFillSync } from 'crypto';
4
4
  import { ApplicationFailure as ApplicationFailure$1 } from '@temporalio/common';
@@ -129,6 +129,11 @@ function createToolRouter(options) {
129
129
  return null;
130
130
  }
131
131
  const effectiveArgs = preResult.args;
132
+ log.debug("tool call dispatched", {
133
+ toolName: toolCall.name,
134
+ toolCallId: toolCall.id,
135
+ turn
136
+ });
132
137
  let result;
133
138
  let content;
134
139
  let resultAppended = false;
@@ -155,6 +160,13 @@ function createToolRouter(options) {
155
160
  content = JSON.stringify(result, null, 2);
156
161
  }
157
162
  } catch (error) {
163
+ log.warn("tool call failed", {
164
+ toolName: toolCall.name,
165
+ toolCallId: toolCall.id,
166
+ turn,
167
+ durationMs: Date.now() - startTime,
168
+ error: error instanceof Error ? error.message : String(error)
169
+ });
158
170
  const recovery = await runFailureHooks(
159
171
  toolCall,
160
172
  tool,
@@ -180,19 +192,26 @@ function createToolRouter(options) {
180
192
  [uuid4(), config]
181
193
  );
182
194
  }
195
+ const durationMs = Date.now() - startTime;
183
196
  const toolResult = {
184
197
  toolCallId: toolCall.id,
185
198
  name: toolCall.name,
186
199
  data: result,
187
200
  ...metadata && { metadata }
188
201
  };
202
+ log.debug("tool call completed", {
203
+ toolName: toolCall.name,
204
+ toolCallId: toolCall.id,
205
+ turn,
206
+ durationMs
207
+ });
189
208
  await runPostHooks(
190
209
  toolCall,
191
210
  tool,
192
211
  toolResult,
193
212
  effectiveArgs,
194
213
  turn,
195
- Date.now() - startTime
214
+ durationMs
196
215
  );
197
216
  return toolResult;
198
217
  }
@@ -380,7 +399,7 @@ function resolveSandboxConfig(config) {
380
399
  if (config === "own") return { source: "own" };
381
400
  return { source: "own", shutdown: config.shutdown };
382
401
  }
383
- function createSubagentHandler(subagents, options) {
402
+ function createSubagentHandler(subagents) {
384
403
  const { taskQueue: parentTaskQueue } = workflowInfo();
385
404
  const childResults = /* @__PURE__ */ new Map();
386
405
  const pendingDestroys = /* @__PURE__ */ new Map();
@@ -408,15 +427,16 @@ function createSubagentHandler(subagents, options) {
408
427
  const continuationThreadId = args.threadId && allowsContinuation ? args.threadId : void 0;
409
428
  let thread;
410
429
  if (continuationThreadId) {
411
- thread = { mode: threadMode, threadId: continuationThreadId };
430
+ thread = {
431
+ mode: threadMode,
432
+ threadId: continuationThreadId
433
+ };
412
434
  }
413
435
  let sandbox;
414
436
  if (sandboxCfg.source === "inherit" && parentSandboxId) {
415
- const stateUpdate = options?.getSandboxStateForInheritance?.();
416
437
  sandbox = {
417
438
  mode: "inherit",
418
- sandboxId: parentSandboxId,
419
- ...stateUpdate && { stateUpdate }
439
+ sandboxId: parentSandboxId
420
440
  };
421
441
  } else if (sandboxCfg.source === "own") {
422
442
  const prevSbId = continuationThreadId ? threadSandboxes.get(continuationThreadId) : void 0;
@@ -435,6 +455,12 @@ function createSubagentHandler(subagents, options) {
435
455
  args: resolvedContext === void 0 ? [args.prompt, workflowInput] : [args.prompt, workflowInput, resolvedContext],
436
456
  taskQueue: config.taskQueue ?? parentTaskQueue
437
457
  };
458
+ log.info("subagent spawned", {
459
+ subagent: config.agentName,
460
+ childWorkflowId,
461
+ threadMode,
462
+ sandboxSource: sandboxCfg.source
463
+ });
438
464
  const childHandle = await startChild(config.workflow, childOpts);
439
465
  const effectiveShutdown = sandboxCfg.shutdown ?? "destroy";
440
466
  const shouldDeferDestroy = effectiveShutdown === "pause-until-parent-close" && (sandboxCfg.source === "own" || allowsContinuation && sandboxCfg.source !== "inherit");
@@ -451,11 +477,20 @@ function createSubagentHandler(subagents, options) {
451
477
  const childResult = childResults.get(childWorkflowId);
452
478
  childResults.delete(childWorkflowId);
453
479
  if (!childResult) {
480
+ log.warn("subagent returned no result", {
481
+ subagent: config.agentName,
482
+ childWorkflowId
483
+ });
454
484
  return {
455
485
  toolResponse: "Subagent workflow did not signal a result",
456
486
  data: null
457
487
  };
458
488
  }
489
+ log.info("subagent completed", {
490
+ subagent: config.agentName,
491
+ childWorkflowId,
492
+ ...childResult.usage && { usage: childResult.usage }
493
+ });
459
494
  const {
460
495
  toolResponse,
461
496
  data,
@@ -521,7 +556,7 @@ function createSubagentHandler(subagents, options) {
521
556
  }
522
557
 
523
558
  // src/lib/subagent/register.ts
524
- function buildSubagentRegistration(subagents, options) {
559
+ function buildSubagentRegistration(subagents) {
525
560
  if (subagents.length === 0) return null;
526
561
  const getEnabled = () => subagents.filter(
527
562
  (s) => typeof s.enabled === "function" ? s.enabled() : s.enabled ?? true
@@ -531,9 +566,7 @@ function buildSubagentRegistration(subagents, options) {
531
566
  if (s.hooks) subagentHooksMap.set(s.agentName, s.hooks);
532
567
  }
533
568
  const resolveSubagentName = (args) => args.subagent;
534
- const { handler, destroySubagentSandboxes } = createSubagentHandler(subagents, {
535
- getSandboxStateForInheritance: options?.getSandboxStateForInheritance
536
- });
569
+ const { handler, destroySubagentSandboxes } = createSubagentHandler(subagents);
537
570
  const registration = {
538
571
  name: SUBAGENT_TOOL_NAME,
539
572
  enabled: () => getEnabled().length > 0,
@@ -672,7 +705,9 @@ async function createSession({
672
705
  sandboxOps,
673
706
  thread: threadInit,
674
707
  sandbox: sandboxInit,
675
- sandboxShutdown = "destroy"
708
+ sandboxShutdown = "destroy",
709
+ virtualFs: virtualFsConfig,
710
+ virtualFsOps
676
711
  }) {
677
712
  const threadMode = threadInit?.mode ?? "new";
678
713
  let threadId;
@@ -698,11 +733,8 @@ async function createSession({
698
733
  } = threadOps;
699
734
  const plugins = [];
700
735
  let destroySubagentSandboxes;
701
- let sandboxStateGetter;
702
736
  if (subagents) {
703
- const result = buildSubagentRegistration(subagents, {
704
- getSandboxStateForInheritance: () => sandboxStateGetter?.()
705
- });
737
+ const result = buildSubagentRegistration(subagents);
706
738
  if (result) {
707
739
  plugins.push(result.registration);
708
740
  destroySubagentSandboxes = result.destroySubagentSandboxes;
@@ -758,23 +790,9 @@ async function createSession({
758
790
  const sandboxMode = sandboxInit?.mode;
759
791
  let sandboxId;
760
792
  let sandboxOwned = false;
761
- sandboxStateGetter = () => {
762
- const fileTree = stateManager.get("fileTree");
763
- const resolverContext = stateManager.get("resolverContext");
764
- const workspaceBase = stateManager.get("workspaceBase");
765
- if (!fileTree && !resolverContext && !workspaceBase) return void 0;
766
- return {
767
- ...fileTree !== void 0 && { fileTree },
768
- ...resolverContext !== void 0 && { resolverContext },
769
- ...workspaceBase !== void 0 && { workspaceBase }
770
- };
771
- };
772
793
  if (sandboxMode === "inherit") {
773
794
  const inheritInit = sandboxInit;
774
795
  sandboxId = inheritInit.sandboxId;
775
- if (inheritInit.stateUpdate) {
776
- stateManager.mergeUpdate(inheritInit.stateUpdate);
777
- }
778
796
  if (!sandboxOps) {
779
797
  throw ApplicationFailure.create({
780
798
  message: "sandboxId provided but no sandboxOps \u2014 cannot manage sandbox lifecycle",
@@ -803,14 +821,25 @@ async function createSession({
803
821
  sandboxOwned = true;
804
822
  } else if (sandboxOps) {
805
823
  const skillFiles = skills ? collectSkillFiles(skills) : void 0;
806
- const result = await sandboxOps.createSandbox(
807
- skillFiles ? { initialFiles: skillFiles } : void 0
808
- );
809
- sandboxId = result.sandboxId;
810
- sandboxOwned = true;
811
- if (result.stateUpdate) {
812
- stateManager.mergeUpdate(result.stateUpdate);
824
+ const ctx = sandboxInit?.ctx;
825
+ const createOptions = skillFiles ? { initialFiles: skillFiles } : void 0;
826
+ const result = await sandboxOps.createSandbox(createOptions, ctx);
827
+ if (result) {
828
+ sandboxId = result.sandboxId;
829
+ sandboxOwned = true;
830
+ }
831
+ }
832
+ if (virtualFsConfig) {
833
+ if (!virtualFsOps) {
834
+ throw ApplicationFailure.create({
835
+ message: "No virtualFsOps provided \u2014 cannot resolve file tree",
836
+ nonRetryable: true
837
+ });
813
838
  }
839
+ const result = await virtualFsOps.resolveFileTree(virtualFsConfig.ctx);
840
+ stateManager.mergeUpdate({
841
+ fileTree: result.fileTree
842
+ });
814
843
  }
815
844
  if (hooks.onSessionStart) {
816
845
  await hooks.onSessionStart({
@@ -819,6 +848,14 @@ async function createSession({
819
848
  metadata
820
849
  });
821
850
  }
851
+ log.info("session started", {
852
+ agentName,
853
+ threadId,
854
+ threadMode,
855
+ maxTurns,
856
+ ...sandboxId && { sandboxId }
857
+ });
858
+ const sessionStartMs = Date.now();
822
859
  const systemPrompt = stateManager.getSystemPrompt();
823
860
  if (threadMode === "fork" && sourceThreadId) {
824
861
  await forkThread(sourceThreadId, threadId, threadKey);
@@ -835,12 +872,18 @@ async function createSession({
835
872
  await initializeThread(threadId, threadKey);
836
873
  }
837
874
  }
838
- await appendHumanMessage(threadId, uuid4(), await buildContextMessage(), threadKey);
875
+ await appendHumanMessage(
876
+ threadId,
877
+ uuid4(),
878
+ await buildContextMessage(),
879
+ threadKey
880
+ );
839
881
  let exitReason = "completed";
840
882
  try {
841
883
  while (stateManager.isRunning() && !stateManager.isTerminal() && stateManager.getTurns() < maxTurns) {
842
884
  stateManager.incrementTurns();
843
885
  const currentTurn = stateManager.getTurns();
886
+ log.debug("turn started", { agentName, threadId, turn: currentTurn });
844
887
  stateManager.setTools(toolRouter.getToolDefinitions());
845
888
  const { message, rawToolCalls, usage } = await runAgent({
846
889
  threadId,
@@ -851,9 +894,24 @@ async function createSession({
851
894
  if (usage) {
852
895
  stateManager.updateUsage(usage);
853
896
  }
897
+ log.debug("model response received", {
898
+ agentName,
899
+ threadId,
900
+ turn: currentTurn,
901
+ toolCallCount: rawToolCalls.length,
902
+ ...usage && { usage }
903
+ });
854
904
  if (!toolRouter.hasTools() || rawToolCalls.length === 0) {
855
905
  stateManager.complete();
856
906
  exitReason = "completed";
907
+ log.info("session ended", {
908
+ agentName,
909
+ threadId,
910
+ exitReason,
911
+ turns: currentTurn,
912
+ durationMs: Date.now() - sessionStartMs,
913
+ usage: stateManager.getTotalUsage()
914
+ });
857
915
  return {
858
916
  threadId,
859
917
  finalMessage: message,
@@ -905,9 +963,21 @@ async function createSession({
905
963
  }
906
964
  if (stateManager.getTurns() >= maxTurns && stateManager.isRunning()) {
907
965
  exitReason = "max_turns";
966
+ log.warn("session hit max turns", {
967
+ agentName,
968
+ threadId,
969
+ maxTurns
970
+ });
908
971
  }
909
972
  } catch (error) {
910
973
  exitReason = "failed";
974
+ log.error("session failed", {
975
+ agentName,
976
+ threadId,
977
+ turns: stateManager.getTurns(),
978
+ durationMs: Date.now() - sessionStartMs,
979
+ error: error instanceof Error ? error.message : String(error)
980
+ });
911
981
  throw ApplicationFailure.fromError(error);
912
982
  } finally {
913
983
  await callSessionEnd(exitReason, stateManager.getTurns());
@@ -926,6 +996,14 @@ async function createSession({
926
996
  await destroySubagentSandboxes();
927
997
  }
928
998
  }
999
+ log.info("session ended", {
1000
+ agentName,
1001
+ threadId,
1002
+ exitReason,
1003
+ turns: stateManager.getTurns(),
1004
+ durationMs: Date.now() - sessionStartMs,
1005
+ usage: stateManager.getTotalUsage()
1006
+ });
929
1007
  return {
930
1008
  threadId,
931
1009
  finalMessage: null,
@@ -1263,6 +1341,60 @@ function defineSubagentWorkflow(config, fn) {
1263
1341
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
1264
1342
  });
1265
1343
  }
1344
+ function createObservabilityHooks(agentName) {
1345
+ const { zeitlichMetrics } = proxySinks();
1346
+ let sessionStartMs = Date.now();
1347
+ return {
1348
+ onSessionStart: (ctx) => {
1349
+ sessionStartMs = Date.now();
1350
+ zeitlichMetrics.sessionStarted({
1351
+ agentName,
1352
+ threadId: ctx.threadId,
1353
+ metadata: ctx.metadata
1354
+ });
1355
+ },
1356
+ onSessionEnd: (ctx) => {
1357
+ zeitlichMetrics.sessionEnded({
1358
+ agentName,
1359
+ threadId: ctx.threadId,
1360
+ exitReason: ctx.exitReason,
1361
+ turns: ctx.turns,
1362
+ usage: {},
1363
+ durationMs: Date.now() - sessionStartMs
1364
+ });
1365
+ },
1366
+ onPostToolUse: (ctx) => {
1367
+ zeitlichMetrics.toolExecuted({
1368
+ agentName,
1369
+ toolName: ctx.toolCall.name,
1370
+ durationMs: ctx.durationMs,
1371
+ success: true,
1372
+ threadId: ctx.threadId,
1373
+ turn: ctx.turn
1374
+ });
1375
+ },
1376
+ onPostToolUseFailure: (ctx) => {
1377
+ zeitlichMetrics.toolExecuted({
1378
+ agentName,
1379
+ toolName: ctx.toolCall.name,
1380
+ durationMs: 0,
1381
+ success: false,
1382
+ threadId: ctx.threadId,
1383
+ turn: ctx.turn
1384
+ });
1385
+ return {};
1386
+ }
1387
+ };
1388
+ }
1389
+ function composeHooks(...fns) {
1390
+ return async (...args) => {
1391
+ let lastResult;
1392
+ for (const fn of fns) {
1393
+ lastResult = await fn(...args);
1394
+ }
1395
+ return lastResult;
1396
+ };
1397
+ }
1266
1398
  var SandboxNotSupportedError = class extends ApplicationFailure$1 {
1267
1399
  constructor(operation) {
1268
1400
  super(
@@ -1278,7 +1410,7 @@ var SandboxNotFoundError = class extends ApplicationFailure$1 {
1278
1410
  }
1279
1411
  };
1280
1412
 
1281
- // src/adapters/sandbox/virtual/mutations.ts
1413
+ // src/lib/virtual-fs/mutations.ts
1282
1414
  function applyVirtualTreeMutations(stateManager, mutations) {
1283
1415
  let tree = [...stateManager.get("fileTree")];
1284
1416
  for (const m of mutations) {
@@ -1300,7 +1432,7 @@ function applyVirtualTreeMutations(stateManager, mutations) {
1300
1432
  return tree;
1301
1433
  }
1302
1434
 
1303
- // src/adapters/sandbox/virtual/tree.ts
1435
+ // src/lib/virtual-fs/tree.ts
1304
1436
  var buildTree = (entries) => {
1305
1437
  const root = { name: "/", children: /* @__PURE__ */ new Map(), isFile: false };
1306
1438
  for (const entry of entries) {
@@ -1348,7 +1480,7 @@ function formatVirtualFileTree(entries, opts = {}) {
1348
1480
  return "/" + printNode(root, "", sort);
1349
1481
  }
1350
1482
 
1351
- // src/adapters/sandbox/virtual/queries.ts
1483
+ // src/lib/virtual-fs/queries.ts
1352
1484
  function hasFileWithMimeType(stateManager, pattern) {
1353
1485
  const tree = stateManager.get("fileTree");
1354
1486
  const matchers = (Array.isArray(pattern) ? pattern : [pattern]).map(buildMatcher);
@@ -1389,6 +1521,25 @@ function buildGlobMatcher(pattern) {
1389
1521
  );
1390
1522
  return (v) => re.test(v);
1391
1523
  }
1524
+ function proxyVirtualFsOps(scope, options) {
1525
+ const resolvedScope = scope ?? workflowInfo().workflowType;
1526
+ const acts = proxyActivities(
1527
+ options ?? {
1528
+ startToCloseTimeout: "30s",
1529
+ retry: {
1530
+ maximumAttempts: 3,
1531
+ initialInterval: "2s",
1532
+ maximumInterval: "30s",
1533
+ backoffCoefficient: 2
1534
+ }
1535
+ }
1536
+ );
1537
+ const prefix = resolvedScope;
1538
+ const p = (key) => `${prefix}${key.charAt(0).toUpperCase()}${key.slice(1)}`;
1539
+ return {
1540
+ resolveFileTree: acts[p("resolveFileTree")]
1541
+ };
1542
+ }
1392
1543
 
1393
1544
  // src/lib/skills/parse.ts
1394
1545
  function parseSkillFile(raw) {
@@ -2023,12 +2174,41 @@ function withParentWorkflowState(client, handler) {
2023
2174
 
2024
2175
  // src/lib/sandbox/manager.ts
2025
2176
  var SandboxManager = class {
2026
- constructor(provider) {
2177
+ constructor(provider, options) {
2027
2178
  this.provider = provider;
2028
- }
2029
- async create(options) {
2030
- const { sandbox, stateUpdate } = await this.provider.create(options);
2031
- return { sandboxId: sandbox.id, ...stateUpdate && { stateUpdate } };
2179
+ this.hooks = options?.hooks ?? {};
2180
+ }
2181
+ hooks;
2182
+ async create(options, ctx) {
2183
+ let providerOptions = options;
2184
+ if (this.hooks.onPreCreate) {
2185
+ const hookResult = await this.hooks.onPreCreate(
2186
+ options ?? {},
2187
+ ctx ?? {}
2188
+ );
2189
+ if (hookResult?.skip) return null;
2190
+ if (hookResult?.modifiedOptions) {
2191
+ const orig = options ?? {};
2192
+ const mod = hookResult.modifiedOptions;
2193
+ providerOptions = {
2194
+ ...mod,
2195
+ ...orig,
2196
+ initialFiles: {
2197
+ ...mod.initialFiles,
2198
+ ...orig.initialFiles
2199
+ },
2200
+ env: {
2201
+ ...mod.env,
2202
+ ...orig.env
2203
+ }
2204
+ };
2205
+ }
2206
+ }
2207
+ const { sandbox } = await this.provider.create(providerOptions);
2208
+ if (this.hooks.onPostCreate) {
2209
+ await this.hooks.onPostCreate(sandbox.id);
2210
+ }
2211
+ return { sandboxId: sandbox.id };
2032
2212
  }
2033
2213
  async getSandbox(id) {
2034
2214
  return this.provider.get(id);
@@ -2065,16 +2245,16 @@ var SandboxManager = class {
2065
2245
  * manager.createActivities("CodingAgent");
2066
2246
  * // registers: inMemoryCodingAgentCreateSandbox, inMemoryCodingAgentDestroySandbox, …
2067
2247
  *
2068
- * const vmgr = new SandboxManager(new VirtualSandboxProvider(resolver));
2069
- * vmgr.createActivities("CodingAgent");
2070
- * // registers: virtualCodingAgentCreateSandbox, …
2248
+ * const dmgr = new SandboxManager(new DaytonaSandboxProvider(config));
2249
+ * dmgr.createActivities("CodingAgent");
2250
+ * // registers: daytonaCodingAgentCreateSandbox, …
2071
2251
  * ```
2072
2252
  */
2073
2253
  createActivities(scope) {
2074
2254
  const prefix = `${this.provider.id}${scope.charAt(0).toUpperCase()}${scope.slice(1)}`;
2075
2255
  const ops = {
2076
- createSandbox: async (options) => {
2077
- return this.create(options);
2256
+ createSandbox: async (options, ctx) => {
2257
+ return this.create(options, ctx);
2078
2258
  },
2079
2259
  destroySandbox: async (sandboxId) => {
2080
2260
  await this.destroy(sandboxId);
@@ -2164,6 +2344,328 @@ var NodeFsSandboxFileSystem = class {
2164
2344
  return posix.resolve(base, path);
2165
2345
  }
2166
2346
  };
2347
+ function normalisePath(p, workspaceBase = "/") {
2348
+ return posix.resolve(workspaceBase, p);
2349
+ }
2350
+ function parentDir(p) {
2351
+ const idx = p.lastIndexOf("/");
2352
+ return idx <= 0 ? "/" : p.slice(0, idx);
2353
+ }
2354
+ function inferDirectories(entries, workspaceBase) {
2355
+ const dirs = /* @__PURE__ */ new Set();
2356
+ dirs.add("/");
2357
+ for (const entry of entries) {
2358
+ let dir = parentDir(normalisePath(entry.path, workspaceBase));
2359
+ while (dir !== "/" && !dirs.has(dir)) {
2360
+ dirs.add(dir);
2361
+ dir = parentDir(dir);
2362
+ }
2363
+ dirs.add("/");
2364
+ }
2365
+ return dirs;
2366
+ }
2367
+ var VirtualFileSystem = class {
2368
+ constructor(tree, resolver, ctx, workspaceBase = "/") {
2369
+ this.resolver = resolver;
2370
+ this.ctx = ctx;
2371
+ this.workspaceBase = normalisePath(workspaceBase);
2372
+ this.entries = new Map(
2373
+ tree.map((e) => [normalisePath(e.path, this.workspaceBase), e])
2374
+ );
2375
+ this.directories = inferDirectories(tree, this.workspaceBase);
2376
+ }
2377
+ workspaceBase;
2378
+ entries;
2379
+ directories;
2380
+ mutations = [];
2381
+ /** Return all mutations accumulated during this invocation. */
2382
+ getMutations() {
2383
+ return this.mutations;
2384
+ }
2385
+ /** Look up a file entry by virtual path. */
2386
+ getEntry(path) {
2387
+ return this.entries.get(normalisePath(path, this.workspaceBase));
2388
+ }
2389
+ // --------------------------------------------------------------------------
2390
+ // Read operations — delegate to resolver lazily
2391
+ // --------------------------------------------------------------------------
2392
+ async readFile(path) {
2393
+ const norm = normalisePath(path, this.workspaceBase);
2394
+ const entry = this.entries.get(norm);
2395
+ if (!entry) throw new Error(`ENOENT: no such file: ${path}`);
2396
+ return this.resolver.readFile(entry.id, this.ctx, entry.metadata);
2397
+ }
2398
+ async readFileBuffer(path) {
2399
+ const norm = normalisePath(path, this.workspaceBase);
2400
+ const entry = this.entries.get(norm);
2401
+ if (!entry) throw new Error(`ENOENT: no such file: ${path}`);
2402
+ return this.resolver.readFileBuffer(entry.id, this.ctx, entry.metadata);
2403
+ }
2404
+ // --------------------------------------------------------------------------
2405
+ // Metadata operations — pure, resolved from the tree
2406
+ // --------------------------------------------------------------------------
2407
+ async exists(path) {
2408
+ const norm = normalisePath(path, this.workspaceBase);
2409
+ return this.entries.has(norm) || this.directories.has(norm);
2410
+ }
2411
+ async stat(path) {
2412
+ const norm = normalisePath(path, this.workspaceBase);
2413
+ const entry = this.entries.get(norm);
2414
+ if (entry) {
2415
+ return {
2416
+ isFile: true,
2417
+ isDirectory: false,
2418
+ isSymbolicLink: false,
2419
+ size: entry.size,
2420
+ mtime: new Date(entry.mtime)
2421
+ };
2422
+ }
2423
+ if (this.directories.has(norm)) {
2424
+ return {
2425
+ isFile: false,
2426
+ isDirectory: true,
2427
+ isSymbolicLink: false,
2428
+ size: 0,
2429
+ mtime: /* @__PURE__ */ new Date()
2430
+ };
2431
+ }
2432
+ throw new Error(`ENOENT: no such file or directory: ${path}`);
2433
+ }
2434
+ async readdir(path) {
2435
+ const norm = normalisePath(path, this.workspaceBase);
2436
+ if (!this.directories.has(norm)) {
2437
+ throw new Error(`ENOENT: no such directory: ${path}`);
2438
+ }
2439
+ const prefix = norm === "/" ? "/" : norm + "/";
2440
+ const names = /* @__PURE__ */ new Set();
2441
+ for (const p of this.entries.keys()) {
2442
+ if (p.startsWith(prefix)) {
2443
+ const rest = p.slice(prefix.length);
2444
+ const seg = rest.split("/")[0];
2445
+ if (seg) names.add(seg);
2446
+ }
2447
+ }
2448
+ for (const d of this.directories) {
2449
+ if (d.startsWith(prefix) && d !== norm) {
2450
+ const rest = d.slice(prefix.length);
2451
+ const seg = rest.split("/")[0];
2452
+ if (seg) names.add(seg);
2453
+ }
2454
+ }
2455
+ return [...names].sort();
2456
+ }
2457
+ async readdirWithFileTypes(path) {
2458
+ const names = await this.readdir(path);
2459
+ const norm = normalisePath(path, this.workspaceBase);
2460
+ const prefix = norm === "/" ? "/" : norm + "/";
2461
+ return names.map((name) => {
2462
+ const full = prefix + name;
2463
+ const isFile = this.entries.has(full);
2464
+ const isDirectory = this.directories.has(full);
2465
+ return { name, isFile, isDirectory, isSymbolicLink: false };
2466
+ });
2467
+ }
2468
+ // --------------------------------------------------------------------------
2469
+ // Write operations — delegate to resolver, record mutations
2470
+ // --------------------------------------------------------------------------
2471
+ async writeFile(path, content) {
2472
+ const norm = normalisePath(path, this.workspaceBase);
2473
+ const existing = this.entries.get(norm);
2474
+ if (existing) {
2475
+ await this.resolver.writeFile(
2476
+ existing.id,
2477
+ content,
2478
+ this.ctx,
2479
+ existing.metadata
2480
+ );
2481
+ const size = typeof content === "string" ? new TextEncoder().encode(content).byteLength : content.byteLength;
2482
+ const updated = {
2483
+ ...existing,
2484
+ size,
2485
+ mtime: (/* @__PURE__ */ new Date()).toISOString()
2486
+ };
2487
+ this.entries.set(norm, updated);
2488
+ this.mutations.push({ type: "update", path: norm, entry: updated });
2489
+ } else {
2490
+ const entry = await this.resolver.createFile(norm, content, this.ctx);
2491
+ const normalised = { ...entry, path: norm };
2492
+ this.entries.set(norm, normalised);
2493
+ this.addParentDirectories(norm);
2494
+ this.mutations.push({ type: "add", entry: normalised });
2495
+ }
2496
+ }
2497
+ async appendFile(path, content) {
2498
+ const norm = normalisePath(path, this.workspaceBase);
2499
+ const existing = this.entries.get(norm);
2500
+ if (!existing) {
2501
+ return this.writeFile(path, content);
2502
+ }
2503
+ const current = await this.resolver.readFile(
2504
+ existing.id,
2505
+ this.ctx,
2506
+ existing.metadata
2507
+ );
2508
+ const appended = typeof content === "string" ? current + content : current + new TextDecoder().decode(content);
2509
+ await this.resolver.writeFile(
2510
+ existing.id,
2511
+ appended,
2512
+ this.ctx,
2513
+ existing.metadata
2514
+ );
2515
+ const size = new TextEncoder().encode(appended).byteLength;
2516
+ const updated = {
2517
+ ...existing,
2518
+ size,
2519
+ mtime: (/* @__PURE__ */ new Date()).toISOString()
2520
+ };
2521
+ this.entries.set(norm, updated);
2522
+ this.mutations.push({ type: "update", path: norm, entry: updated });
2523
+ }
2524
+ async mkdir(_path, _options) {
2525
+ const norm = normalisePath(_path, this.workspaceBase);
2526
+ if (this.directories.has(norm)) return;
2527
+ if (_options?.recursive) {
2528
+ this.addParentDirectories(norm + "/placeholder");
2529
+ this.directories.add(norm);
2530
+ } else {
2531
+ const parent = parentDir(norm);
2532
+ if (!this.directories.has(parent)) {
2533
+ throw new Error(`ENOENT: no such directory: ${parent}`);
2534
+ }
2535
+ this.directories.add(norm);
2536
+ }
2537
+ }
2538
+ async rm(path, options) {
2539
+ const norm = normalisePath(path, this.workspaceBase);
2540
+ const entry = this.entries.get(norm);
2541
+ if (entry) {
2542
+ await this.resolver.deleteFile(entry.id, this.ctx, entry.metadata);
2543
+ this.entries.delete(norm);
2544
+ this.mutations.push({ type: "remove", path: norm });
2545
+ return;
2546
+ }
2547
+ if (this.directories.has(norm)) {
2548
+ if (!options?.recursive) {
2549
+ throw new Error(`EISDIR: is a directory (use recursive): ${path}`);
2550
+ }
2551
+ const prefix = norm === "/" ? "/" : norm + "/";
2552
+ for (const [p, e] of this.entries) {
2553
+ if (p.startsWith(prefix)) {
2554
+ await this.resolver.deleteFile(e.id, this.ctx, e.metadata);
2555
+ this.entries.delete(p);
2556
+ this.mutations.push({ type: "remove", path: p });
2557
+ }
2558
+ }
2559
+ for (const d of this.directories) {
2560
+ if (d.startsWith(prefix)) this.directories.delete(d);
2561
+ }
2562
+ this.directories.delete(norm);
2563
+ return;
2564
+ }
2565
+ if (!options?.force) {
2566
+ throw new Error(`ENOENT: no such file or directory: ${path}`);
2567
+ }
2568
+ }
2569
+ async cp(src, dest, _options) {
2570
+ const normSrc = normalisePath(src, this.workspaceBase);
2571
+ const normDest = normalisePath(dest, this.workspaceBase);
2572
+ const entry = this.entries.get(normSrc);
2573
+ if (entry) {
2574
+ const content = await this.resolver.readFile(
2575
+ entry.id,
2576
+ this.ctx,
2577
+ entry.metadata
2578
+ );
2579
+ await this.writeFile(normDest, content);
2580
+ return;
2581
+ }
2582
+ if (!this.directories.has(normSrc)) {
2583
+ throw new Error(`ENOENT: no such file or directory: ${src}`);
2584
+ }
2585
+ if (!_options?.recursive) {
2586
+ throw new Error(`EISDIR: is a directory (use recursive): ${src}`);
2587
+ }
2588
+ const prefix = normSrc === "/" ? "/" : normSrc + "/";
2589
+ for (const [p, e] of this.entries) {
2590
+ if (p.startsWith(prefix)) {
2591
+ const relative = p.slice(normSrc.length);
2592
+ const content = await this.resolver.readFile(
2593
+ e.id,
2594
+ this.ctx,
2595
+ e.metadata
2596
+ );
2597
+ await this.writeFile(normDest + relative, content);
2598
+ }
2599
+ }
2600
+ }
2601
+ async mv(src, dest) {
2602
+ await this.cp(src, dest, { recursive: true });
2603
+ await this.rm(src, { recursive: true });
2604
+ }
2605
+ // --------------------------------------------------------------------------
2606
+ // Unsupported
2607
+ // --------------------------------------------------------------------------
2608
+ async readlink(_path) {
2609
+ throw new SandboxNotSupportedError("readlink");
2610
+ }
2611
+ resolvePath(base, path) {
2612
+ return posix.resolve(normalisePath(base, this.workspaceBase), path);
2613
+ }
2614
+ // --------------------------------------------------------------------------
2615
+ // Helpers
2616
+ // --------------------------------------------------------------------------
2617
+ addParentDirectories(filePath) {
2618
+ let dir = parentDir(normalisePath(filePath, this.workspaceBase));
2619
+ while (!this.directories.has(dir)) {
2620
+ this.directories.add(dir);
2621
+ dir = parentDir(dir);
2622
+ }
2623
+ }
2624
+ };
2625
+
2626
+ // src/lib/virtual-fs/with-virtual-fs.ts
2627
+ function withVirtualFs(client, resolver, handler) {
2628
+ return async (args, context) => {
2629
+ const state = await queryParentWorkflowState(client);
2630
+ const { fileTree, ctx, workspaceBase } = state;
2631
+ if (!fileTree) {
2632
+ return {
2633
+ toolResponse: `Error: No fileTree in agent state. The ${context.toolName} tool requires a virtual filesystem.`,
2634
+ data: null
2635
+ };
2636
+ }
2637
+ const virtualFs = new VirtualFileSystem(
2638
+ fileTree,
2639
+ resolver,
2640
+ ctx,
2641
+ workspaceBase ?? "/"
2642
+ );
2643
+ const response = await handler(args, { ...context, virtualFs });
2644
+ const mutations = virtualFs.getMutations();
2645
+ return {
2646
+ toolResponse: response.toolResponse,
2647
+ data: {
2648
+ ...response.data ?? {},
2649
+ treeMutations: mutations
2650
+ }
2651
+ };
2652
+ };
2653
+ }
2654
+
2655
+ // src/lib/virtual-fs/manager.ts
2656
+ function createVirtualFsActivities(resolver, scope) {
2657
+ const ops = {
2658
+ resolveFileTree: async (ctx) => {
2659
+ const fileTree = await resolver.resolveEntries(ctx);
2660
+ return { fileTree };
2661
+ }
2662
+ };
2663
+ const prefix = scope;
2664
+ const cap = (s) => s.charAt(0).toUpperCase() + s.slice(1);
2665
+ return Object.fromEntries(
2666
+ Object.entries(ops).map(([k, v]) => [`${prefix}${cap(k)}`, v])
2667
+ );
2668
+ }
2167
2669
 
2168
2670
  // src/tools/bash/handler.ts
2169
2671
  var bashHandler = async (args, { sandbox }) => {
@@ -2419,6 +2921,6 @@ var toTree = async (fs, opts = {}) => {
2419
2921
  return base + subtree;
2420
2922
  };
2421
2923
 
2422
- export { FileSystemSkillProvider, NodeFsSandboxFileSystem, SandboxManager, SandboxNotFoundError, SandboxNotSupportedError, applyVirtualTreeMutations, askUserQuestionTool, bashHandler, bashTool, createAgentStateManager, createAskUserQuestionHandler, createBashToolDescription, createReadSkillHandler, createReadSkillTool, createRunAgentActivity, createSession, createTaskCreateHandler, createTaskGetHandler, createTaskListHandler, createTaskUpdateHandler, createThreadManager, createToolRouter, defineSubagent, defineSubagentWorkflow, defineTool, defineWorkflow, editHandler, editTool, filesWithMimeType, formatVirtualFileTree, getShortId, globHandler, globTool, grepTool, hasDirectory, hasFileWithMimeType, hasNoOtherToolCalls, isTerminalStatus, parseSkillFile, queryParentWorkflowState, readFileHandler, readFileTool, taskCreateTool, taskGetTool, taskListTool, taskUpdateTool, toTree, withAutoAppend, withParentWorkflowState, withSandbox, writeFileHandler, writeFileTool };
2924
+ export { FileSystemSkillProvider, NodeFsSandboxFileSystem, SandboxManager, SandboxNotFoundError, SandboxNotSupportedError, VirtualFileSystem, applyVirtualTreeMutations, askUserQuestionTool, bashHandler, bashTool, composeHooks, createAgentStateManager, createAskUserQuestionHandler, createBashToolDescription, createObservabilityHooks, createReadSkillHandler, createReadSkillTool, createRunAgentActivity, createSession, createTaskCreateHandler, createTaskGetHandler, createTaskListHandler, createTaskUpdateHandler, createThreadManager, createToolRouter, createVirtualFsActivities, defineSubagent, defineSubagentWorkflow, defineTool, defineWorkflow, editHandler, editTool, filesWithMimeType, formatVirtualFileTree, getShortId, globHandler, globTool, grepTool, hasDirectory, hasFileWithMimeType, hasNoOtherToolCalls, isTerminalStatus, parseSkillFile, proxyVirtualFsOps, queryParentWorkflowState, readFileHandler, readFileTool, taskCreateTool, taskGetTool, taskListTool, taskUpdateTool, toTree, withAutoAppend, withParentWorkflowState, withSandbox, withVirtualFs, writeFileHandler, writeFileTool };
2423
2925
  //# sourceMappingURL=index.js.map
2424
2926
  //# sourceMappingURL=index.js.map