@mastra/temporal 0.5.0 → 0.6.0-alpha.1

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/worker.cjs CHANGED
@@ -23,12 +23,12 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
23
23
  const require_utils = require("./utils-BVE1AkTt.cjs");
24
24
  let _mastra_core_workflows = require("@mastra/core/workflows");
25
25
  let _mastra_core_di = require("@mastra/core/di");
26
+ let _mastra_core_error = require("@mastra/core/error");
26
27
  let fs = require("fs");
27
28
  let fs_promises = require("fs/promises");
28
29
  let path = require("path");
29
30
  path = __toESM(path, 1);
30
31
  let url = require("url");
31
- let _mastra_core_error = require("@mastra/core/error");
32
32
  let _mastra_core_schema = require("@mastra/core/schema");
33
33
  let _temporalio_activity = require("@temporalio/activity");
34
34
  let _babel_generator = require("@babel/generator");
@@ -427,24 +427,55 @@ function hasLocalMastraBinding(ast) {
427
427
  }
428
428
  function createTemporalActivitiesHelperStatements(mastraImportPath, hasMastraBinding, requestContextClassName) {
429
429
  const helperSource = `
430
- function withRequestContext(params) {
430
+ function withRequestContext(params, args) {
431
431
  const { requestContext, initData, ...rest } = params;
432
+ let suspended;
432
433
  return {
433
434
  ...rest,
434
435
  requestContext: new ${requestContextClassName}(requestContext),
435
436
  getInitData: () => initData,
437
+ suspend: async (suspendPayload, options) => {
438
+ const parsedSuspendPayload = await parseWithSchema(args.suspendSchema, suspendPayload, 'Suspend payload');
439
+ suspended = {
440
+ __temporalSuspension: true,
441
+ suspendPayload: parsedSuspendPayload,
442
+ ...(options?.resumeLabel !== undefined && { resumeLabel: options.resumeLabel }),
443
+ };
444
+ },
445
+ __getTemporalSuspension: () => suspended,
436
446
  };
437
447
  }
438
448
 
449
+ async function parseWithSchema(schema, value, label) {
450
+ if (!schema) return value;
451
+ if (schema['~standard']?.validate) {
452
+ const result = await schema['~standard'].validate(value);
453
+ if ('issues' in result && result.issues?.length) {
454
+ throw new Error(label + ' validation failed: ' + result.issues.map(issue => issue.message).join(', '));
455
+ }
456
+ return result.value;
457
+ }
458
+ if (typeof schema.parseAsync === 'function') return schema.parseAsync(value);
459
+ if (typeof schema.parse === 'function') return schema.parse(value);
460
+ return value;
461
+ }
462
+
463
+ async function executeTemporalStep(args, context) {
464
+ const result = await args.execute(context);
465
+ return context.__getTemporalSuspension() ?? result;
466
+ }
467
+
439
468
  function createStep(args) {
440
469
  return {
441
470
  inputSchema: args.inputSchema,
442
471
  requestContextSchema: args.requestContextSchema,
472
+ suspendSchema: args.suspendSchema,
473
+ resumeSchema: args.resumeSchema,
443
474
  execute: async (params) => {
444
475
  ${mastraImportPath ? `
445
476
  const { mastra } = await import(${JSON.stringify(mastraImportPath)});
446
- return args.execute({ ...withRequestContext(params), mastra });
447
- ` : hasMastraBinding ? "return args.execute({ ...withRequestContext(params), mastra });" : "return args.execute(withRequestContext(params));"}
477
+ return executeTemporalStep(args, { ...withRequestContext(params, args), mastra });
478
+ ` : hasMastraBinding ? "return executeTemporalStep(args, { ...withRequestContext(params, args), mastra });" : "return executeTemporalStep(args, withRequestContext(params, args));"}
448
479
  },
449
480
  };
450
481
  }
@@ -1181,6 +1212,44 @@ function getActivityBindingsPath(outputDir) {
1181
1212
  return path.default.join(outputDir, ACTIVITY_BINDINGS_FILE_NAME);
1182
1213
  }
1183
1214
  /**
1215
+ * Temporal reduces a thrown error to its class name and message, so the step's own fields go in
1216
+ * the failure's `details` for start() to rebuild the result a local run returns.
1217
+ */
1218
+ function toStepFailureDetails(error) {
1219
+ const serialized = (0, _mastra_core_error.getErrorFromUnknown)(error, { serializeStack: false }).toJSON();
1220
+ let details;
1221
+ try {
1222
+ details = JSON.parse(JSON.stringify(serialized));
1223
+ } catch {
1224
+ details = {
1225
+ name: serialized.name,
1226
+ message: serialized.message
1227
+ };
1228
+ }
1229
+ if (error instanceof Error && error.name === "TripWire") {
1230
+ const { options, processorId } = error;
1231
+ return {
1232
+ error: details,
1233
+ tripwire: {
1234
+ reason: error.message,
1235
+ retry: options?.retry,
1236
+ metadata: options?.metadata,
1237
+ processorId
1238
+ }
1239
+ };
1240
+ }
1241
+ return { error: details };
1242
+ }
1243
+ /** Fails as Temporal's own conversion would (same type, message and retries), plus the details. */
1244
+ async function runStep(execute) {
1245
+ try {
1246
+ return await execute();
1247
+ } catch (error) {
1248
+ if (error instanceof _temporalio_activity.ApplicationFailure || error instanceof _temporalio_activity.CancelledFailure) throw error;
1249
+ throw _temporalio_activity.ApplicationFailure.fromError(error, { details: [toStepFailureDetails(error)] });
1250
+ }
1251
+ }
1252
+ /**
1184
1253
  * Activities queued by a Workflow built before `validateInputs` existed carry no flag and run
1185
1254
  * unchecked. A mismatch is non-retryable because a retry gets the same input.
1186
1255
  */
@@ -1203,7 +1272,8 @@ async function checkStepParams(stepId, { inputSchema, requestContextSchema }, {
1203
1272
  type: error instanceof _mastra_core_error.MastraError ? error.id : error.name,
1204
1273
  message: error.message,
1205
1274
  nonRetryable: true,
1206
- cause: error
1275
+ cause: error,
1276
+ details: [toStepFailureDetails(error)]
1207
1277
  });
1208
1278
  return {
1209
1279
  ...params,
@@ -1267,9 +1337,10 @@ var MastraPlugin = class {
1267
1337
  if (generatedActivities[binding.stepId]) continue;
1268
1338
  generatedActivities[binding.stepId] = async (params) => {
1269
1339
  const activity = (await this.#loadCompiledActivitiesModule(compiledActivitiesPath))[binding.exportName];
1270
- if (typeof activity === "function") return activity(params);
1340
+ if (typeof activity === "function") return runStep(() => activity(params));
1271
1341
  if (typeof activity?.execute !== "function") throw new Error(`Unable to load activity '${binding.exportName}' from ${compiledActivitiesPath}`);
1272
- return activity.execute(await checkStepParams(binding.stepId, activity, params));
1342
+ const checkedParams = await checkStepParams(binding.stepId, activity, params);
1343
+ return runStep(() => activity.execute(checkedParams));
1273
1344
  };
1274
1345
  }
1275
1346
  return generatedActivities;