@mastra/inngest 0.0.0-redis-cloud-transporter-20250508194049 → 0.0.0-support-d1-client-20250701191943

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -1,19 +1,26 @@
1
1
  import { randomUUID } from 'crypto';
2
2
  import { subscribe } from '@inngest/realtime';
3
3
  import { RuntimeContext } from '@mastra/core/di';
4
- import { Run, NewWorkflow, cloneStep, createStep, DefaultExecutionEngine } from '@mastra/core/workflows/vNext';
4
+ import { Tool } from '@mastra/core/tools';
5
+ import { Run, Workflow, DefaultExecutionEngine } from '@mastra/core/workflows';
6
+ import { EMITTER_SYMBOL } from '@mastra/core/workflows/_constants';
5
7
  import { serve as serve$1 } from 'inngest/hono';
8
+ import { z } from 'zod';
6
9
 
7
10
  // src/index.ts
8
11
  function serve({ mastra, inngest }) {
9
- const wfs = mastra.vnext_getWorkflows();
10
- const functions = Object.values(wfs).flatMap((wf) => {
11
- if (wf instanceof InngestWorkflow) {
12
- wf.__registerMastra(mastra);
13
- return wf.getFunctions();
14
- }
15
- return [];
16
- });
12
+ const wfs = mastra.getWorkflows();
13
+ const functions = Array.from(
14
+ new Set(
15
+ Object.values(wfs).flatMap((wf) => {
16
+ if (wf instanceof InngestWorkflow) {
17
+ wf.__registerMastra(mastra);
18
+ return wf.getFunctions();
19
+ }
20
+ return [];
21
+ })
22
+ )
23
+ );
17
24
  return serve$1({
18
25
  client: inngest,
19
26
  functions
@@ -21,14 +28,16 @@ function serve({ mastra, inngest }) {
21
28
  }
22
29
  var InngestRun = class extends Run {
23
30
  inngest;
31
+ serializedStepGraph;
24
32
  #mastra;
25
33
  constructor(params, inngest) {
26
34
  super(params);
27
35
  this.inngest = inngest;
36
+ this.serializedStepGraph = params.serializedStepGraph;
28
37
  this.#mastra = params.mastra;
29
38
  }
30
39
  async getRuns(eventId) {
31
- const response = await fetch(`${this.inngest.apiBaseUrl}/v1/events/${eventId}/runs`, {
40
+ const response = await fetch(`${this.inngest.apiBaseUrl ?? "https://api.inngest.com"}/v1/events/${eventId}/runs`, {
32
41
  headers: {
33
42
  Authorization: `Bearer ${process.env.INNGEST_SIGNING_KEY}`
34
43
  }
@@ -38,15 +47,49 @@ var InngestRun = class extends Run {
38
47
  }
39
48
  async getRunOutput(eventId) {
40
49
  let runs = await this.getRuns(eventId);
41
- while (runs?.[0]?.status !== "Completed") {
50
+ while (runs?.[0]?.status !== "Completed" || runs?.[0]?.event_id !== eventId) {
42
51
  await new Promise((resolve) => setTimeout(resolve, 1e3));
43
52
  runs = await this.getRuns(eventId);
44
- if (runs?.[0]?.status === "Failed" || runs?.[0]?.status === "Cancelled") {
53
+ if (runs?.[0]?.status === "Failed") {
45
54
  throw new Error(`Function run ${runs?.[0]?.status}`);
55
+ } else if (runs?.[0]?.status === "Cancelled") {
56
+ const snapshot = await this.#mastra?.storage?.loadWorkflowSnapshot({
57
+ workflowName: this.workflowId,
58
+ runId: this.runId
59
+ });
60
+ return { output: { result: { steps: snapshot?.context, status: "canceled" } } };
46
61
  }
47
62
  }
48
63
  return runs?.[0];
49
64
  }
65
+ async sendEvent(event, data) {
66
+ await this.inngest.send({
67
+ name: `user-event-${event}`,
68
+ data
69
+ });
70
+ }
71
+ async cancel() {
72
+ await this.inngest.send({
73
+ name: `cancel.workflow.${this.workflowId}`,
74
+ data: {
75
+ runId: this.runId
76
+ }
77
+ });
78
+ const snapshot = await this.#mastra?.storage?.loadWorkflowSnapshot({
79
+ workflowName: this.workflowId,
80
+ runId: this.runId
81
+ });
82
+ if (snapshot) {
83
+ await this.#mastra?.storage?.persistWorkflowSnapshot({
84
+ workflowName: this.workflowId,
85
+ runId: this.runId,
86
+ snapshot: {
87
+ ...snapshot,
88
+ status: "canceled"
89
+ }
90
+ });
91
+ }
92
+ }
50
93
  async start({
51
94
  inputData
52
95
  }) {
@@ -55,11 +98,13 @@ var InngestRun = class extends Run {
55
98
  runId: this.runId,
56
99
  snapshot: {
57
100
  runId: this.runId,
101
+ serializedStepGraph: this.serializedStepGraph,
58
102
  value: {},
59
103
  context: {},
60
104
  activePaths: [],
61
105
  suspendedPaths: {},
62
- timestamp: Date.now()
106
+ timestamp: Date.now(),
107
+ status: "running"
63
108
  }
64
109
  });
65
110
  const eventOutput = await this.inngest.send({
@@ -78,10 +123,23 @@ var InngestRun = class extends Run {
78
123
  if (result.status === "failed") {
79
124
  result.error = new Error(result.error);
80
125
  }
81
- this.cleanup?.();
126
+ if (result.status !== "suspended") {
127
+ this.cleanup?.();
128
+ }
82
129
  return result;
83
130
  }
84
131
  async resume(params) {
132
+ const p = this._resume(params).then((result) => {
133
+ if (result.status !== "suspended") {
134
+ this.closeStreamAction?.().catch(() => {
135
+ });
136
+ }
137
+ return result;
138
+ });
139
+ this.executionResults = p;
140
+ return p;
141
+ }
142
+ async _resume(params) {
85
143
  const steps = (Array.isArray(params.step) ? params.step : [params.step]).map(
86
144
  (step) => typeof step === "string" ? step : step?.id
87
145
  );
@@ -115,27 +173,62 @@ var InngestRun = class extends Run {
115
173
  }
116
174
  return result;
117
175
  }
118
- watch(cb) {
176
+ watch(cb, type = "watch") {
177
+ let active = true;
119
178
  const streamPromise = subscribe(
120
179
  {
121
180
  channel: `workflow:${this.workflowId}:${this.runId}`,
122
- topics: ["watch"],
181
+ topics: [type],
123
182
  app: this.inngest
124
183
  },
125
184
  (message) => {
126
- cb(message.data);
185
+ if (active) {
186
+ cb(message.data);
187
+ }
127
188
  }
128
189
  );
129
190
  return () => {
130
- streamPromise.then((stream) => {
131
- stream.cancel();
191
+ active = false;
192
+ streamPromise.then(async (stream) => {
193
+ return stream.cancel();
132
194
  }).catch((err) => {
133
195
  console.error(err);
134
196
  });
135
197
  };
136
198
  }
199
+ stream({ inputData, runtimeContext } = {}) {
200
+ const { readable, writable } = new TransformStream();
201
+ const writer = writable.getWriter();
202
+ const unwatch = this.watch(async (event) => {
203
+ try {
204
+ await writer.write(event);
205
+ } catch {
206
+ }
207
+ }, "watch-v2");
208
+ this.closeStreamAction = async () => {
209
+ unwatch();
210
+ try {
211
+ await writer.close();
212
+ } catch (err) {
213
+ console.error("Error closing stream:", err);
214
+ } finally {
215
+ writer.releaseLock();
216
+ }
217
+ };
218
+ this.executionResults = this.start({ inputData, runtimeContext }).then((result) => {
219
+ if (result.status !== "suspended") {
220
+ this.closeStreamAction?.().catch(() => {
221
+ });
222
+ }
223
+ return result;
224
+ });
225
+ return {
226
+ stream: readable,
227
+ getWorkflowState: () => this.executionResults
228
+ };
229
+ }
137
230
  };
138
- var InngestWorkflow = class _InngestWorkflow extends NewWorkflow {
231
+ var InngestWorkflow = class _InngestWorkflow extends Workflow {
139
232
  #mastra;
140
233
  inngest;
141
234
  function;
@@ -156,11 +249,32 @@ var InngestWorkflow = class _InngestWorkflow extends NewWorkflow {
156
249
  const storage = this.#mastra?.getStorage();
157
250
  if (!storage) {
158
251
  this.logger.debug("Cannot get workflow runs. Mastra engine is not initialized");
159
- return null;
252
+ return this.runs.get(runId) ? { ...this.runs.get(runId), workflowName: this.id } : null;
160
253
  }
161
254
  const run = await storage.getWorkflowRunById({ runId, workflowName: this.id });
162
255
  return run ?? (this.runs.get(runId) ? { ...this.runs.get(runId), workflowName: this.id } : null);
163
256
  }
257
+ async getWorkflowRunExecutionResult(runId) {
258
+ const storage = this.#mastra?.getStorage();
259
+ if (!storage) {
260
+ this.logger.debug("Cannot get workflow run execution result. Mastra storage is not initialized");
261
+ return null;
262
+ }
263
+ const run = await storage.getWorkflowRunById({ runId, workflowName: this.id });
264
+ if (!run?.snapshot) {
265
+ return null;
266
+ }
267
+ if (typeof run.snapshot === "string") {
268
+ return null;
269
+ }
270
+ return {
271
+ status: run.snapshot.status,
272
+ result: run.snapshot.result,
273
+ error: run.snapshot.error,
274
+ payload: run.snapshot.context?.input,
275
+ steps: run.snapshot.context
276
+ };
277
+ }
164
278
  __registerMastra(mastra) {
165
279
  this.#mastra = mastra;
166
280
  this.executionEngine.__registerMastra(mastra);
@@ -187,6 +301,7 @@ var InngestWorkflow = class _InngestWorkflow extends NewWorkflow {
187
301
  runId: runIdToUse,
188
302
  executionEngine: this.executionEngine,
189
303
  executionGraph: this.executionGraph,
304
+ serializedStepGraph: this.serializedStepGraph,
190
305
  mastra: this.#mastra,
191
306
  retryConfig: this.retryConfig,
192
307
  cleanup: () => this.runs.delete(runIdToUse)
@@ -196,13 +311,55 @@ var InngestWorkflow = class _InngestWorkflow extends NewWorkflow {
196
311
  this.runs.set(runIdToUse, run);
197
312
  return run;
198
313
  }
314
+ async createRunAsync(options) {
315
+ const runIdToUse = options?.runId || randomUUID();
316
+ const run = this.runs.get(runIdToUse) ?? new InngestRun(
317
+ {
318
+ workflowId: this.id,
319
+ runId: runIdToUse,
320
+ executionEngine: this.executionEngine,
321
+ executionGraph: this.executionGraph,
322
+ serializedStepGraph: this.serializedStepGraph,
323
+ mastra: this.#mastra,
324
+ retryConfig: this.retryConfig,
325
+ cleanup: () => this.runs.delete(runIdToUse)
326
+ },
327
+ this.inngest
328
+ );
329
+ this.runs.set(runIdToUse, run);
330
+ const workflowSnapshotInStorage = await this.getWorkflowRunExecutionResult(runIdToUse);
331
+ if (!workflowSnapshotInStorage) {
332
+ await this.mastra?.getStorage()?.persistWorkflowSnapshot({
333
+ workflowName: this.id,
334
+ runId: runIdToUse,
335
+ snapshot: {
336
+ runId: runIdToUse,
337
+ status: "pending",
338
+ value: {},
339
+ context: {},
340
+ activePaths: [],
341
+ serializedStepGraph: this.serializedStepGraph,
342
+ suspendedPaths: {},
343
+ result: void 0,
344
+ error: void 0,
345
+ // @ts-ignore
346
+ timestamp: Date.now()
347
+ }
348
+ });
349
+ }
350
+ return run;
351
+ }
199
352
  getFunction() {
200
353
  if (this.function) {
201
354
  return this.function;
202
355
  }
203
356
  this.function = this.inngest.createFunction(
204
- // @ts-ignore
205
- { id: `workflow.${this.id}`, retries: this.retryConfig?.attempts ?? 0 },
357
+ {
358
+ id: `workflow.${this.id}`,
359
+ // @ts-ignore
360
+ retries: this.retryConfig?.attempts ?? 0,
361
+ cancelOn: [{ event: `cancel.workflow.${this.id}` }]
362
+ },
206
363
  { event: `workflow.${this.id}` },
207
364
  async ({ event, step, attempt, publish }) => {
208
365
  let { inputData, runId, resume } = event.data;
@@ -219,12 +376,18 @@ var InngestWorkflow = class _InngestWorkflow extends NewWorkflow {
219
376
  try {
220
377
  await publish({
221
378
  channel: `workflow:${this.id}:${runId}`,
222
- topic: "watch",
379
+ topic: event2,
223
380
  data
224
381
  });
225
382
  } catch (err) {
226
383
  this.logger.error("Error emitting event: " + (err?.stack ?? err?.message ?? err));
227
384
  }
385
+ },
386
+ on: (_event, _callback) => {
387
+ },
388
+ off: (_event, _callback) => {
389
+ },
390
+ once: (_event, _callback) => {
228
391
  }
229
392
  };
230
393
  const engine = new InngestExecutionEngine(this.#mastra, step, attempt);
@@ -232,12 +395,14 @@ var InngestWorkflow = class _InngestWorkflow extends NewWorkflow {
232
395
  workflowId: this.id,
233
396
  runId,
234
397
  graph: this.executionGraph,
398
+ serializedStepGraph: this.serializedStepGraph,
235
399
  input: inputData,
236
400
  emitter,
237
401
  retryConfig: this.retryConfig,
238
402
  runtimeContext: new RuntimeContext(),
239
403
  // TODO
240
- resume
404
+ resume,
405
+ abortController: new AbortController()
241
406
  });
242
407
  return { result, runId };
243
408
  }
@@ -261,20 +426,110 @@ var InngestWorkflow = class _InngestWorkflow extends NewWorkflow {
261
426
  return [this.getFunction(), ...this.getNestedFunctions(this.executionGraph.steps)];
262
427
  }
263
428
  };
264
- function cloneWorkflow(workflow, opts) {
265
- const wf = new InngestWorkflow(
266
- {
267
- id: opts.id,
268
- inputSchema: workflow.inputSchema,
269
- outputSchema: workflow.outputSchema,
270
- steps: workflow.stepDefs,
271
- mastra: workflow.mastra
272
- },
273
- workflow.inngest
274
- );
275
- wf.setStepFlow(workflow.stepGraph);
276
- wf.commit();
277
- return wf;
429
+ function isAgent(params) {
430
+ return params?.component === "AGENT";
431
+ }
432
+ function isTool(params) {
433
+ return params instanceof Tool;
434
+ }
435
+ function createStep(params) {
436
+ if (isAgent(params)) {
437
+ return {
438
+ id: params.name,
439
+ // @ts-ignore
440
+ inputSchema: z.object({
441
+ prompt: z.string()
442
+ // resourceId: z.string().optional(),
443
+ // threadId: z.string().optional(),
444
+ }),
445
+ // @ts-ignore
446
+ outputSchema: z.object({
447
+ text: z.string()
448
+ }),
449
+ execute: async ({ inputData, [EMITTER_SYMBOL]: emitter, runtimeContext, abortSignal, abort }) => {
450
+ let streamPromise = {};
451
+ streamPromise.promise = new Promise((resolve, reject) => {
452
+ streamPromise.resolve = resolve;
453
+ streamPromise.reject = reject;
454
+ });
455
+ const toolData = {
456
+ name: params.name,
457
+ args: inputData
458
+ };
459
+ await emitter.emit("watch-v2", {
460
+ type: "tool-call-streaming-start",
461
+ ...toolData
462
+ });
463
+ const { fullStream } = await params.stream(inputData.prompt, {
464
+ // resourceId: inputData.resourceId,
465
+ // threadId: inputData.threadId,
466
+ runtimeContext,
467
+ onFinish: (result) => {
468
+ streamPromise.resolve(result.text);
469
+ },
470
+ abortSignal
471
+ });
472
+ if (abortSignal.aborted) {
473
+ return abort();
474
+ }
475
+ for await (const chunk of fullStream) {
476
+ switch (chunk.type) {
477
+ case "text-delta":
478
+ await emitter.emit("watch-v2", {
479
+ type: "tool-call-delta",
480
+ ...toolData,
481
+ argsTextDelta: chunk.textDelta
482
+ });
483
+ break;
484
+ case "step-start":
485
+ case "step-finish":
486
+ case "finish":
487
+ break;
488
+ case "tool-call":
489
+ case "tool-result":
490
+ case "tool-call-streaming-start":
491
+ case "tool-call-delta":
492
+ case "source":
493
+ case "file":
494
+ default:
495
+ await emitter.emit("watch-v2", chunk);
496
+ break;
497
+ }
498
+ }
499
+ return {
500
+ text: await streamPromise.promise
501
+ };
502
+ }
503
+ };
504
+ }
505
+ if (isTool(params)) {
506
+ if (!params.inputSchema || !params.outputSchema) {
507
+ throw new Error("Tool must have input and output schemas defined");
508
+ }
509
+ return {
510
+ // TODO: tool probably should have strong id type
511
+ // @ts-ignore
512
+ id: params.id,
513
+ inputSchema: params.inputSchema,
514
+ outputSchema: params.outputSchema,
515
+ execute: async ({ inputData, mastra, runtimeContext }) => {
516
+ return params.execute({
517
+ context: inputData,
518
+ mastra,
519
+ runtimeContext
520
+ });
521
+ }
522
+ };
523
+ }
524
+ return {
525
+ id: params.id,
526
+ description: params.description,
527
+ inputSchema: params.inputSchema,
528
+ outputSchema: params.outputSchema,
529
+ resumeSchema: params.resumeSchema,
530
+ suspendSchema: params.suspendSchema,
531
+ execute: params.execute
532
+ };
278
533
  }
279
534
  function init(inngest) {
280
535
  return {
@@ -282,8 +537,27 @@ function init(inngest) {
282
537
  return new InngestWorkflow(params, inngest);
283
538
  },
284
539
  createStep,
285
- cloneStep,
286
- cloneWorkflow
540
+ cloneStep(step, opts) {
541
+ return {
542
+ id: opts.id,
543
+ description: step.description,
544
+ inputSchema: step.inputSchema,
545
+ outputSchema: step.outputSchema,
546
+ execute: step.execute
547
+ };
548
+ },
549
+ cloneWorkflow(workflow, opts) {
550
+ const wf = new Workflow({
551
+ id: opts.id,
552
+ inputSchema: workflow.inputSchema,
553
+ outputSchema: workflow.outputSchema,
554
+ steps: workflow.stepDefs,
555
+ mastra: workflow.mastra
556
+ });
557
+ wf.setStepFlow(workflow.stepGraph);
558
+ wf.commit();
559
+ return wf;
560
+ }
287
561
  };
288
562
  }
289
563
  var InngestExecutionEngine = class extends DefaultExecutionEngine {
@@ -294,6 +568,18 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
294
568
  this.inngestStep = inngestStep;
295
569
  this.inngestAttempts = inngestAttempts;
296
570
  }
571
+ async execute(params) {
572
+ await params.emitter.emit("watch-v2", {
573
+ type: "start",
574
+ payload: { runId: params.runId }
575
+ });
576
+ const result = await super.execute(params);
577
+ await params.emitter.emit("watch-v2", {
578
+ type: "finish",
579
+ payload: { runId: params.runId }
580
+ });
581
+ return result;
582
+ }
297
583
  async fmtReturnValue(executionSpan, emitter, stepResults, lastOutput, error) {
298
584
  const base = {
299
585
  status: lastOutput.status,
@@ -360,6 +646,7 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
360
646
  resume,
361
647
  prevOutput,
362
648
  emitter,
649
+ abortController,
363
650
  runtimeContext
364
651
  }) {
365
652
  return super.executeStep({
@@ -371,9 +658,23 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
371
658
  resume,
372
659
  prevOutput,
373
660
  emitter,
661
+ abortController,
374
662
  runtimeContext
375
663
  });
376
664
  }
665
+ async executeSleep({ id, duration }) {
666
+ await this.inngestStep.sleep(id, duration);
667
+ }
668
+ async executeWaitForEvent({ event, timeout }) {
669
+ const eventData = await this.inngestStep.waitForEvent(`user-event-${event}`, {
670
+ event: `user-event-${event}`,
671
+ timeout: timeout ?? 5e3
672
+ });
673
+ if (eventData === null) {
674
+ throw "Timeout waiting for event";
675
+ }
676
+ return eventData?.data;
677
+ }
377
678
  async executeStep({
378
679
  step,
379
680
  stepResults,
@@ -381,11 +682,13 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
381
682
  resume,
382
683
  prevOutput,
383
684
  emitter,
685
+ abortController,
384
686
  runtimeContext
385
687
  }) {
386
- await this.inngestStep.run(
688
+ const startedAt = await this.inngestStep.run(
387
689
  `workflow.${executionContext.workflowId}.run.${executionContext.runId}.step.${step.id}.running_ev`,
388
690
  async () => {
691
+ const startedAt2 = Date.now();
389
692
  await emitter.emit("watch", {
390
693
  type: "watch",
391
694
  payload: {
@@ -407,6 +710,14 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
407
710
  },
408
711
  eventTimestamp: Date.now()
409
712
  });
713
+ await emitter.emit("watch-v2", {
714
+ type: "step-start",
715
+ payload: {
716
+ id: step.id,
717
+ status: "running"
718
+ }
719
+ });
720
+ return startedAt2;
410
721
  }
411
722
  );
412
723
  if (step instanceof InngestWorkflow) {
@@ -467,6 +778,15 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
467
778
  },
468
779
  eventTimestamp: Date.now()
469
780
  });
781
+ await emitter.emit("watch-v2", {
782
+ type: "step-result",
783
+ payload: {
784
+ id: step.id,
785
+ status: "failed",
786
+ error: result?.error,
787
+ payload: prevOutput
788
+ }
789
+ });
470
790
  return { executionContext, result: { status: "failed", error: result?.error } };
471
791
  } else if (result.status === "suspended") {
472
792
  const suspendedSteps = Object.entries(result.steps).filter(([_stepName, stepResult]) => {
@@ -493,6 +813,13 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
493
813
  },
494
814
  eventTimestamp: Date.now()
495
815
  });
816
+ await emitter.emit("watch-v2", {
817
+ type: "step-suspended",
818
+ payload: {
819
+ id: step.id,
820
+ status: "suspended"
821
+ }
822
+ });
496
823
  return {
497
824
  executionContext,
498
825
  result: {
@@ -543,6 +870,21 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
543
870
  },
544
871
  eventTimestamp: Date.now()
545
872
  });
873
+ await emitter.emit("watch-v2", {
874
+ type: "step-result",
875
+ payload: {
876
+ id: step.id,
877
+ status: "success",
878
+ output: result?.result
879
+ }
880
+ });
881
+ await emitter.emit("watch-v2", {
882
+ type: "step-finish",
883
+ payload: {
884
+ id: step.id,
885
+ metadata: {}
886
+ }
887
+ });
546
888
  return { executionContext, result: { status: "success", output: result?.result } };
547
889
  }
548
890
  );
@@ -552,8 +894,10 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
552
894
  const stepRes = await this.inngestStep.run(`workflow.${executionContext.workflowId}.step.${step.id}`, async () => {
553
895
  let execResults;
554
896
  let suspended;
897
+ let bailed;
555
898
  try {
556
899
  const result = await step.execute({
900
+ runId: executionContext.runId,
557
901
  mastra: this.mastra,
558
902
  runtimeContext,
559
903
  inputData: prevOutput,
@@ -570,20 +914,54 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
570
914
  executionContext.suspendedPaths[step.id] = executionContext.executionPath;
571
915
  suspended = { payload: suspendPayload };
572
916
  },
917
+ bail: (result2) => {
918
+ bailed = { payload: result2 };
919
+ },
573
920
  resume: {
574
921
  steps: resume?.steps?.slice(1) || [],
575
922
  resumePayload: resume?.resumePayload,
576
923
  // @ts-ignore
577
924
  runId: stepResults[step.id]?.payload?.__workflow_meta?.runId
578
925
  },
579
- emitter
926
+ [EMITTER_SYMBOL]: emitter,
927
+ engine: {
928
+ step: this.inngestStep
929
+ },
930
+ abortSignal: abortController.signal
580
931
  });
581
- execResults = { status: "success", output: result };
932
+ const endedAt = Date.now();
933
+ execResults = {
934
+ status: "success",
935
+ output: result,
936
+ startedAt,
937
+ endedAt,
938
+ payload: prevOutput,
939
+ resumedAt: resume?.steps[0] === step.id ? startedAt : void 0,
940
+ resumePayload: resume?.steps[0] === step.id ? resume?.resumePayload : void 0
941
+ };
582
942
  } catch (e) {
583
- execResults = { status: "failed", error: e instanceof Error ? e.message : String(e) };
943
+ execResults = {
944
+ status: "failed",
945
+ payload: prevOutput,
946
+ error: e instanceof Error ? e.message : String(e),
947
+ endedAt: Date.now(),
948
+ startedAt,
949
+ resumedAt: resume?.steps[0] === step.id ? startedAt : void 0,
950
+ resumePayload: resume?.steps[0] === step.id ? resume?.resumePayload : void 0
951
+ };
584
952
  }
585
953
  if (suspended) {
586
- execResults = { status: "suspended", payload: suspended.payload };
954
+ execResults = {
955
+ status: "suspended",
956
+ suspendedPayload: suspended.payload,
957
+ payload: prevOutput,
958
+ suspendedAt: Date.now(),
959
+ startedAt,
960
+ resumedAt: resume?.steps[0] === step.id ? startedAt : void 0,
961
+ resumePayload: resume?.steps[0] === step.id ? resume?.resumePayload : void 0
962
+ };
963
+ } else if (bailed) {
964
+ execResults = { status: "bailed", output: bailed.payload, payload: prevOutput, endedAt: Date.now(), startedAt };
587
965
  }
588
966
  if (execResults.status === "failed") {
589
967
  if (executionContext.retryConfig.attempts > 0 && this.inngestAttempts < executionContext.retryConfig.attempts) {
@@ -595,18 +973,41 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
595
973
  payload: {
596
974
  currentStep: {
597
975
  id: step.id,
598
- status: execResults.status,
599
- output: execResults.output
976
+ ...execResults
600
977
  },
601
978
  workflowState: {
602
979
  status: "running",
603
- steps: stepResults,
980
+ steps: { ...stepResults, [step.id]: execResults },
604
981
  result: null,
605
982
  error: null
606
983
  }
607
984
  },
608
985
  eventTimestamp: Date.now()
609
986
  });
987
+ if (execResults.status === "suspended") {
988
+ await emitter.emit("watch-v2", {
989
+ type: "step-suspended",
990
+ payload: {
991
+ id: step.id,
992
+ ...execResults
993
+ }
994
+ });
995
+ } else {
996
+ await emitter.emit("watch-v2", {
997
+ type: "step-result",
998
+ payload: {
999
+ id: step.id,
1000
+ ...execResults
1001
+ }
1002
+ });
1003
+ await emitter.emit("watch-v2", {
1004
+ type: "step-finish",
1005
+ payload: {
1006
+ id: step.id,
1007
+ metadata: {}
1008
+ }
1009
+ });
1010
+ }
610
1011
  return { result: execResults, executionContext, stepResults };
611
1012
  });
612
1013
  Object.assign(executionContext.suspendedPaths, stepRes.executionContext.suspendedPaths);
@@ -617,7 +1018,11 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
617
1018
  workflowId,
618
1019
  runId,
619
1020
  stepResults,
620
- executionContext
1021
+ executionContext,
1022
+ serializedStepGraph,
1023
+ workflowStatus,
1024
+ result,
1025
+ error
621
1026
  }) {
622
1027
  await this.inngestStep.run(
623
1028
  `workflow.${workflowId}.run.${runId}.path.${JSON.stringify(executionContext.executionPath)}.stepUpdate`,
@@ -631,6 +1036,10 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
631
1036
  context: stepResults,
632
1037
  activePaths: [],
633
1038
  suspendedPaths: executionContext.suspendedPaths,
1039
+ serializedStepGraph,
1040
+ status: workflowStatus,
1041
+ result,
1042
+ error,
634
1043
  // @ts-ignore
635
1044
  timestamp: Date.now()
636
1045
  }
@@ -645,9 +1054,11 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
645
1054
  prevOutput,
646
1055
  prevStep,
647
1056
  stepResults,
1057
+ serializedStepGraph,
648
1058
  resume,
649
1059
  executionContext,
650
1060
  emitter,
1061
+ abortController,
651
1062
  runtimeContext
652
1063
  }) {
653
1064
  let execResults;
@@ -656,8 +1067,10 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
656
1067
  (cond, index) => this.inngestStep.run(`workflow.${workflowId}.conditional.${index}`, async () => {
657
1068
  try {
658
1069
  const result = await cond({
1070
+ runId,
659
1071
  mastra: this.mastra,
660
1072
  runtimeContext,
1073
+ runCount: -1,
661
1074
  inputData: prevOutput,
662
1075
  getInitData: () => stepResults?.input,
663
1076
  getStepResult: (step) => {
@@ -673,7 +1086,16 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
673
1086
  // TODO: this function shouldn't have suspend probably?
674
1087
  suspend: async (_suspendPayload) => {
675
1088
  },
676
- emitter
1089
+ bail: () => {
1090
+ },
1091
+ abort: () => {
1092
+ abortController.abort();
1093
+ },
1094
+ [EMITTER_SYMBOL]: emitter,
1095
+ engine: {
1096
+ step: this.inngestStep
1097
+ },
1098
+ abortSignal: abortController.signal
677
1099
  });
678
1100
  return result ? index : null;
679
1101
  } catch (e) {
@@ -692,6 +1114,7 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
692
1114
  prevStep,
693
1115
  stepResults,
694
1116
  resume,
1117
+ serializedStepGraph,
695
1118
  executionContext: {
696
1119
  workflowId,
697
1120
  runId,
@@ -701,21 +1124,22 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
701
1124
  executionSpan: executionContext.executionSpan
702
1125
  },
703
1126
  emitter,
1127
+ abortController,
704
1128
  runtimeContext
705
1129
  })
706
1130
  )
707
1131
  );
708
- const hasFailed = results.find((result) => result.status === "failed");
709
- const hasSuspended = results.find((result) => result.status === "suspended");
1132
+ const hasFailed = results.find((result) => result.result.status === "failed");
1133
+ const hasSuspended = results.find((result) => result.result.status === "suspended");
710
1134
  if (hasFailed) {
711
- execResults = { status: "failed", error: hasFailed.error };
1135
+ execResults = { status: "failed", error: hasFailed.result.error };
712
1136
  } else if (hasSuspended) {
713
- execResults = { status: "suspended", payload: hasSuspended.payload };
1137
+ execResults = { status: "suspended", payload: hasSuspended.result.suspendPayload };
714
1138
  } else {
715
1139
  execResults = {
716
1140
  status: "success",
717
1141
  output: results.reduce((acc, result, index) => {
718
- if (result.status === "success") {
1142
+ if (result.result.status === "success") {
719
1143
  acc[stepsToRun[index].step.id] = result.output;
720
1144
  }
721
1145
  return acc;
@@ -726,4 +1150,4 @@ var InngestExecutionEngine = class extends DefaultExecutionEngine {
726
1150
  }
727
1151
  };
728
1152
 
729
- export { InngestExecutionEngine, InngestRun, InngestWorkflow, init, serve };
1153
+ export { InngestExecutionEngine, InngestRun, InngestWorkflow, createStep, init, serve };