@hatchet-dev/typescript-sdk 1.3.3 → 1.3.4

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.
@@ -9,6 +9,8 @@ declare enum ListenStrategy {
9
9
  }
10
10
  export interface Action extends AssignedAction {
11
11
  }
12
+ export type ActionKey = string;
13
+ export declare function createActionKey(action: Action): ActionKey;
12
14
  export declare class ActionListener {
13
15
  config: ClientConfig;
14
16
  client: PbDispatcherClient;
@@ -33,6 +33,8 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
33
33
  };
34
34
  Object.defineProperty(exports, "__esModule", { value: true });
35
35
  exports.ActionListener = void 0;
36
+ exports.createActionKey = createActionKey;
37
+ const dispatcher_1 = require("../../protoc/dispatcher");
36
38
  const nice_grpc_1 = require("nice-grpc");
37
39
  const sleep_1 = __importDefault(require("../../util/sleep"));
38
40
  const hatchet_error_1 = __importDefault(require("../../util/errors/hatchet-error"));
@@ -45,6 +47,20 @@ var ListenStrategy;
45
47
  ListenStrategy[ListenStrategy["LISTEN_STRATEGY_V1"] = 1] = "LISTEN_STRATEGY_V1";
46
48
  ListenStrategy[ListenStrategy["LISTEN_STRATEGY_V2"] = 2] = "LISTEN_STRATEGY_V2";
47
49
  })(ListenStrategy || (ListenStrategy = {}));
