arvo-event-handler 1.0.0 → 1.0.2

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/CHANGELOG.md CHANGED
@@ -3,6 +3,7 @@
3
3
  ## [0.0.1] - 2024-09-07
4
4
 
5
5
  - Finalised version 0.0.1 of the event handlers for Arvo
6
+
6
7
  ## [0.0.4] - 2024-09-09
7
8
 
8
9
  - Finalised Event Handler implementation
@@ -14,4 +15,7 @@
14
15
  ## [1.0.0] - 2024-09-10
15
16
 
16
17
  - First version rrelease
18
+ ## [1.0.2] - 2024-09-10
19
+
20
+ - Added ArvoEventRouter as a mechanism to group ArvoEventHandlers
17
21
 
package/README.md CHANGED
@@ -25,18 +25,61 @@ Whether you're building a small microservice or a large-scale distributed system
25
25
 
26
26
  # Arvo - Event Handler
27
27
 
28
+ This package contains the event handler primitive required to enable an Arvo Event Driven System. These are light weight classes and types which take care of event listening, contract bound type inference, distributed open telemetry and much more.
29
+
30
+ ## Documentation & Resources
31
+
32
+ | Source | Link |
33
+ | ------------ | ----------------------------------------------------------------- |
34
+ | Package | https://www.npmjs.com/package/arvo-event-handler?activeTab=readme |
35
+ | Github | https://github.com/SaadAhmad123/arvo-event-handler |
36
+ | Documenation | https://saadahmad123.github.io/arvo-event-handler/index.html |
37
+
28
38
  ## Installation
29
39
 
30
40
  You can install the core package via `npm` or `yarn`
31
41
 
32
42
  ```bash
33
- npm install arvo-event-handler
43
+ npm install arvo-event-handler arvo-core
34
44
  ```
35
45
 