50
+ function createActionKey(action) {
51
+ switch (action.actionType) {
52
+ case dispatcher_1.ActionType.START_GET_GROUP_KEY:
53
+ return `${action.getGroupKeyRunId}/${action.retryCount}`;
54
+ case dispatcher_1.ActionType.CANCEL_STEP_RUN:
55
+ case dispatcher_1.ActionType.START_STEP_RUN:
56
+ case dispatcher_1.ActionType.UNRECOGNIZED:
57
+ return `${action.stepRunId}/${action.retryCount}`;
58
+ default:
59
+ // eslint-disable-next-line no-case-declarations
60
+ const exhaustivenessCheck = action.actionType;
61
+ throw new Error(`Unhandled action type: ${exhaustivenessCheck}`);
62
+ }
63
+ }
48
64
  class ActionListener {
49
65
  constructor(client, workerId, retryInterval = DEFAULT_ACTION_LISTENER_RETRY_INTERVAL, retryCount = DEFAULT_ACTION_LISTENER_RETRY_COUNT) {
50
66
  this.lastConnectionAttempt = 0;
@@ -1,5 +1,5 @@
1
1
  import { InternalHatchetClient } from '../hatchet-client';
2
- import { Action, ActionListener } from '../dispatcher/action-listener';
2
+ import { Action, ActionKey, ActionListener } from '../dispatcher/action-listener';
3
3
  import { StepActionEvent, StepActionEventType, GroupKeyActionEvent, GroupKeyActionEventType } from '../../protoc/dispatcher';
4
4
  import HatchetPromise from '../../util/hatchet-promise/hatchet-promise';
5
5
  import { Workflow } from '../../workflow';
@@ -25,8 +25,8 @@ export declare class V0Worker {
25
25
  action_registry: ActionRegistry;
26
26
  workflow_registry: Array<WorkflowDefinition | Workflow>;
27
27
  listener: ActionListener | undefined;
28
- futures: Record<Action['stepRunId'], HatchetPromise<any>>;
29
- contexts: Record<Action['stepRunId'], Context<any, any>>;
28
+ futures: Record<ActionKey, HatchetPromise<any>>;
29
+ contexts: Record<ActionKey, Context<any, any>>;
30
30
  maxRuns?: number;
31
31
  logger: Logger;
32
32
  registeredWorkflowPromises: Array<Promise<any>>;
@@ -21,6 +21,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
21
21
  Object.defineProperty(exports, "__esModule", { value: true });
22
22
  exports.V0Worker = void 0;
23
23
  const hatchet_error_1 = __importDefault(require("../../util/errors/hatchet-error"));
24
+ const action_listener_1 = require("../dispatcher/action-listener");
24
25
  const dispatcher_1 = require("../../protoc/dispatcher");
25
26
  const hatchet_promise_1 = __importDefault(require("../../util/hatchet-promise/hatchet-promise"));
26
27
  const workflows_1 = require("../../protoc/workflows");
@@ -336,7 +337,7 @@ class V0Worker {
336
337
  try {
337
338
  // Note: we always use a DurableContext since its a superset of the Context class
338
339
  const context = new step_1.DurableContext(action, this.client, this);
339
- this.contexts[action.stepRunId] = context;
340
+ this.contexts[(0, action_listener_1.createActionKey)(action)] = context;
340
341
  const step = this.action_registry[actionId];
341
342
  if (!step) {
342
343
  this.logger.error(`Registered actions: '${Object.keys(this.action_registry).join(', ')}'`);
@@ -367,8 +368,8 @@ class V0Worker {
367
368
  }
368
369
  finally {
369
370
  // delete the run from the futures
370
- delete this.futures[action.stepRunId];
371
- delete this.contexts[action.stepRunId];
371
+ delete this.futures[(0, action_listener_1.createActionKey)(action)];
372
+ delete this.contexts[(0, action_listener_1.createActionKey)(action)];
372
373
  }
373
374
  });
374
375
  const failure = (error) => __awaiter(this, void 0, void 0, function* () {
@@ -390,8 +391,8 @@ class V0Worker {
390
391
  }
391
392
  finally {
392
393
  // delete the run from the futures
393
- delete this.futures[action.stepRunId];
394
- delete this.contexts[action.stepRunId];
394
+ delete this.futures[(0, action_listener_1.createActionKey)(action)];
395
+ delete this.contexts[(0, action_listener_1.createActionKey)(action)];
395
396
  }
396
397
  });
397
398
  const future = new hatchet_promise_1.default((() => __awaiter(this, void 0, void 0, function* () {
@@ -405,7 +406,7 @@ class V0Worker {
405
406
  }
406
407
  yield success(result);
407
408
  }))());
408
- this.futures[action.stepRunId] = future;
409
+ this.futures[(0, action_listener_1.createActionKey)(action)] = future;
409
410
  // Send the action event to the dispatcher
410
411
  const event = this.getStepActionEvent(action, dispatcher_1.StepActionEventType.STEP_EVENT_TYPE_STARTED, false, undefined, action.retryCount);
411
412
  this.client.dispatcher.sendStepActionEvent(event).catch((e) => {
@@ -428,7 +429,7 @@ class V0Worker {
428
429
  const { actionId } = action;
429
430
  try {
430
431
  const context = new step_1.Context(action, this.client, this);
431
- const key = action.getGroupKeyRunId;
432
+ const key = (0, action_listener_1.createActionKey)(action);
432
433
  if (!key) {
433
434
  this.logger.error(`No group key run id provided for action ${actionId}`);
434
435
  return;
@@ -527,8 +528,8 @@ class V0Worker {
527
528
  const { stepRunId } = action;
528
529
  try {
529
530
  this.logger.info(`Cancelling step run ${action.stepRunId}`);
530
- const future = this.futures[stepRunId];
531
- const context = this.contexts[stepRunId];
531
+ const future = this.futures[(0, action_listener_1.createActionKey)(action)];
532
+ const context = this.contexts[(0, action_listener_1.createActionKey)(action)];
532
533
  if (context && context.controller) {
533
534
  context.controller.abort('Cancelled by worker');
534
535
  }
@@ -544,8 +545,8 @@ class V0Worker {
544
545
  this.logger.error('Could not cancel step run: ', e);
545
546
  }
546
547
  finally {
547
- delete this.futures[stepRunId];
548
- delete this.contexts[stepRunId];
548
+ delete this.futures[(0, action_listener_1.createActionKey)(action)];
549
+ delete this.contexts[(0, action_listener_1.createActionKey)(action)];
549
550
  }
550
551
  });
551
552
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hatchet-dev/typescript-sdk",
3
- "version": "1.3.3",
3
+ "version": "1.3.4",
4
4
  "description": "Background task orchestration & visibility for developers",
5
5
  "types": "dist/index.d.ts",
6
6
  "files": [
@@ -0,0 +1,2 @@
1
+ import HatchetClient from '../../../sdk';
2
+ export declare const hatchet: HatchetClient;
@@ -0,0 +1,8 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.hatchet = void 0;
7
+ const sdk_1 = __importDefault(require("../../../sdk"));
8
+ exports.hatchet = sdk_1.default.init();
@@ -0,0 +1,23 @@
1
+ export declare function processImageTask(req: {
2
+ body: {
3
+ imageUrl: string;
4
+ filters: string[];
5
+ };
6
+ }): Promise<{
7
+ success: boolean;
8
+ processedUrl: string;
9
+ }>;
10
+ type ImageProcessInput = {
11
+ imageUrl: string;
12
+ filters: string[];
13
+ };
14
+ type ImageProcessOutput = {
15
+ processedUrl: string;
16
+ metadata: {
17
+ size: number;
18
+ format: string;
19
+ appliedFilters: string[];
20
+ };
21
+ };
22
+ export declare const imageProcessor: import("../..").TaskWorkflowDeclaration<ImageProcessInput, ImageProcessOutput>;
23
+ export {};
@@ -0,0 +1,109 @@
1
+ "use strict";
2
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
+ return new (P || (P = Promise))(function (resolve, reject) {
5
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
9
+ });
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ exports.imageProcessor = void 0;
13
+ exports.processImageTask = processImageTask;
14
+ const hatchet_client_1 = require("./hatchet-client");
15
+ function processImage(imageUrl, filters) {
16
+ // Do some image processing
17
+ return Promise.resolve({ url: imageUrl, size: 100, format: 'png' });
18
+ }
19
+ // ❓ Before (Mergent)
20
+ function processImageTask(req) {
21
+ return __awaiter(this, void 0, void 0, function* () {
22
+ const { imageUrl, filters } = req.body;
23
+ try {
24
+ const result = yield processImage(imageUrl, filters);
25
+ return { success: true, processedUrl: result.url };
26
+ }
27
+ catch (error) {
28
+ console.error('Image processing failed:', error);
29
+ throw error;
30
+ }
31
+ });
32
+ }
33
+ exports.imageProcessor = hatchet_client_1.hatchet.task({
34
+ name: 'image-processor',
35
+ retries: 3,
36
+ executionTimeout: '10m',
37
+ fn: (_a) => __awaiter(void 0, [_a], void 0, function* ({ imageUrl, filters }) {
38
+ // Do some image processing
39
+ const result = yield processImage(imageUrl, filters);
40
+ if (!result.url)
41
+ throw new Error('Processing failed to generate URL');
42
+ return {
43
+ processedUrl: result.url,
44
+ metadata: {
45
+ size: result.size,
46
+ format: result.format,
47
+ appliedFilters: filters,
48
+ },
49
+ };
50
+ }),
51
+ });
52
+ // !!
53
+ function run() {
54
+ return __awaiter(this, void 0, void 0, function* () {
55
+ // ❓ Running a task (Mergent)
56
+ const options = {
57
+ method: 'POST',
58
+ headers: { Authorization: 'Bearer <token>', 'Content-Type': 'application/json' },
59
+ body: JSON.stringify({
60
+ name: '4cf95241-fa19-47ef-8a67-71e483747649',
61
+ queue: 'default',
62
+ request: {
63
+ url: 'https://example.com',
64
+ headers: { Authorization: 'fake-secret-token', 'Content-Type': 'application/json' },
65
+ body: 'Hello, world!',
66
+ },
67
+ }),
68
+ };
69
+ fetch('https://api.mergent.co/v2/tasks', options)
70
+ .then((response) => response.json())
71
+ .then((response) => console.log(response))
72
+ .catch((err) => console.error(err));
73
+ // !!
74
+ // ❓ Running a task (Hatchet)
75
+ const result = yield exports.imageProcessor.run({
76
+ imageUrl: 'https://example.com/image.png',
77
+ filters: ['blur'],
78
+ });
79
+ // you can await fully typed results
80
+ console.log(result);
81
+ // !!
82
+ });
83
+ }
84
+ function schedule() {
85
+ return __awaiter(this, void 0, void 0, function* () {
86
+ // ❓ Scheduling tasks (Mergent)
87
+ const options = {
88
+ // same options as before
89
+ body: JSON.stringify({
90
+ // same body as before
91
+ delay: '5m',
92
+ }),
93
+ };
94
+ // !!
95
+ // ❓ Scheduling tasks (Hatchet)
96
+ // Schedule the task to run at a specific time
97
+ const runAt = new Date(Date.now() + 1000 * 60 * 60 * 24);
98
+ exports.imageProcessor.schedule(runAt, {
99
+ imageUrl: 'https://example.com/image.png',
100
+ filters: ['blur'],
101
+ });
102
+ // Schedule the task to run every hour
103
+ exports.imageProcessor.cron('run-hourly', '0 * * * *', {
104
+ imageUrl: 'https://example.com/image.png',
105
+ filters: ['blur'],
106
+ });
107
+ // !!
108
+ });
109
+ }
package/version.d.ts CHANGED
@@ -1 +1 @@
1
- export declare const HATCHET_VERSION = "1.3.3";
1
+ export declare const HATCHET_VERSION = "1.3.4";
package/version.js CHANGED
@@ -1,4 +1,4 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.HATCHET_VERSION = void 0;
4
- exports.HATCHET_VERSION = '1.3.3';
4
+ exports.HATCHET_VERSION = '1.3.4';