36
46
  ```bash
37
- yarn add arvo-event-handler
47
+ yarn add arvo-event-handler arvo-core
48
+ ```
49
+
50
+ ## Components
51
+
52
+ There 2 main types of event handlers in Arvo event driven system
53
+
54
+ - [ArvoEventHandler](src/ArvoEventHandler/README.md) is designed to facilitate the handling of events as per an `ArvoContract` (see [arvo-core](https://saadahmad123.github.io/arvo-core/documents/ArvoContract.html)). It provides a robust and flexible way to create, manage, and execute event handlers for Arvo-based event driven systems.
55
+ - [ArvoEventRouter](src/ArvoEventRouter/README.md) is designed to route ArvoEvents to appropriate ArvoEventHandlers. It provides a centralized mechanism for managing and executing multiple event handlers based on event types.
56
+ - [MultiArvoEventHandler](src/MultiArvoEventHandler/README.md) is a flexible and powerful event handling class designed to process multiple event types across different ArvoContracts. This handler offers greater versatility compared to the more specialized `ArvoEventHandler`, as it's not bound to a specific contract or event type.
57
+
58
+
59
+ ## Getting Started
60
+
61
+ To start using Arvo Event Handlers in your project:
62
+
63
+ - Install the package as shown in the Installation section.
64
+ - Import the necessary components:
65
+
66
+ ```javascript
67
+ import {
68
+ createArvoEvent,
69
+ createArvoContract,
70
+ createArvoContractLibrary,
71
+ createArvoEventFactory,
72
+ } from 'arvo-core';
73
+
74
+ import {
75
+ createArvoEventHandler,
76
+ createMultiArvoEventHandler,
77
+ createArvoEventRouter,
78
+ } from 'arvo-event-handler'
38
79
  ```
39
80
 
81
+ - Begin defining your events, contracts, and handlers using the provided classes.
82
+
40
83
  ## License
41
84
 
42
85
  This package is available under the MIT License. For more details, refer to the [LICENSE.md](LICENSE.md) file in the project repository.
@@ -58,4 +101,4 @@ For a detailed list of changes and updates, please refer to the [document](CHANG
58
101
  [![Security Rating](https://sonarcloud.io/api/project_badges/measure?project=SaadAhmad123_arvo-event-handler&metric=security_rating)](https://sonarcloud.io/summary/new_code?id=SaadAhmad123_arvo-event-handler)
59
102
  [![Technical Debt](https://sonarcloud.io/api/project_badges/measure?project=SaadAhmad123_arvo-event-handler&metric=sqale_index)](https://sonarcloud.io/summary/new_code?id=SaadAhmad123_arvo-event-handler)
60
103
  [![Maintainability Rating](https://sonarcloud.io/api/project_badges/measure?project=SaadAhmad123_arvo-event-handler&metric=sqale_rating)](https://sonarcloud.io/summary/new_code?id=SaadAhmad123_arvo-event-handler)
61
- [![Vulnerabilities](https://sonarcloud.io/api/project_badges/measure?project=SaadAhmad123_arvo-event-handler&metric=vulnerabilities)](https://sonarcloud.io/summary/new_code?id=SaadAhmad123_arvo-event-handler)
104
+ [![Vulnerabilities](https://sonarcloud.io/api/project_badges/measure?project=SaadAhmad123_arvo-event-handler&metric=vulnerabilities)](https://sonarcloud.io/summary/new_code?id=SaadAhmad123_arvo-event-handler)
@@ -22,7 +22,7 @@ export default class ArvoEventHandler<TContract extends ArvoContract> {
22
22
  * @remarks
23
23
  * For all the events which are emitted by the handler, this is
24
24
  * the source field value of them all.
25
- */
25
+ */
26
26
  readonly source: string;
27
27
  readonly openInferenceSpanKind: OpenInferenceSpanKind;
28
28
  readonly arvoExecutionSpanKind: ArvoExecutionSpanKind;
@@ -70,6 +70,7 @@ export default class ArvoEventHandler<TContract extends ArvoContract> {
70
70
  * @throws All error throw during the execution are returned as a system error event
71
71
  *
72
72
  * **Routing**
73
+ *
73
74
  * The routing of the resulting events is determined as follows:
74
75
  * - The `to` field of the output event is set in this priority:
75
76
  * 1. The `to` field provided by the handler result
@@ -78,6 +79,7 @@ export default class ArvoEventHandler<TContract extends ArvoContract> {
78
79
  * - For system error events, the `to` field is always set to the `source` of the input event.
79
80
  *
80
81
  * **Telemetry**
82
+ *
81
83
  * - Creates a new span for each execution as per the traceparent and tracestate field
82
84
  * of the event. If those are not present, then a brand new span is created and distributed
83
85
  * tracing is disabled
@@ -102,9 +102,12 @@ var ArvoEventHandler = /** @class */ (function () {
102
102
  }
103
103
  }
104
104
  this.source = param.source || this.contract.accepts.type;
105
- this.arvoExecutionSpanKind = ((_a = param.spanKind) === null || _a === void 0 ? void 0 : _a.arvoExecution) || this.arvoExecutionSpanKind;
106
- this.openInferenceSpanKind = ((_b = param.spanKind) === null || _b === void 0 ? void 0 : _b.openInference) || this.openInferenceSpanKind;
107
- this.openTelemetrySpanKind = ((_c = param.spanKind) === null || _c === void 0 ? void 0 : _c.openTelemetry) || this.openTelemetrySpanKind;
105
+ this.arvoExecutionSpanKind =
106
+ ((_a = param.spanKind) === null || _a === void 0 ? void 0 : _a.arvoExecution) || this.arvoExecutionSpanKind;
107
+ this.openInferenceSpanKind =
108
+ ((_b = param.spanKind) === null || _b === void 0 ? void 0 : _b.openInference) || this.openInferenceSpanKind;
109
+ this.openTelemetrySpanKind =
110
+ ((_c = param.spanKind) === null || _c === void 0 ? void 0 : _c.openTelemetry) || this.openTelemetrySpanKind;
108
111
  }
109
112
  /**
110
113
  * Executes the event handler for a given event.
@@ -136,6 +139,7 @@ var ArvoEventHandler = /** @class */ (function () {
136
139
  * @throws All error throw during the execution are returned as a system error event
137
140
  *
138
141
  * **Routing**
142
+ *
139
143
  * The routing of the resulting events is determined as follows:
140
144
  * - The `to` field of the output event is set in this priority:
141
145
  * 1. The `to` field provided by the handler result
@@ -144,6 +148,7 @@ var ArvoEventHandler = /** @class */ (function () {
144
148
  * - For system error events, the `to` field is always set to the `source` of the input event.
145
149
  *
146
150
  * **Telemetry**
151
+ *
147
152
  * - Creates a new span for each execution as per the traceparent and tracestate field
148
153
  * of the event. If those are not present, then a brand new span is created and distributed
149
154
  * tracing is disabled
@@ -165,7 +170,7 @@ var ArvoEventHandler = /** @class */ (function () {
165
170
  attributes: (_a = {},
166
171
  _a[arvo_core_1.OpenInference.ATTR_SPAN_KIND] = this.openInferenceSpanKind,
167
172
  _a[arvo_core_1.ArvoExecution.ATTR_SPAN_KIND] = this.arvoExecutionSpanKind,
168
- _a)
173
+ _a),
169
174
  };
170
175
  if (event.traceparent) {
171
176
  inheritedContext = (0, OpenTelemetry_1.extractContext)(event.traceparent, event.tracestate);
@@ -194,7 +199,10 @@ var ArvoEventHandler = /** @class */ (function () {
194
199
  if (inputEventValidation.error) {
195
200
  throw new Error("Invalid event payload: ".concat(inputEventValidation.error));
196
201
  }
197
- return [4 /*yield*/, this._handler({ event: event, source: this.source })];
202
+ return [4 /*yield*/, this._handler({
203
+ event: event,
204
+ source: this.source,
205
+ })];
198
206
  case 2:
199
207
  _handleOutput = _a.sent();
200
208
  if (!_handleOutput)
@@ -210,9 +218,9 @@ var ArvoEventHandler = /** @class */ (function () {
210
218
  var __extensions = output.__extensions, handlerResult = __rest(output, ["__extensions"]);
211
219
  var result = eventFactory.emits(__assign(__assign({}, handlerResult), { traceparent: otelSpanHeaders.traceparent || undefined, tracestate: otelSpanHeaders.tracestate || undefined, source: _this.source, subject: event.subject,
212
220
  // The user should be able to override the `to` field
213
- // If that is not present then the 'redirectto' field
221
+ // If that is not present then the 'redirectto' field
214
222
  // is referred to. Then, after all else, 'source' field
215
- // is used as a form of reply.
223
+ // is used as a form of reply.
216
224
  to: (0, utils_1.coalesceOrDefault)([handlerResult.to, event.redirectto], event.source), executionunits: (0, utils_1.coalesce)(handlerResult.executionunits, _this.executionunits) }), __extensions);
217
225
  Object.entries(result.otelAttributes).forEach(function (_a) {
218
226
  var key = _a[0], value = _a[1];
@@ -230,7 +238,7 @@ var ArvoEventHandler = /** @class */ (function () {
230
238
  result = eventFactory.systemError({
231
239
  source: this.source,
232
240
  subject: event.subject,
233
- // The system error must always got back to
241
+ // The system error must always got back to
234
242
  // the source
235
243
  to: event.source,
236
244
  error: error_1,
@@ -274,7 +282,7 @@ var ArvoEventHandler = /** @class */ (function () {
274
282
  get: function () {
275
283
  return {
276
284
  type: "sys.".concat(this.contract.accepts.type, ".error"),
277
- schema: arvo_core_1.ArvoErrorSchema
285
+ schema: arvo_core_1.ArvoErrorSchema,
278
286
  };
279
287
  },
280
288
  enumerable: false,
@@ -0,0 +1,36 @@
1
+ import { ArvoEventRouter } from '.';
2
+ import { IArvoEventRouter } from './types';
3
+ /**
4
+ * Creates and returns a new instance of ArvoEventRouter.
5
+ *
6
+ * @param {IArvoEventRouter} param - Configuration object for the ArvoEventRouter.
7
+ * @returns {ArvoEventRouter} A new instance of ArvoEventRouter.
8
+ *
9
+ * @throws {Error} If there are duplicate handlers for the same event type.
10
+ * @throws {Error} If the provided source is an invalid string.
11
+ *
12
+ * @example
13
+ * const router = createArvoEventRouter({
14
+ * source: 'my-router',
15
+ * handlers: [handler1, handler2],
16
+ * executionunits: 10
17
+ * });
18
+ *
19
+ * @remarks
20
+ * This function is a factory method that simplifies the creation of an ArvoEventRouter instance.
21
+ * It encapsulates the instantiation process, allowing for a more concise and readable way to create routers.
22
+ *
23
+ * The `IArvoEventRouter` parameter should include:
24
+ * - `source`: (optional) A string identifying the source of the router. Used to match the `event.to` field.
25
+ * - `handlers`: An array of ArvoEventHandler instances that the router will use to process events.
26
+ * - `executionunits`: A number representing the default execution cost of the function.
27
+ *
28
+ * The created ArvoEventRouter will:
29
+ * - Validate the source string if provided.
30
+ * - Check for and prevent duplicate handlers for the same event type.
31
+ * - Set up internal data structures for efficient event routing.
32
+ *
33
+ * @see {@link ArvoEventRouter} for more details on the router's functionality.
34
+ * @see {@link IArvoEventRouter} for the structure of the configuration object.
35
+ */
36
+ export declare const createArvoEventRouter: (param: IArvoEventRouter) => ArvoEventRouter;
@@ -0,0 +1,41 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createArvoEventRouter = void 0;
4
+ var _1 = require(".");
5
+ /**
6
+ * Creates and returns a new instance of ArvoEventRouter.
7
+ *
8
+ * @param {IArvoEventRouter} param - Configuration object for the ArvoEventRouter.
9
+ * @returns {ArvoEventRouter} A new instance of ArvoEventRouter.
10
+ *
11
+ * @throws {Error} If there are duplicate handlers for the same event type.
12
+ * @throws {Error} If the provided source is an invalid string.
13
+ *
14
+ * @example
15
+ * const router = createArvoEventRouter({
16
+ * source: 'my-router',
17
+ * handlers: [handler1, handler2],
18
+ * executionunits: 10
19
+ * });
20
+ *
21
+ * @remarks
22
+ * This function is a factory method that simplifies the creation of an ArvoEventRouter instance.
23
+ * It encapsulates the instantiation process, allowing for a more concise and readable way to create routers.
24
+ *
25
+ * The `IArvoEventRouter` parameter should include:
26
+ * - `source`: (optional) A string identifying the source of the router. Used to match the `event.to` field.
27
+ * - `handlers`: An array of ArvoEventHandler instances that the router will use to process events.
28
+ * - `executionunits`: A number representing the default execution cost of the function.
29
+ *
30
+ * The created ArvoEventRouter will:
31
+ * - Validate the source string if provided.
32
+ * - Check for and prevent duplicate handlers for the same event type.
33
+ * - Set up internal data structures for efficient event routing.
34
+ *
35
+ * @see {@link ArvoEventRouter} for more details on the router's functionality.
36
+ * @see {@link IArvoEventRouter} for the structure of the configuration object.
37
+ */
38
+ var createArvoEventRouter = function (param) {
39
+ return new _1.ArvoEventRouter(param);
40
+ };
41
+ exports.createArvoEventRouter = createArvoEventRouter;
@@ -0,0 +1,85 @@
1
+ import { ArvoContract, ArvoEvent, ArvoExecutionSpanKind, OpenInferenceSpanKind } from 'arvo-core';
2
+ import ArvoEventHandler from '../ArvoEventHandler';
3
+ import { IArvoEventRouter } from './types';
4
+ import { SpanKind } from '@opentelemetry/api';
5
+ /**
6
+ * ArvoEventRouter class handles routing of ArvoEvents to appropriate event handlers.
7
+ */
8
+ export declare class ArvoEventRouter {
9
+ /**
10
+ * The source name of the router. The router attempts
11
+ * to match the `event.to` field with this value
12
+ * @property {string} [source]
13
+ */
14
+ readonly source: string | null;
15
+ /**
16
+ * A list of all available event handlers to be used by the router.
17
+ * @property {ArvoEventHandler<ArvoContract>[]} handlers
18
+ */
19
+ readonly handlers: ArvoEventHandler<ArvoContract>[];
20
+ /**
21
+ * The default execution cost of the function.
22
+ * This can represent a dollar value or some other number with a rate card.
23
+ */
24
+ readonly executionunits: number;
25
+ /**
26
+ * A map of all the available event handlers
27
+ */
28
+ readonly handlersMap: Record<string, ArvoEventHandler<ArvoContract>>;
29
+ readonly openInferenceSpanKind: OpenInferenceSpanKind;
30
+ readonly arvoExecutionSpanKind: ArvoExecutionSpanKind;
31
+ readonly openTelemetrySpanKind: SpanKind;
32
+ /**
33
+ * Creates an instance of ArvoEventRouter.
34
+ * @param {IArvoEventRouter} param - The parameters for initializing the router
35
+ * @throws {Error} If there are duplicate handlers for the same event type or the
36
+ * source in an invalid string
37
+ */
38
+ constructor(param: IArvoEventRouter);
39
+ /**
40
+ * Executes the routing process for a given ArvoEvent.
41
+ *
42
+ * @param event - The ArvoEvent to be processed and routed.
43
+ * @returns A Promise that resolves to an array of ArvoEvents.
44
+ *
45
+ * @remarks
46
+ * This function performs the following steps:
47
+ * 1. Initializes OpenTelemetry span for tracing and monitoring.
48
+ * 2. Validates the event's destination ('to' field) against the router's source.
49
+ * 3. Finds the appropriate handler for the event based on its type.
50
+ * 4. Executes the handler and processes the results.
51
+ * 5. Handles any errors that occur during the process.
52
+ *
53
+ * @throws Error event if the event's 'to' field doesn't match the router's source.
54
+ * @throws Error event if no valid handler is found for the event type.
55
+ *
56
+ * **Telemetry**
57
+ *
58
+ * - Creates an OpenTelemetry span for the entire execution process.
59
+ * - Sets span attributes for OpenInference and ArvoExecution.
60
+ * - Propagates trace context from the input event if available.
61
+ * - Records any errors in the span and sets the span status accordingly.
62
+ * - Adds event attributes to the span for both input and output events.
63
+ *
64
+ * **Routing**
65
+ *
66
+ * The routing process involves:
67
+ * 1. Matching the event's 'to' field with the router's source (if specified).
68
+ * 2. Finding a handler that accepts the event's type.
69
+ * 3. Executing the matched handler with the event.
70
+ * 4. Processing the handler's results and creating new events.
71
+ *
72
+ * **Error Handling**
73
+ *
74
+ * If an error occurs during execution:
75
+ * 1. The error is recorded in the OpenTelemetry span.
76
+ * 2. A new error event is created and returned.
77
+ * 3. The error event is sent back to the original event's source.
78
+ *
79
+ * **Performance**
80
+ *
81
+ * - Execution units are tracked for both successful executions and errors.
82
+ * - The router's default execution units are used for error events.
83
+ */
84
+ execute(event: ArvoEvent): Promise<ArvoEvent[]>;
85
+ }
@@ -0,0 +1,242 @@
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
+ var __generator = (this && this.__generator) || function (thisArg, body) {
12
+ var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;
13
+ return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g;
14
+ function verb(n) { return function (v) { return step([n, v]); }; }
15
+ function step(op) {
16
+ if (f) throw new TypeError("Generator is already executing.");
17
+ while (g && (g = 0, op[0] && (_ = 0)), _) try {
18
+ if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
19
+ if (y = 0, t) op = [op[0] & 2, t.value];
20
+ switch (op[0]) {
21
+ case 0: case 1: t = op; break;
22
+ case 4: _.label++; return { value: op[1], done: false };
23
+ case 5: _.label++; y = op[1]; op = [0]; continue;
24
+ case 7: op = _.ops.pop(); _.trys.pop(); continue;
25
+ default:
26
+ if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }
27
+ if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }
28
+ if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }
29
+ if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }
30
+ if (t[2]) _.ops.pop();
31
+ _.trys.pop(); continue;
32
+ }
33
+ op = body.call(thisArg, _);
34
+ } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }
35
+ if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };
36
+ }
37
+ };
38
+ Object.defineProperty(exports, "__esModule", { value: true });
39
+ exports.ArvoEventRouter = void 0;
40
+ var arvo_core_1 = require("arvo-core");
41
+ var utils_1 = require("../utils");
42
+ var api_1 = require("@opentelemetry/api");
43
+ var OpenTelemetry_1 = require("../OpenTelemetry");
44
+ var utils_2 = require("./utils");
45
+ var schema_1 = require("arvo-core/dist/ArvoEvent/schema");
46
+ /**
47
+ * ArvoEventRouter class handles routing of ArvoEvents to appropriate event handlers.
48
+ */
49
+ var ArvoEventRouter = /** @class */ (function () {
50
+ /**
51
+ * Creates an instance of ArvoEventRouter.
52
+ * @param {IArvoEventRouter} param - The parameters for initializing the router
53
+ * @throws {Error} If there are duplicate handlers for the same event type or the
54
+ * source in an invalid string
55
+ */
56
+ function ArvoEventRouter(param) {
57
+ /**
58
+ * A map of all the available event handlers
59
+ */
60
+ this.handlersMap = {};
61
+ this.openInferenceSpanKind = arvo_core_1.OpenInferenceSpanKind.CHAIN;
62
+ this.arvoExecutionSpanKind = arvo_core_1.ArvoExecutionSpanKind.EVENT_HANDLER;
63
+ this.openTelemetrySpanKind = api_1.SpanKind.INTERNAL;
64
+ this.handlers = param.handlers;
65
+ if (param.source) {
66
+ var error = schema_1.CloudEventContextSchema.pick({
67
+ source: true,
68
+ }).safeParse({ source: param.source }).error;
69
+ if (error) {
70
+ throw new Error("The provided 'source' is not a valid string. Error: ".concat(error.message));
71
+ }
72
+ }
73
+ this.source = (0, utils_1.isNullOrUndefined)(param.source) ? null : param.source;
74
+ this.executionunits = param.executionunits;
75
+ for (var _i = 0, _a = this.handlers; _i < _a.length; _i++) {
76
+ var handler = _a[_i];
77
+ if (this.handlersMap[handler.contract.accepts.type]) {
78
+ var existingHandler = this.handlersMap[handler.contract.accepts.type];
79
+ throw new Error((0, arvo_core_1.cleanString)("\n Duplicate handlers for event.type=".concat(handler.contract.accepts.type, " found. There are same 'contract.accept.types' in \n contracts 'uri=").concat(existingHandler.contract.uri, "' and 'uri=").concat(handler.contract.uri, "'. This router does not support handlers\n with the same 'contract.accept.type'.\n ")));
80
+ }
81
+ this.handlersMap[handler.contract.accepts.type] = handler;
82
+ }
83
+ Object.freeze(this.handlers);
84
+ Object.freeze(this.handlersMap);
85
+ }
86
+ /**
87
+ * Executes the routing process for a given ArvoEvent.
88
+ *
89
+ * @param event - The ArvoEvent to be processed and routed.
90
+ * @returns A Promise that resolves to an array of ArvoEvents.
91
+ *
92
+ * @remarks
93
+ * This function performs the following steps:
94
+ * 1. Initializes OpenTelemetry span for tracing and monitoring.
95
+ * 2. Validates the event's destination ('to' field) against the router's source.
96
+ * 3. Finds the appropriate handler for the event based on its type.
97
+ * 4. Executes the handler and processes the results.
98
+ * 5. Handles any errors that occur during the process.
99
+ *
100
+ * @throws Error event if the event's 'to' field doesn't match the router's source.
101
+ * @throws Error event if no valid handler is found for the event type.
102
+ *
103
+ * **Telemetry**
104
+ *
105
+ * - Creates an OpenTelemetry span for the entire execution process.
106
+ * - Sets span attributes for OpenInference and ArvoExecution.
107
+ * - Propagates trace context from the input event if available.
108
+ * - Records any errors in the span and sets the span status accordingly.
109
+ * - Adds event attributes to the span for both input and output events.
110
+ *
111
+ * **Routing**
112
+ *
113
+ * The routing process involves:
114
+ * 1. Matching the event's 'to' field with the router's source (if specified).
115
+ * 2. Finding a handler that accepts the event's type.
116
+ * 3. Executing the matched handler with the event.
117
+ * 4. Processing the handler's results and creating new events.
118
+ *
119
+ * **Error Handling**
120
+ *
121
+ * If an error occurs during execution:
122
+ * 1. The error is recorded in the OpenTelemetry span.
123
+ * 2. A new error event is created and returned.
124
+ * 3. The error event is sent back to the original event's source.
125
+ *
126
+ * **Performance**
127
+ *
128
+ * - Execution units are tracked for both successful executions and errors.
129
+ * - The router's default execution units are used for error events.
130
+ */
131
+ ArvoEventRouter.prototype.execute = function (event) {
132
+ return __awaiter(this, void 0, void 0, function () {
133
+ var spanName, spanOptions, span, inheritedContext;
134
+ var _a;
135
+ var _this = this;
136
+ var _b;
137
+ return __generator(this, function (_c) {
138
+ switch (_c.label) {
139
+ case 0:
140
+ spanName = "ArvoEventRouter.source<".concat((_b = this.source) !== null && _b !== void 0 ? _b : 'arvo.event.router', ">.execute<").concat(event.type, ">");
141
+ spanOptions = {
142
+ kind: this.openTelemetrySpanKind,
143
+ attributes: (_a = {},
144
+ _a[arvo_core_1.OpenInference.ATTR_SPAN_KIND] = this.openInferenceSpanKind,
145
+ _a[arvo_core_1.ArvoExecution.ATTR_SPAN_KIND] = this.arvoExecutionSpanKind,
146
+ _a),
147
+ };
148
+ if (event.traceparent) {
149
+ inheritedContext = (0, OpenTelemetry_1.extractContext)(event.traceparent, event.tracestate);
150
+ span = OpenTelemetry_1.ArvoEventHandlerTracer.startSpan(spanName, spanOptions, inheritedContext);
151
+ }
152
+ else {
153
+ span = OpenTelemetry_1.ArvoEventHandlerTracer.startSpan(spanName, spanOptions);
154
+ }
155
+ return [4 /*yield*/, api_1.context.with(api_1.trace.setSpan(api_1.context.active(), span), function () { return __awaiter(_this, void 0, void 0, function () {
156
+ var otelSpanHeaders, newEvent, results, error_1, result;
157
+ var _this = this;
158
+ var _a, _b;
159
+ return __generator(this, function (_c) {
160
+ switch (_c.label) {
161
+ case 0:
162
+ otelSpanHeaders = (0, arvo_core_1.currentOpenTelemetryHeaders)();
163
+ newEvent = (0, utils_2.deleteOtelHeaders)(event);
164
+ _c.label = 1;
165
+ case 1:
166
+ _c.trys.push([1, 3, 4, 5]);
167
+ span.setStatus({ code: api_1.SpanStatusCode.OK });
168
+ if (!(0, utils_1.isNullOrUndefined)(this.source) && newEvent.to !== this.source) {
169
+ throw new Error((0, arvo_core_1.cleanString)("\n Invalid event. The 'event.to' is ".concat(newEvent.to, " while this handler \n listens to only 'event.to' equal to ").concat(this.source, ". If this is a mistake,\n please update the 'source' field of the handler\n ")));
170
+ }
171
+ if (!this.handlersMap[newEvent.type]) {
172
+ throw new Error((0, arvo_core_1.cleanString)("\n Invalid event (type=".concat(newEvent.type, "). No valid handler \n <handler[*].contract.accepts.type> found in the router.\n ")));
173
+ }
174
+ return [4 /*yield*/, this.handlersMap[newEvent.type].execute(newEvent)];
175
+ case 2:
176
+ results = _c.sent();
177
+ return [2 /*return*/, results.map(function (event) {
178
+ var _a;
179
+ return new arvo_core_1.ArvoEvent({
180
+ id: event.id,
181
+ time: event.time,
182
+ source: (0, utils_1.getValueOrDefault)(_this.source, event.source),
183
+ specversion: '1.0',
184
+ type: event.type,
185
+ subject: event.subject,
186
+ datacontenttype: event.datacontenttype,
187
+ dataschema: event.dataschema,
188
+ to: event.to,
189
+ accesscontrol: event.accesscontrol,
190
+ redirectto: event.redirectto,
191
+ executionunits: ((_a = event.executionunits) !== null && _a !== void 0 ? _a : 0) + _this.executionunits,
192
+ traceparent: otelSpanHeaders.traceparent,
193
+ tracestate: otelSpanHeaders.tracestate,
194
+ }, event.data, event.cloudevent.extensions);
195
+ })];
196
+ case 3:
197
+ error_1 = _c.sent();
198
+ (0, arvo_core_1.exceptionToSpan)(error_1);
199
+ span.setStatus({
200
+ code: api_1.SpanStatusCode.ERROR,
201
+ message: error_1.message,
202
+ });
203
+ Object.entries(event.otelAttributes).forEach(function (_a) {
204
+ var key = _a[0], value = _a[1];
205
+ return span.setAttribute("to_process.0.".concat(key), value);
206
+ });
207
+ result = (0, arvo_core_1.createArvoEvent)({
208
+ type: "sys.arvo.event.router.error",
209
+ source: this.source || "arvo.event.router",
210
+ subject: event.subject,
211
+ // The system error must always got back to
212
+ // the source
213
+ to: event.source,
214
+ executionunits: this.executionunits,
215
+ traceparent: (_a = otelSpanHeaders.traceparent) !== null && _a !== void 0 ? _a : undefined,
216
+ tracestate: (_b = otelSpanHeaders.tracestate) !== null && _b !== void 0 ? _b : undefined,
217
+ data: {
218
+ errorName: error_1.name,
219
+ errorMessage: error_1.message,
220
+ errorStack: error_1.stack || null,
221
+ },
222
+ });
223
+ Object.entries(result.otelAttributes).forEach(function (_a) {
224
+ var key = _a[0], value = _a[1];
225
+ return span.setAttribute("to_emit.0.".concat(key), value);
226
+ });
227
+ return [2 /*return*/, [result]];
228
+ case 4:
229
+ span.end();
230
+ return [7 /*endfinally*/];
231
+ case 5: return [2 /*return*/];
232
+ }
233
+ });
234
+ }); })];
235
+ case 1: return [2 /*return*/, _c.sent()];
236
+ }
237
+ });
238
+ });
239
+ };
240
+ return ArvoEventRouter;
241
+ }());
242
+ exports.ArvoEventRouter = ArvoEventRouter;
@@ -0,0 +1,56 @@
1
+ import { ArvoContract, ArvoExecutionSpanKind, OpenInferenceSpanKind } from 'arvo-core';
2
+ import ArvoEventHandler from '../ArvoEventHandler';
3
+ import { SpanKind } from '@opentelemetry/api';
4
+ /**
5
+ * Interface for defining an Arvo Event Router.
6
+ *
7
+ * @interface IArvoEventRouter
8
+ */
9
+ export interface IArvoEventRouter {
10
+ /**
11
+ * Defines the source name of the router.
12
+ *
13
+ * @property {string} [source]
14
+ *
15
+ * @remarks
16
+ * If this field is defined:
17
+ * - The router will only listen to events with a `to` field matching this `source`.
18
+ * - If an event's `to` field doesn't match, a system error event will be emitted.
19
+ * - For all emitted events, the `source` field will be overridden by this value.
20
+ *
21
+ * If this field is not defined:
22
+ * - The router will listen to all events.
23
+ * - If no appropriate handler is found for an event, a system error event will be emitted.
24
+ * - The `source` field of emitted events will be set according to the configuration
25
+ * in the relevant `ArvoEventHandler`.
26
+ */
27
+ source: string;
28
+ /**
29
+ * The default execution cost of the function.
30
+ * This can represent a dollar value or some other number with a rate card.
31
+ */
32
+ executionunits: number;
33
+ /**
34
+ * A list of all available event handlers to be used by the router.
35
+ *
36
+ * @property {ArvoEventHandler<ArvoContract>[]} handlers
37
+ *
38
+ * @remarks
39
+ * This array contains instances of `ArvoEventHandler<ArvoContract>` which define
40
+ * how different types of events should be processed. The router will use these
41
+ * handlers to manage incoming events and generate appropriate responses or actions.
42
+ */
43
+ handlers: ArvoEventHandler<ArvoContract<any, any, any, any>>[];
44
+ /**
45
+ * The OpenTelemetry span kind attributes for the handler
46
+ * executor.
47
+ * @param [openInference] - The OpenInference span kind. Default is "CHAIN"
48
+ * @param [arvoExecution] - The ArvoExecution span kind. Default is "EVENT_HANDLER"
49
+ * @param [openTelemetry] - The OpenTelemetry span kind. Default is "INTERNAL"
50
+ */
51
+ spanKind?: {
52
+ openInference?: OpenInferenceSpanKind;
53
+ arvoExecution?: ArvoExecutionSpanKind;
54
+ openTelemetry?: SpanKind;
55
+ };
56
+ }
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,10 @@
1
+ import { ArvoEvent } from 'arvo-core';
2
+ export declare const deleteOtelHeaders: (event: ArvoEvent) => ArvoEvent<Record<string, any>, Record<string, string | number | boolean | null> & {
3
+ to: string | null;
4
+ accesscontrol: string | null;
5
+ redirectto: string | null;
6
+ executionunits: number | null;
7
+ } & {
8
+ traceparent: string | null;
9
+ tracestate: string | null;
10
+ }, string>;
@@ -0,0 +1,23 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.deleteOtelHeaders = void 0;
4
+ var arvo_core_1 = require("arvo-core");
5
+ var deleteOtelHeaders = function (event) {
6
+ return new arvo_core_1.ArvoEvent({
7
+ id: event.id,
8
+ time: event.time,
9
+ source: event.source,
10
+ specversion: '1.0',
11
+ type: event.type,
12
+ subject: event.subject,
13
+ datacontenttype: event.datacontenttype,
14
+ dataschema: event.dataschema,
15
+ to: event.to,
16
+ accesscontrol: event.accesscontrol,
17
+ redirectto: event.redirectto,
18
+ executionunits: event.executionunits,
19
+ traceparent: null,
20
+ tracestate: null,
21
+ }, event.data, event.cloudevent.extensions);
22
+ };
23
+ exports.deleteOtelHeaders = deleteOtelHeaders;
@@ -1,6 +1,6 @@
1
1
  import { SpanKind } from '@opentelemetry/api';
2
- import { ArvoEvent, ArvoExecutionSpanKind, OpenInferenceSpanKind } from "arvo-core";
3
- import { IMultiArvoEventHandler } from "./types";
2
+ import { ArvoEvent, ArvoExecutionSpanKind, OpenInferenceSpanKind } from 'arvo-core';
3
+ import { IMultiArvoEventHandler } from './types';
4
4
  /**
5
5
  * Represents a Multi ArvoEvent handler that can process multiple event types.
6
6
  *
@@ -17,9 +17,13 @@ export default class MultiArvoEventHandler {
17
17
  * The source identifier for events produced by this handler
18
18
  *
19
19
  * @remarks
20
+ * The handler listens to the events with field `event.to` equal
21
+ * to the this `source` value. If the event does not confirm to
22
+ * this, a system error event is returned
23
+ *
20
24
  * For all the events which are emitted by the handler, this is
21
25
  * the source field value of them all.
22
- */
26
+ */
23
27
  readonly source: string;
24
28
  readonly openInferenceSpanKind: OpenInferenceSpanKind;
25
29
  readonly arvoExecutionSpanKind: ArvoExecutionSpanKind;
@@ -41,9 +45,10 @@ export default class MultiArvoEventHandler {
41
45
  * @remarks
42
46
  * This method performs the following steps:
43
47
  * 1. Creates an OpenTelemetry span for the execution.
44
- * 2. Executes the handler function.
45
- * 3. Creates and returns the result event(s).
46
- * 4. Handles any errors and creates an error event if necessary.
48
+ * 2. Validates that the event's 'to' field matches the handler's 'source'.
49
+ * 3. Executes the handler function.
50
+ * 4. Creates and returns the result event(s).
51
+ * 5. Handles any errors and creates an error event if necessary.
47
52
  *
48
53
  * All telemetry data is properly set and propagated throughout the execution.
49
54
  *
@@ -57,22 +62,32 @@ export default class MultiArvoEventHandler {
57
62
  * const resultEvents = await handler.execute(inputEvent);
58
63
  * ```
59
64
  *
60
- * @throws All errors thrown during the execution are returned as a system error event
65
+ * @throws {Error} Throws an error if the event's 'to' field doesn't match the handler's 'source'.
66
+ * All other errors thrown during the execution are returned as a system error event.
61
67
  *
62
68
  * **Routing**
69
+ *
63
70
  * The routing of the resulting events is determined as follows:
64
71
  * - The `to` field of the output event is set in this priority:
65
72
  * 1. The `to` field provided by the handler result
66
- * 2. The `source` field from the input event (as a form of reply)
73
+ * 2. The `redirectto` field from the input event
74
+ * 3. The `source` field from the input event (as a form of reply)
67
75
  * - For system error events, the `to` field is always set to the `source` of the input event.
68
76
  *
69
77
  * **Telemetry**
78
+ *
70
79
  * - Creates a new span for each execution as per the traceparent and tracestate field
71
80
  * of the event. If those are not present, then a brand new span is created and distributed
72
81
  * tracing is disabled
73
82
  * - Sets span attributes for input and output events
74
83
  * - Propagates trace context to output events
75
84
  * - Handles error cases and sets appropriate span status
85
+ *
86
+ * **Event Validation**
87
+ *
88
+ * - Checks if the event's 'to' field matches the handler's 'source'.
89
+ * - If they don't match, an error is thrown with a descriptive message.
90
+ * - This ensures that the handler only processes events intended for it.
76
91
  */
77
92
  execute(event: ArvoEvent): Promise<ArvoEvent[]>;
78
93
  /**
@@ -87,15 +87,18 @@ var MultiArvoEventHandler = /** @class */ (function () {
87
87
  this.executionunits = param.executionunits;
88
88
  this._handler = param.handler;
89
89
  var error = schema_1.CloudEventContextSchema.pick({
90
- source: true
90
+ source: true,
91
91
  }).safeParse({ source: param.source }).error;
92
92
  if (error) {
93
93
  throw new Error("The provided 'source' is not a valid string. Error: ".concat(error.message));
94
94
  }
95
95
  this.source = param.source;
96
- this.arvoExecutionSpanKind = ((_a = param.spanKind) === null || _a === void 0 ? void 0 : _a.arvoExecution) || this.arvoExecutionSpanKind;
97
- this.openInferenceSpanKind = ((_b = param.spanKind) === null || _b === void 0 ? void 0 : _b.openInference) || this.openInferenceSpanKind;
98
- this.openTelemetrySpanKind = ((_c = param.spanKind) === null || _c === void 0 ? void 0 : _c.openTelemetry) || this.openTelemetrySpanKind;
96
+ this.arvoExecutionSpanKind =
97
+ ((_a = param.spanKind) === null || _a === void 0 ? void 0 : _a.arvoExecution) || this.arvoExecutionSpanKind;
98
+ this.openInferenceSpanKind =
99
+ ((_b = param.spanKind) === null || _b === void 0 ? void 0 : _b.openInference) || this.openInferenceSpanKind;
100
+ this.openTelemetrySpanKind =
101
+ ((_c = param.spanKind) === null || _c === void 0 ? void 0 : _c.openTelemetry) || this.openTelemetrySpanKind;
99
102
  }
100
103
  /**
101
104
  * Executes the event handler for a given event.
@@ -106,9 +109,10 @@ var MultiArvoEventHandler = /** @class */ (function () {
106
109
  * @remarks
107
110
  * This method performs the following steps:
108
111
  * 1. Creates an OpenTelemetry span for the execution.
109
- * 2. Executes the handler function.
110
- * 3. Creates and returns the result event(s).
111
- * 4. Handles any errors and creates an error event if necessary.
112
+ * 2. Validates that the event's 'to' field matches the handler's 'source'.
113
+ * 3. Executes the handler function.
114
+ * 4. Creates and returns the result event(s).
115
+ * 5. Handles any errors and creates an error event if necessary.
112
116
  *
113
117
  * All telemetry data is properly set and propagated throughout the execution.
114
118
  *
@@ -122,22 +126,32 @@ var MultiArvoEventHandler = /** @class */ (function () {
122
126
  * const resultEvents = await handler.execute(inputEvent);
123
127
  * ```
124
128
  *
125
- * @throws All errors thrown during the execution are returned as a system error event
129
+ * @throws {Error} Throws an error if the event's 'to' field doesn't match the handler's 'source'.
130
+ * All other errors thrown during the execution are returned as a system error event.
126
131
  *
127
132
  * **Routing**
133
+ *
128
134
  * The routing of the resulting events is determined as follows:
129
135
  * - The `to` field of the output event is set in this priority:
130
136
  * 1. The `to` field provided by the handler result
131
- * 2. The `source` field from the input event (as a form of reply)
137
+ * 2. The `redirectto` field from the input event
138
+ * 3. The `source` field from the input event (as a form of reply)
132
139
  * - For system error events, the `to` field is always set to the `source` of the input event.
133
140
  *
134
141
  * **Telemetry**
142
+ *
135
143
  * - Creates a new span for each execution as per the traceparent and tracestate field
136
144
  * of the event. If those are not present, then a brand new span is created and distributed
137
145
  * tracing is disabled
138
146
  * - Sets span attributes for input and output events
139
147
  * - Propagates trace context to output events
140
148
  * - Handles error cases and sets appropriate span status
149
+ *
150
+ * **Event Validation**
151
+ *
152
+ * - Checks if the event's 'to' field matches the handler's 'source'.
153
+ * - If they don't match, an error is thrown with a descriptive message.
154
+ * - This ensures that the handler only processes events intended for it.
141
155
  */
142
156
  MultiArvoEventHandler.prototype.execute = function (event) {
143
157
  return __awaiter(this, void 0, void 0, function () {
@@ -153,7 +167,7 @@ var MultiArvoEventHandler = /** @class */ (function () {
153
167
  attributes: (_a = {},
154
168
  _a[arvo_core_1.OpenInference.ATTR_SPAN_KIND] = this.openInferenceSpanKind,
155
169
  _a[arvo_core_1.ArvoExecution.ATTR_SPAN_KIND] = this.arvoExecutionSpanKind,
156
- _a)
170
+ _a),
157
171
  };
158
172
  if (event.traceparent) {
159
173
  inheritedContext = (0, OpenTelemetry_1.extractContext)(event.traceparent, event.tracestate);
@@ -177,7 +191,13 @@ var MultiArvoEventHandler = /** @class */ (function () {
177
191
  var key = _a[0], value = _a[1];
178
192
  return span.setAttribute("to_process.0.".concat(key), value);
179
193
  });
180
- return [4 /*yield*/, this._handler({ event: event, source: this.source })];
194
+ if (event.to !== this.source) {
195
+ throw new Error((0, arvo_core_1.cleanString)("\n Invalid event. The 'event.to' is ".concat(event.to, " while this handler \n listens to only 'event.to' equal to ").concat(this.source, ". If this is a mistake,\n please update the 'source' field of the handler\n ")));
196
+ }
197
+ return [4 /*yield*/, this._handler({
198
+ event: event,
199
+ source: this.source,
200
+ })];
181
201
  case 2:
182
202
  _handlerOutput = _a.sent();
183
203
  if (!_handlerOutput)
@@ -193,9 +213,9 @@ var MultiArvoEventHandler = /** @class */ (function () {
193
213
  var __extensions = output.__extensions, handlerResult = __rest(output, ["__extensions"]);
194
214
  var result = (0, arvo_core_1.createArvoEvent)(__assign(__assign({}, handlerResult), { traceparent: otelSpanHeaders.traceparent || undefined, tracestate: otelSpanHeaders.tracestate || undefined, source: _this.source, subject: event.subject,
195
215
  // The user should be able to override the `to` field
196
- // If that is not present then the 'redirectto' field
216
+ // If that is not present then the 'redirectto' field
197
217
  // is referred to. Then, after all else, 'source' field
198
- // is used as a form of reply.
218
+ // is used as a form of reply.
199
219
  to: (0, utils_1.coalesceOrDefault)([handlerResult.to, event.redirectto], event.source), executionunits: (0, utils_1.coalesce)(handlerResult.executionunits, _this.executionunits) }), __extensions);
200
220
  Object.entries(result.otelAttributes).forEach(function (_a) {
201
221
  var key = _a[0], value = _a[1];
@@ -214,7 +234,7 @@ var MultiArvoEventHandler = /** @class */ (function () {
214
234
  type: "sys.".concat(this.source, ".error"),
215
235
  source: this.source,
216
236
  subject: event.subject,
217
- // The system error must always got back to
237
+ // The system error must always got back to
218
238
  // the source
219
239
  to: event.source,
220
240
  executionunits: this.executionunits,
@@ -223,8 +243,8 @@ var MultiArvoEventHandler = /** @class */ (function () {
223
243
  data: {
224
244
  errorName: error_1.name,
225
245
  errorMessage: error_1.message,
226
- errorStack: error_1.stack || null
227
- }
246
+ errorStack: error_1.stack || null,
247
+ },
228
248
  });
229
249
  Object.entries(result.otelAttributes).forEach(function (_a) {
230
250
  var key = _a[0], value = _a[1];
@@ -262,7 +282,7 @@ var MultiArvoEventHandler = /** @class */ (function () {
262
282
  get: function () {
263
283
  return {
264
284
  type: "sys.".concat(this.source, ".error"),
265
- schema: arvo_core_1.ArvoErrorSchema
285
+ schema: arvo_core_1.ArvoErrorSchema,
266
286
  };
267
287
  },
268
288
  enumerable: false,
@@ -1,5 +1,5 @@
1
- import { SpanKind } from "@opentelemetry/api";
2
- import { ArvoEvent, ArvoExecutionSpanKind, CreateArvoEvent, OpenInferenceSpanKind } from "arvo-core";
1
+ import { SpanKind } from '@opentelemetry/api';
2
+ import { ArvoEvent, ArvoExecutionSpanKind, CreateArvoEvent, OpenInferenceSpanKind } from 'arvo-core';
3
3
  /**
4
4
  * Represents the input for a Multi ArvoEvent handler function.
5
5
  */
@@ -35,11 +35,15 @@ export type MultiArvoEventHandlerFunction = (param: MultiArvoEventHandlerFunctio
35
35
  */
36
36
  export interface IMultiArvoEventHandler {
37
37
  /**
38
- * The source definition of the MultiArvoEventHanlder.
38
+ * The source identifier for events produced by this handler
39
39
  *
40
40
  * @remarks
41
- * For all the events which are emitted by the handler, this will be the source
42
- * field value of them all.
41
+ * The handler listens to the events with field `event.to` equal
42
+ * to the this `source` value. If the event does not confirm to
43
+ * this, a system error event is returned
44
+ *
45
+ * For all the events which are emitted by the handler, this is
46
+ * the source field value of them all.
43
47
  */
44
48
  source: string;
45
49
  /**
package/dist/index.d.ts CHANGED
@@ -6,4 +6,7 @@ import MultiArvoEventHandler from './MultiArvoEventHandler';
6
6
  import { MultiArvoEventHandlerFunctionInput, MultiArvoEventHandlerFunctionOutput, MultiArvoEventHandlerFunction, IMultiArvoEventHandler } from './MultiArvoEventHandler/types';
7
7
  import { createMultiArvoEventHandler } from './MultiArvoEventHandler/helpers';
8
8
  import { isNullOrUndefined, getValueOrDefault, coalesce, coalesceOrDefault } from './utils';
9
- export { ArvoEventHandler, createArvoEventHandler, IArvoEventHandler, ArvoEventHandlerFunctionOutput, ArvoEventHandlerFunctionInput, ArvoEventHandlerFunction, PartialExcept, MultiArvoEventHandler, MultiArvoEventHandlerFunctionInput, MultiArvoEventHandlerFunctionOutput, MultiArvoEventHandlerFunction, IMultiArvoEventHandler, createMultiArvoEventHandler, isNullOrUndefined, getValueOrDefault, coalesce, coalesceOrDefault, };
9
+ import { IArvoEventRouter } from './ArvoEventRouter/types';
10
+ import { ArvoEventRouter } from './ArvoEventRouter';
11
+ import { createArvoEventRouter } from './ArvoEventRouter/helpers';
12
+ export { ArvoEventHandler, createArvoEventHandler, IArvoEventHandler, ArvoEventHandlerFunctionOutput, ArvoEventHandlerFunctionInput, ArvoEventHandlerFunction, PartialExcept, MultiArvoEventHandler, MultiArvoEventHandlerFunctionInput, MultiArvoEventHandlerFunctionOutput, MultiArvoEventHandlerFunction, IMultiArvoEventHandler, createMultiArvoEventHandler, isNullOrUndefined, getValueOrDefault, coalesce, coalesceOrDefault, IArvoEventRouter, ArvoEventRouter, createArvoEventRouter, };
package/dist/index.js CHANGED
@@ -3,7 +3,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
3
3
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.coalesceOrDefault = exports.coalesce = exports.getValueOrDefault = exports.isNullOrUndefined = exports.createMultiArvoEventHandler = exports.MultiArvoEventHandler = exports.createArvoEventHandler = exports.ArvoEventHandler = void 0;
6
+ exports.createArvoEventRouter = exports.ArvoEventRouter = exports.coalesceOrDefault = exports.coalesce = exports.getValueOrDefault = exports.isNullOrUndefined = exports.createMultiArvoEventHandler = exports.MultiArvoEventHandler = exports.createArvoEventHandler = exports.ArvoEventHandler = void 0;
7
7
  var ArvoEventHandler_1 = __importDefault(require("./ArvoEventHandler"));
8
8
  exports.ArvoEventHandler = ArvoEventHandler_1.default;
9
9
  var helpers_1 = require("./ArvoEventHandler/helpers");
@@ -17,3 +17,7 @@ Object.defineProperty(exports, "isNullOrUndefined", { enumerable: true, get: fun
17
17
  Object.defineProperty(exports, "getValueOrDefault", { enumerable: true, get: function () { return utils_1.getValueOrDefault; } });
18
18
  Object.defineProperty(exports, "coalesce", { enumerable: true, get: function () { return utils_1.coalesce; } });
19
19
  Object.defineProperty(exports, "coalesceOrDefault", { enumerable: true, get: function () { return utils_1.coalesceOrDefault; } });
20
+ var ArvoEventRouter_1 = require("./ArvoEventRouter");
21
+ Object.defineProperty(exports, "ArvoEventRouter", { enumerable: true, get: function () { return ArvoEventRouter_1.ArvoEventRouter; } });
22
+ var helpers_3 = require("./ArvoEventRouter/helpers");
23
+ Object.defineProperty(exports, "createArvoEventRouter", { enumerable: true, get: function () { return helpers_3.createArvoEventRouter; } });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "arvo-event-handler",
3
- "version": "1.0.0",
3
+ "version": "1.0.2",
4
4
  "description": "This package contains class and function for event handlers in an Arvo Event Driven system",
5
5
  "main": "dist/index.js",
6
6
  "scripts": {
@@ -42,13 +42,14 @@
42
42
  "ts-jest": "^29.2.5",
43
43
  "ts-node": "^10.9.2",
44
44
  "typedoc": "^0.26.6",
45
+ "typedoc-github-theme": "^0.1.2",
45
46
  "typedoc-plugin-mermaid": "^1.12.0",
46
47
  "typedoc-plugin-zod": "^1.2.1",
47
48
  "typescript": "^5.5.4"
48
49
  },
49
50
  "dependencies": {
50
51
  "@opentelemetry/api": "^1.9.0",
51
- "arvo-core": "^1.0.29",
52
+ "arvo-core": "^1.0.30",
52
53
  "uuid": "^10.0.0",
53
54
  "zod": "^3.23.8"
54
55
  }