@rolandsall24/nest-mediator 0.5.2 → 0.7.0
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/README.md +597 -40
- package/dist/lib/decorators/event-criticality.decorator.d.ts +61 -0
- package/dist/lib/decorators/event-criticality.decorator.d.ts.map +1 -0
- package/dist/lib/decorators/event-criticality.decorator.js +71 -0
- package/dist/lib/decorators/event-criticality.decorator.js.map +1 -0
- package/dist/lib/decorators/event-handler.decorator.d.ts +21 -0
- package/dist/lib/decorators/event-handler.decorator.d.ts.map +1 -0
- package/dist/lib/decorators/event-handler.decorator.js +27 -0
- package/dist/lib/decorators/event-handler.decorator.js.map +1 -0
- package/dist/lib/decorators/index.d.ts +2 -0
- package/dist/lib/decorators/index.d.ts.map +1 -1
- package/dist/lib/decorators/index.js +2 -0
- package/dist/lib/decorators/index.js.map +1 -1
- package/dist/lib/decorators/pipeline-behavior.decorator.d.ts +49 -0
- package/dist/lib/decorators/pipeline-behavior.decorator.d.ts.map +1 -1
- package/dist/lib/decorators/pipeline-behavior.decorator.js +56 -1
- package/dist/lib/decorators/pipeline-behavior.decorator.js.map +1 -1
- package/dist/lib/interfaces/command-bus.interface.d.ts +25 -0
- package/dist/lib/interfaces/command-bus.interface.d.ts.map +1 -0
- package/dist/lib/interfaces/command-bus.interface.js +3 -0
- package/dist/lib/interfaces/command-bus.interface.js.map +1 -0
- package/dist/lib/interfaces/event-bus.interface.d.ts +35 -0
- package/dist/lib/interfaces/event-bus.interface.d.ts.map +1 -0
- package/dist/lib/interfaces/event-bus.interface.js +3 -0
- package/dist/lib/interfaces/event-bus.interface.js.map +1 -0
- package/dist/lib/interfaces/event-consumer.interface.d.ts +64 -0
- package/dist/lib/interfaces/event-consumer.interface.d.ts.map +1 -0
- package/dist/lib/interfaces/event-consumer.interface.js +3 -0
- package/dist/lib/interfaces/event-consumer.interface.js.map +1 -0
- package/dist/lib/interfaces/event-criticality.interface.d.ts +28 -0
- package/dist/lib/interfaces/event-criticality.interface.d.ts.map +1 -0
- package/dist/lib/interfaces/event-criticality.interface.js +25 -0
- package/dist/lib/interfaces/event-criticality.interface.js.map +1 -0
- package/dist/lib/interfaces/event-handler.interface.d.ts +24 -0
- package/dist/lib/interfaces/event-handler.interface.d.ts.map +1 -0
- package/dist/lib/interfaces/event-handler.interface.js +3 -0
- package/dist/lib/interfaces/event-handler.interface.js.map +1 -0
- package/dist/lib/interfaces/event.interface.d.ts +30 -0
- package/dist/lib/interfaces/event.interface.d.ts.map +1 -0
- package/dist/lib/interfaces/event.interface.js +3 -0
- package/dist/lib/interfaces/event.interface.js.map +1 -0
- package/dist/lib/interfaces/index.d.ts +7 -0
- package/dist/lib/interfaces/index.d.ts.map +1 -1
- package/dist/lib/interfaces/index.js +7 -0
- package/dist/lib/interfaces/index.js.map +1 -1
- package/dist/lib/interfaces/mediator.interface.d.ts +14 -0
- package/dist/lib/interfaces/mediator.interface.d.ts.map +1 -0
- package/dist/lib/interfaces/mediator.interface.js +3 -0
- package/dist/lib/interfaces/mediator.interface.js.map +1 -0
- package/dist/lib/interfaces/query-bus.interface.d.ts +26 -0
- package/dist/lib/interfaces/query-bus.interface.d.ts.map +1 -0
- package/dist/lib/interfaces/query-bus.interface.js +3 -0
- package/dist/lib/interfaces/query-bus.interface.js.map +1 -0
- package/dist/lib/nest-mediator.module.d.ts.map +1 -1
- package/dist/lib/nest-mediator.module.js +37 -2
- package/dist/lib/nest-mediator.module.js.map +1 -1
- package/dist/lib/services/command.bus.d.ts +30 -0
- package/dist/lib/services/command.bus.d.ts.map +1 -0
- package/dist/lib/services/command.bus.js +69 -0
- package/dist/lib/services/command.bus.js.map +1 -0
- package/dist/lib/services/event.bus.d.ts +61 -0
- package/dist/lib/services/event.bus.d.ts.map +1 -0
- package/dist/lib/services/event.bus.js +176 -0
- package/dist/lib/services/event.bus.js.map +1 -0
- package/dist/lib/services/mediator.bus.d.ts +50 -31
- package/dist/lib/services/mediator.bus.d.ts.map +1 -1
- package/dist/lib/services/mediator.bus.js +60 -97
- package/dist/lib/services/mediator.bus.js.map +1 -1
- package/dist/lib/services/pipeline.orchestrator.d.ts +46 -0
- package/dist/lib/services/pipeline.orchestrator.d.ts.map +1 -0
- package/dist/lib/services/pipeline.orchestrator.js +87 -0
- package/dist/lib/services/pipeline.orchestrator.js.map +1 -0
- package/dist/lib/services/query.bus.d.ts +31 -0
- package/dist/lib/services/query.bus.d.ts.map +1 -0
- package/dist/lib/services/query.bus.js +68 -0
- package/dist/lib/services/query.bus.js.map +1 -0
- package/package.json +1 -1
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Marker interface for events
|
|
3
|
+
* Events represent something that has happened in the domain.
|
|
4
|
+
* Multiple handlers can subscribe to the same event.
|
|
5
|
+
*/
|
|
6
|
+
export interface IEvent {
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Result of publishing an event
|
|
10
|
+
*/
|
|
11
|
+
export interface EventPublishResult {
|
|
12
|
+
/**
|
|
13
|
+
* Total number of handlers that were invoked
|
|
14
|
+
*/
|
|
15
|
+
totalHandlers: number;
|
|
16
|
+
/**
|
|
17
|
+
* Number of critical handlers that executed successfully
|
|
18
|
+
*/
|
|
19
|
+
criticalSucceeded: number;
|
|
20
|
+
/**
|
|
21
|
+
* Number of non-critical handlers that were dispatched
|
|
22
|
+
* Note: Non-critical handlers run in background, so this only indicates they were started
|
|
23
|
+
*/
|
|
24
|
+
nonCriticalDispatched: number;
|
|
25
|
+
/**
|
|
26
|
+
* Number of compensations that were executed (only non-zero when a critical handler fails)
|
|
27
|
+
*/
|
|
28
|
+
compensationsRun: number;
|
|
29
|
+
}
|
|
30
|
+
//# sourceMappingURL=event.interface.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"event.interface.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/event.interface.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AACH,MAAM,WAAW,MAAM;CAAG;AAE1B;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC;;OAEG;IACH,aAAa,EAAE,MAAM,CAAC;IAEtB;;OAEG;IACH,iBAAiB,EAAE,MAAM,CAAC;IAE1B;;;OAGG;IACH,qBAAqB,EAAE,MAAM,CAAC;IAE9B;;OAEG;IACH,gBAAgB,EAAE,MAAM,CAAC;CAC1B"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"event.interface.js","sourceRoot":"","sources":["../../../src/lib/interfaces/event.interface.ts"],"names":[],"mappings":""}
|
|
@@ -3,4 +3,11 @@ export * from './query.interface.js';
|
|
|
3
3
|
export * from './command-handler.interface.js';
|
|
4
4
|
export * from './query-handler.interface.js';
|
|
5
5
|
export * from './pipeline-behavior.interface.js';
|
|
6
|
+
export * from './event.interface.js';
|
|
7
|
+
export * from './event-consumer.interface.js';
|
|
8
|
+
export * from './event-criticality.interface.js';
|
|
9
|
+
export * from './command-bus.interface.js';
|
|
10
|
+
export * from './query-bus.interface.js';
|
|
11
|
+
export * from './event-bus.interface.js';
|
|
12
|
+
export * from './mediator.interface.js';
|
|
6
13
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/index.ts"],"names":[],"mappings":"AAAA,cAAc,wBAAwB,CAAC;AACvC,cAAc,sBAAsB,CAAC;AACrC,cAAc,gCAAgC,CAAC;AAC/C,cAAc,8BAA8B,CAAC;AAC7C,cAAc,kCAAkC,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/index.ts"],"names":[],"mappings":"AAAA,cAAc,wBAAwB,CAAC;AACvC,cAAc,sBAAsB,CAAC;AACrC,cAAc,gCAAgC,CAAC;AAC/C,cAAc,8BAA8B,CAAC;AAC7C,cAAc,kCAAkC,CAAC;AACjD,cAAc,sBAAsB,CAAC;AACrC,cAAc,+BAA+B,CAAC;AAC9C,cAAc,kCAAkC,CAAC;AACjD,cAAc,4BAA4B,CAAC;AAC3C,cAAc,0BAA0B,CAAC;AACzC,cAAc,0BAA0B,CAAC;AACzC,cAAc,yBAAyB,CAAC"}
|
|
@@ -19,4 +19,11 @@ __exportStar(require("./query.interface.js"), exports);
|
|
|
19
19
|
__exportStar(require("./command-handler.interface.js"), exports);
|
|
20
20
|
__exportStar(require("./query-handler.interface.js"), exports);
|
|
21
21
|
__exportStar(require("./pipeline-behavior.interface.js"), exports);
|
|
22
|
+
__exportStar(require("./event.interface.js"), exports);
|
|
23
|
+
__exportStar(require("./event-consumer.interface.js"), exports);
|
|
24
|
+
__exportStar(require("./event-criticality.interface.js"), exports);
|
|
25
|
+
__exportStar(require("./command-bus.interface.js"), exports);
|
|
26
|
+
__exportStar(require("./query-bus.interface.js"), exports);
|
|
27
|
+
__exportStar(require("./event-bus.interface.js"), exports);
|
|
28
|
+
__exportStar(require("./mediator.interface.js"), exports);
|
|
22
29
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/lib/interfaces/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,yDAAuC;AACvC,uDAAqC;AACrC,iEAA+C;AAC/C,+DAA6C;AAC7C,mEAAiD"}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/lib/interfaces/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,yDAAuC;AACvC,uDAAqC;AACrC,iEAA+C;AAC/C,+DAA6C;AAC7C,mEAAiD;AACjD,uDAAqC;AACrC,gEAA8C;AAC9C,mEAAiD;AACjD,6DAA2C;AAC3C,2DAAyC;AACzC,2DAAyC;AACzC,0DAAwC"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { ICommandBus } from './command-bus.interface.js';
|
|
2
|
+
import { IQueryBus } from './query-bus.interface.js';
|
|
3
|
+
import { IEventBus } from './event-bus.interface.js';
|
|
4
|
+
/**
|
|
5
|
+
* Unified mediator interface combining command, query, and event bus capabilities.
|
|
6
|
+
* This is the primary interface clients should depend on.
|
|
7
|
+
*/
|
|
8
|
+
export interface IMediator extends ICommandBus, IQueryBus, IEventBus {
|
|
9
|
+
/**
|
|
10
|
+
* Get registered behavior names (for debugging)
|
|
11
|
+
*/
|
|
12
|
+
getRegisteredBehaviors(): string[];
|
|
13
|
+
}
|
|
14
|
+
//# sourceMappingURL=mediator.interface.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mediator.interface.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/mediator.interface.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,4BAA4B,CAAC;AACzD,OAAO,EAAE,SAAS,EAAE,MAAM,0BAA0B,CAAC;AACrD,OAAO,EAAE,SAAS,EAAE,MAAM,0BAA0B,CAAC;AAErD;;;GAGG;AACH,MAAM,WAAW,SAAU,SAAQ,WAAW,EAAE,SAAS,EAAE,SAAS;IAClE;;OAEG;IACH,sBAAsB,IAAI,MAAM,EAAE,CAAC;CACpC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"mediator.interface.js","sourceRoot":"","sources":["../../../src/lib/interfaces/mediator.interface.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { Type } from '@nestjs/common';
|
|
2
|
+
import { IQuery } from './query.interface.js';
|
|
3
|
+
import { IQueryHandler } from './query-handler.interface.js';
|
|
4
|
+
/**
|
|
5
|
+
* Interface for the query bus.
|
|
6
|
+
* Responsible for dispatching queries to their handlers.
|
|
7
|
+
*/
|
|
8
|
+
export interface IQueryBus {
|
|
9
|
+
/**
|
|
10
|
+
* Execute a query through its handler
|
|
11
|
+
* @param query - The query instance
|
|
12
|
+
* @returns Promise with the result
|
|
13
|
+
*/
|
|
14
|
+
query<TQuery extends IQuery, TResult = any>(query: TQuery): Promise<TResult>;
|
|
15
|
+
/**
|
|
16
|
+
* Register a query handler
|
|
17
|
+
* @param query - The query class
|
|
18
|
+
* @param handler - The handler class
|
|
19
|
+
*/
|
|
20
|
+
registerQueryHandler(query: Type<IQuery>, handler: Type<IQueryHandler<any, any>>): void;
|
|
21
|
+
/**
|
|
22
|
+
* Get registered query names (for debugging)
|
|
23
|
+
*/
|
|
24
|
+
getRegisteredQueries(): string[];
|
|
25
|
+
}
|
|
26
|
+
//# sourceMappingURL=query-bus.interface.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"query-bus.interface.d.ts","sourceRoot":"","sources":["../../../src/lib/interfaces/query-bus.interface.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,gBAAgB,CAAC;AACtC,OAAO,EAAE,MAAM,EAAE,MAAM,sBAAsB,CAAC;AAC9C,OAAO,EAAE,aAAa,EAAE,MAAM,8BAA8B,CAAC;AAE7D;;;GAGG;AACH,MAAM,WAAW,SAAS;IACxB;;;;OAIG;IACH,KAAK,CAAC,MAAM,SAAS,MAAM,EAAE,OAAO,GAAG,GAAG,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;IAE7E;;;;OAIG;IACH,oBAAoB,CAClB,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC,EACnB,OAAO,EAAE,IAAI,CAAC,aAAa,CAAC,GAAG,EAAE,GAAG,CAAC,CAAC,GACrC,IAAI,CAAC;IAER;;OAEG;IACH,oBAAoB,IAAI,MAAM,EAAE,CAAC;CAClC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"query-bus.interface.js","sourceRoot":"","sources":["../../../src/lib/interfaces/query-bus.interface.ts"],"names":[],"mappings":""}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"nest-mediator.module.d.ts","sourceRoot":"","sources":["../../src/lib/nest-mediator.module.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAgB,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAC3E,OAAO,EAAE,SAAS,EAAE,gBAAgB,EAAmB,MAAM,cAAc,CAAC;AAC5E,OAAO,EAAE,WAAW,EAAE,MAAM,qBAAqB,CAAC;
|
|
1
|
+
{"version":3,"file":"nest-mediator.module.d.ts","sourceRoot":"","sources":["../../src/lib/nest-mediator.module.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAgB,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAC3E,OAAO,EAAE,SAAS,EAAE,gBAAgB,EAAmB,MAAM,cAAc,CAAC;AAC5E,OAAO,EAAE,WAAW,EAAE,MAAM,qBAAqB,CAAC;AA8BlD;;GAEG;AACH,MAAM,WAAW,yBAAyB;IACxC;;;;OAIG;IACH,aAAa,CAAC,EAAE,OAAO,CAAC;IAExB;;;;OAIG;IACH,gBAAgB,CAAC,EAAE,OAAO,CAAC;IAE3B;;;;OAIG;IACH,uBAAuB,CAAC,EAAE,OAAO,CAAC;IAElC;;;;OAIG;IACH,yBAAyB,CAAC,EAAE,OAAO,CAAC;IAEpC;;;;;OAKG;IACH,sBAAsB,CAAC,EAAE,MAAM,CAAC;CACjC;AAED;;GAEG;AACH,eAAO,MAAM,qBAAqB,0BAA0B,CAAC;AAE7D,qBACa,kBAAmB,YAAW,YAAY;IAEnD,OAAO,CAAC,QAAQ,CAAC,WAAW;IAC5B,OAAO,CAAC,QAAQ,CAAC,SAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,gBAAgB;gBAFhB,WAAW,EAAE,WAAW,EACxB,SAAS,EAAE,SAAS,EACpB,gBAAgB,EAAE,gBAAgB;IAGrD,YAAY;IAwHZ;;;;;;;;;;;;;;;;;;;;;OAqBG;IACH,MAAM,CAAC,OAAO,CAAC,OAAO,GAAE,yBAA8B,GAAG,aAAa;CAwCvE"}
|
|
@@ -14,6 +14,10 @@ exports.NestMediatorModule = exports.NEST_MEDIATOR_OPTIONS = void 0;
|
|
|
14
14
|
const common_1 = require("@nestjs/common");
|
|
15
15
|
const core_1 = require("@nestjs/core");
|
|
16
16
|
const index_js_1 = require("./services/index.js");
|
|
17
|
+
const command_bus_js_1 = require("./services/command.bus.js");
|
|
18
|
+
const query_bus_js_1 = require("./services/query.bus.js");
|
|
19
|
+
const event_bus_js_1 = require("./services/event.bus.js");
|
|
20
|
+
const pipeline_orchestrator_js_1 = require("./services/pipeline.orchestrator.js");
|
|
17
21
|
const index_js_2 = require("./decorators/index.js");
|
|
18
22
|
const index_js_3 = require("./behaviors/index.js");
|
|
19
23
|
/**
|
|
@@ -53,8 +57,35 @@ let NestMediatorModule = NestMediatorModule_1 = class NestMediatorModule {
|
|
|
53
57
|
// Register pipeline behaviors
|
|
54
58
|
const behaviorMetadata = this.reflector.get(index_js_2.PIPELINE_BEHAVIOR_METADATA, handlerType);
|
|
55
59
|
if (behaviorMetadata) {
|
|
56
|
-
|
|
57
|
-
|
|
60
|
+
// Try to infer request type from handle method's first parameter
|
|
61
|
+
// This only works if @PipelineBehavior() decorator is applied to the handle method
|
|
62
|
+
const handleParamTypes = Reflect.getMetadata('design:paramtypes', handlerType.prototype, 'handle');
|
|
63
|
+
// Get the first parameter type (the request type)
|
|
64
|
+
// Only use it if it's a concrete class (not Object, Function, or undefined)
|
|
65
|
+
let requestType;
|
|
66
|
+
if (handleParamTypes && handleParamTypes[0]) {
|
|
67
|
+
const firstParamType = handleParamTypes[0];
|
|
68
|
+
// Exclude generic types like Object, Function that indicate no specific type
|
|
69
|
+
if (firstParamType !== Object &&
|
|
70
|
+
firstParamType !== Function &&
|
|
71
|
+
typeof firstParamType === 'function') {
|
|
72
|
+
requestType = firstParamType;
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
const requestTypeInfo = requestType ? `, requestType: ${requestType.name}` : '';
|
|
76
|
+
console.log(`[NestMediator] Registering pipeline behavior: ${handlerType.name} (priority: ${behaviorMetadata.priority ?? 0}, scope: ${behaviorMetadata.scope ?? 'all'}${requestTypeInfo})`);
|
|
77
|
+
this.mediatorBus.registerPipelineBehavior(handlerType, behaviorMetadata, requestType);
|
|
78
|
+
}
|
|
79
|
+
// Register event handlers
|
|
80
|
+
const eventMetadata = this.reflector.get(index_js_2.EVENT_HANDLER_METADATA, handlerType);
|
|
81
|
+
if (eventMetadata) {
|
|
82
|
+
// Get criticality metadata (if any)
|
|
83
|
+
const criticalityMetadata = this.reflector.get(index_js_2.EVENT_CRITICALITY_METADATA, handlerType);
|
|
84
|
+
const criticalityInfo = criticalityMetadata
|
|
85
|
+
? ` (criticality: ${criticalityMetadata.criticality}, order: ${criticalityMetadata.order})`
|
|
86
|
+
: ' (criticality: non-critical)';
|
|
87
|
+
console.log(`[NestMediator] Registering event handler: ${handlerType.name} for event: ${eventMetadata.name}${criticalityInfo}`);
|
|
88
|
+
this.mediatorBus.registerEventHandler(eventMetadata, handlerType, criticalityMetadata);
|
|
58
89
|
}
|
|
59
90
|
}
|
|
60
91
|
}
|
|
@@ -99,6 +130,10 @@ let NestMediatorModule = NestMediatorModule_1 = class NestMediatorModule {
|
|
|
99
130
|
module: NestMediatorModule_1,
|
|
100
131
|
imports: [core_1.DiscoveryModule],
|
|
101
132
|
providers: [
|
|
133
|
+
pipeline_orchestrator_js_1.PipelineOrchestrator,
|
|
134
|
+
command_bus_js_1.CommandBus,
|
|
135
|
+
query_bus_js_1.QueryBus,
|
|
136
|
+
event_bus_js_1.EventBus,
|
|
102
137
|
index_js_1.MediatorBus,
|
|
103
138
|
core_1.Reflector,
|
|
104
139
|
...builtInProviders,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"nest-mediator.module.js","sourceRoot":"","sources":["../../src/lib/nest-mediator.module.ts"],"names":[],"mappings":";;;;;;;;;;;;;AAAA,2CAA2E;AAC3E,uCAA4E;AAC5E,kDAAkD;AAClD,
|
|
1
|
+
{"version":3,"file":"nest-mediator.module.js","sourceRoot":"","sources":["../../src/lib/nest-mediator.module.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { Type } from '@nestjs/common';
|
|
2
|
+
import { ModuleRef } from '@nestjs/core';
|
|
3
|
+
import { ICommand, ICommandHandler, ICommandBus } from '../interfaces/index.js';
|
|
4
|
+
import { PipelineOrchestrator } from './pipeline.orchestrator.js';
|
|
5
|
+
/**
|
|
6
|
+
* Command bus implementation.
|
|
7
|
+
* Dispatches commands to their handlers through the pipeline.
|
|
8
|
+
*/
|
|
9
|
+
export declare class CommandBus implements ICommandBus {
|
|
10
|
+
private readonly moduleRef;
|
|
11
|
+
private readonly pipelineOrchestrator;
|
|
12
|
+
private readonly handlers;
|
|
13
|
+
constructor(moduleRef: ModuleRef, pipelineOrchestrator: PipelineOrchestrator);
|
|
14
|
+
/**
|
|
15
|
+
* Send a command to its handler through the pipeline
|
|
16
|
+
* @param command - The command instance
|
|
17
|
+
*/
|
|
18
|
+
send<TCommand extends ICommand>(command: TCommand): Promise<void>;
|
|
19
|
+
/**
|
|
20
|
+
* Register a command handler
|
|
21
|
+
* @param command - The command class
|
|
22
|
+
* @param handler - The handler class
|
|
23
|
+
*/
|
|
24
|
+
registerCommandHandler(command: Type<ICommand>, handler: Type<ICommandHandler<any>>): void;
|
|
25
|
+
/**
|
|
26
|
+
* Get registered command names (for debugging)
|
|
27
|
+
*/
|
|
28
|
+
getRegisteredCommands(): string[];
|
|
29
|
+
}
|
|
30
|
+
//# sourceMappingURL=command.bus.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"command.bus.d.ts","sourceRoot":"","sources":["../../../src/lib/services/command.bus.ts"],"names":[],"mappings":"AAAA,OAAO,EAAc,IAAI,EAAE,MAAM,gBAAgB,CAAC;AAClD,OAAO,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC;AACzC,OAAO,EAAE,QAAQ,EAAE,eAAe,EAAE,WAAW,EAAE,MAAM,wBAAwB,CAAC;AAEhF,OAAO,EAAE,oBAAoB,EAAE,MAAM,4BAA4B,CAAC;AAElE;;;GAGG;AACH,qBACa,UAAW,YAAW,WAAW;IAI1C,OAAO,CAAC,QAAQ,CAAC,SAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,oBAAoB;IAJvC,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAiD;gBAGvD,SAAS,EAAE,SAAS,EACpB,oBAAoB,EAAE,oBAAoB;IAG7D;;;OAGG;IACG,IAAI,CAAC,QAAQ,SAAS,QAAQ,EAAE,OAAO,EAAE,QAAQ,GAAG,OAAO,CAAC,IAAI,CAAC;IAsBvE;;;;OAIG;IACH,sBAAsB,CACpB,OAAO,EAAE,IAAI,CAAC,QAAQ,CAAC,EACvB,OAAO,EAAE,IAAI,CAAC,eAAe,CAAC,GAAG,CAAC,CAAC,GAClC,IAAI;IAUP;;OAEG;IACH,qBAAqB,IAAI,MAAM,EAAE;CAGlC"}
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
3
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
4
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
5
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
6
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
7
|
+
};
|
|
8
|
+
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
9
|
+
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
10
|
+
};
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
exports.CommandBus = void 0;
|
|
13
|
+
const common_1 = require("@nestjs/common");
|
|
14
|
+
const core_1 = require("@nestjs/core");
|
|
15
|
+
const handler_not_found_exception_js_1 = require("../exceptions/handler-not-found.exception.js");
|
|
16
|
+
const pipeline_orchestrator_js_1 = require("./pipeline.orchestrator.js");
|
|
17
|
+
/**
|
|
18
|
+
* Command bus implementation.
|
|
19
|
+
* Dispatches commands to their handlers through the pipeline.
|
|
20
|
+
*/
|
|
21
|
+
let CommandBus = class CommandBus {
|
|
22
|
+
constructor(moduleRef, pipelineOrchestrator) {
|
|
23
|
+
this.moduleRef = moduleRef;
|
|
24
|
+
this.pipelineOrchestrator = pipelineOrchestrator;
|
|
25
|
+
this.handlers = new Map();
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* Send a command to its handler through the pipeline
|
|
29
|
+
* @param command - The command instance
|
|
30
|
+
*/
|
|
31
|
+
async send(command) {
|
|
32
|
+
const commandName = command.constructor.name;
|
|
33
|
+
const handlerType = this.handlers.get(commandName);
|
|
34
|
+
if (!handlerType) {
|
|
35
|
+
throw new handler_not_found_exception_js_1.HandlerNotFoundException(commandName, 'command');
|
|
36
|
+
}
|
|
37
|
+
const handler = this.moduleRef.get(handlerType, {
|
|
38
|
+
strict: false,
|
|
39
|
+
});
|
|
40
|
+
// Build and execute pipeline
|
|
41
|
+
const pipeline = this.pipelineOrchestrator.buildPipeline(command, 'command', () => handler.execute(command));
|
|
42
|
+
await pipeline();
|
|
43
|
+
}
|
|
44
|
+
/**
|
|
45
|
+
* Register a command handler
|
|
46
|
+
* @param command - The command class
|
|
47
|
+
* @param handler - The handler class
|
|
48
|
+
*/
|
|
49
|
+
registerCommandHandler(command, handler) {
|
|
50
|
+
const commandName = command.name;
|
|
51
|
+
if (this.handlers.has(commandName)) {
|
|
52
|
+
throw new Error(`Command handler for ${commandName} is already registered`);
|
|
53
|
+
}
|
|
54
|
+
this.handlers.set(commandName, handler);
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Get registered command names (for debugging)
|
|
58
|
+
*/
|
|
59
|
+
getRegisteredCommands() {
|
|
60
|
+
return Array.from(this.handlers.keys());
|
|
61
|
+
}
|
|
62
|
+
};
|
|
63
|
+
exports.CommandBus = CommandBus;
|
|
64
|
+
exports.CommandBus = CommandBus = __decorate([
|
|
65
|
+
(0, common_1.Injectable)(),
|
|
66
|
+
__metadata("design:paramtypes", [core_1.ModuleRef,
|
|
67
|
+
pipeline_orchestrator_js_1.PipelineOrchestrator])
|
|
68
|
+
], CommandBus);
|
|
69
|
+
//# sourceMappingURL=command.bus.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"command.bus.js","sourceRoot":"","sources":["../../../src/lib/services/command.bus.ts"],"names":[],"mappings":";;;;;;;;;;;;AAAA,2CAAkD;AAClD,uCAAyC;AAEzC,iGAAwF;AACxF,yEAAkE;AAElE;;;GAGG;AAEI,IAAM,UAAU,GAAhB,MAAM,UAAU;IAGrB,YACmB,SAAoB,EACpB,oBAA0C;QAD1C,cAAS,GAAT,SAAS,CAAW;QACpB,yBAAoB,GAApB,oBAAoB,CAAsB;QAJ5C,aAAQ,GAAG,IAAI,GAAG,EAAsC,CAAC;IAKvE,CAAC;IAEJ;;;OAGG;IACH,KAAK,CAAC,IAAI,CAA4B,OAAiB;QACrD,MAAM,WAAW,GAAG,OAAO,CAAC,WAAW,CAAC,IAAI,CAAC;QAC7C,MAAM,WAAW,GAAG,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,WAAW,CAAC,CAAC;QAEnD,IAAI,CAAC,WAAW,EAAE,CAAC;YACjB,MAAM,IAAI,yDAAwB,CAAC,WAAW,EAAE,SAAS,CAAC,CAAC;QAC7D,CAAC;QAED,MAAM,OAAO,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CAA4B,WAAW,EAAE;YACzE,MAAM,EAAE,KAAK;SACd,CAAC,CAAC;QAEH,6BAA6B;QAC7B,MAAM,QAAQ,GAAG,IAAI,CAAC,oBAAoB,CAAC,aAAa,CACtD,OAAO,EACP,SAAS,EACT,GAAG,EAAE,CAAC,OAAO,CAAC,OAAO,CAAC,OAAO,CAAC,CAC/B,CAAC;QAEF,MAAM,QAAQ,EAAE,CAAC;IACnB,CAAC;IAED;;;;OAIG;IACH,sBAAsB,CACpB,OAAuB,EACvB,OAAmC;QAEnC,MAAM,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC;QACjC,IAAI,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,WAAW,CAAC,EAAE,CAAC;YACnC,MAAM,IAAI,KAAK,CACb,uBAAuB,WAAW,wBAAwB,CAC3D,CAAC;QACJ,CAAC;QACD,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,WAAW,EAAE,OAAO,CAAC,CAAC;IAC1C,CAAC;IAED;;OAEG;IACH,qBAAqB;QACnB,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,IAAI,EAAE,CAAC,CAAC;IAC1C,CAAC;CACF,CAAA;AA1DY,gCAAU;qBAAV,UAAU;IADtB,IAAA,mBAAU,GAAE;qCAKmB,gBAAS;QACE,+CAAoB;GALlD,UAAU,CA0DtB"}
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
import { Type } from '@nestjs/common';
|
|
2
|
+
import { ModuleRef } from '@nestjs/core';
|
|
3
|
+
import { IEvent, IEventConsumer, IEventBus, EventPublishResult, EventCriticalityMetadata } from '../interfaces/index.js';
|
|
4
|
+
/**
|
|
5
|
+
* Event bus implementation.
|
|
6
|
+
* Publishes events to their consumers with critical/non-critical handling.
|
|
7
|
+
* Supports saga-style compensation for critical consumers.
|
|
8
|
+
*/
|
|
9
|
+
export declare class EventBus implements IEventBus {
|
|
10
|
+
private readonly moduleRef;
|
|
11
|
+
private readonly logger;
|
|
12
|
+
private readonly handlers;
|
|
13
|
+
constructor(moduleRef: ModuleRef);
|
|
14
|
+
/**
|
|
15
|
+
* Publish an event to all its consumers
|
|
16
|
+
*
|
|
17
|
+
* Execution flow:
|
|
18
|
+
* 1. Critical consumers run sequentially in order (lower order first)
|
|
19
|
+
* 2. If a critical consumer fails:
|
|
20
|
+
* - Compensations run in reverse order for previously succeeded consumers
|
|
21
|
+
* - Non-critical consumers are NOT dispatched
|
|
22
|
+
* - Original error is thrown after compensations complete
|
|
23
|
+
* 3. If all critical consumers succeed, non-critical consumers are fired in parallel (fire-and-forget)
|
|
24
|
+
*
|
|
25
|
+
* @param event - The event instance
|
|
26
|
+
* @returns Promise with the publish result
|
|
27
|
+
*/
|
|
28
|
+
publish<TEvent extends IEvent>(event: TEvent): Promise<EventPublishResult>;
|
|
29
|
+
/**
|
|
30
|
+
* Run compensations for succeeded consumers in reverse order
|
|
31
|
+
* Continues even if individual compensations fail (logs errors)
|
|
32
|
+
*
|
|
33
|
+
* @param succeededConsumers - Consumers that succeeded and have compensate()
|
|
34
|
+
* @param event - The event to pass to compensate()
|
|
35
|
+
* @returns Number of compensations that were run
|
|
36
|
+
*/
|
|
37
|
+
private runCompensations;
|
|
38
|
+
/**
|
|
39
|
+
* Register an event consumer
|
|
40
|
+
* @param event - The event class
|
|
41
|
+
* @param handler - The consumer class
|
|
42
|
+
* @param criticalityMetadata - Criticality metadata
|
|
43
|
+
*/
|
|
44
|
+
registerEventHandler(event: Type<IEvent>, handler: Type<IEventConsumer<any>>, criticalityMetadata?: EventCriticalityMetadata): void;
|
|
45
|
+
/**
|
|
46
|
+
* Get registered events and their consumers (for debugging)
|
|
47
|
+
*/
|
|
48
|
+
getRegisteredEvents(): {
|
|
49
|
+
event: string;
|
|
50
|
+
handlers: {
|
|
51
|
+
name: string;
|
|
52
|
+
criticality: string;
|
|
53
|
+
order: number;
|
|
54
|
+
}[];
|
|
55
|
+
}[];
|
|
56
|
+
/**
|
|
57
|
+
* Execute a non-critical consumer in the background
|
|
58
|
+
*/
|
|
59
|
+
private executeNonCriticalConsumer;
|
|
60
|
+
}
|
|
61
|
+
//# sourceMappingURL=event.bus.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"event.bus.d.ts","sourceRoot":"","sources":["../../../src/lib/services/event.bus.ts"],"names":[],"mappings":"AAAA,OAAO,EAAsB,IAAI,EAAE,MAAM,gBAAgB,CAAC;AAC1D,OAAO,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC;AACzC,OAAO,EACL,MAAM,EACN,cAAc,EAEd,SAAS,EACT,kBAAkB,EAClB,wBAAwB,EAEzB,MAAM,wBAAwB,CAAC;AAmBhC;;;;GAIG;AACH,qBACa,QAAS,YAAW,SAAS;IAI5B,OAAO,CAAC,QAAQ,CAAC,SAAS;IAHtC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAA0B;IACjD,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAgD;gBAE5C,SAAS,EAAE,SAAS;IAEjD;;;;;;;;;;;;;OAaG;IACG,OAAO,CAAC,MAAM,SAAS,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,kBAAkB,CAAC;IAqFhF;;;;;;;OAOG;YACW,gBAAgB;IA0B9B;;;;;OAKG;IACH,oBAAoB,CAClB,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC,EACnB,OAAO,EAAE,IAAI,CAAC,cAAc,CAAC,GAAG,CAAC,CAAC,EAClC,mBAAmB,CAAC,EAAE,wBAAwB,GAC7C,IAAI;IAkBP;;OAEG;IACH,mBAAmB,IAAI;QACrB,KAAK,EAAE,MAAM,CAAC;QACd,QAAQ,EAAE;YAAE,IAAI,EAAE,MAAM,CAAC;YAAC,WAAW,EAAE,MAAM,CAAC;YAAC,KAAK,EAAE,MAAM,CAAA;SAAE,EAAE,CAAC;KAClE,EAAE;IAWH;;OAEG;IACH,OAAO,CAAC,0BAA0B;CAqBnC"}
|
|
@@ -0,0 +1,176 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
3
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
4
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
5
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
6
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
7
|
+
};
|
|
8
|
+
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
9
|
+
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
10
|
+
};
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
exports.EventBus = void 0;
|
|
13
|
+
const common_1 = require("@nestjs/common");
|
|
14
|
+
const core_1 = require("@nestjs/core");
|
|
15
|
+
const index_js_1 = require("../interfaces/index.js");
|
|
16
|
+
/**
|
|
17
|
+
* Event bus implementation.
|
|
18
|
+
* Publishes events to their consumers with critical/non-critical handling.
|
|
19
|
+
* Supports saga-style compensation for critical consumers.
|
|
20
|
+
*/
|
|
21
|
+
let EventBus = class EventBus {
|
|
22
|
+
constructor(moduleRef) {
|
|
23
|
+
this.moduleRef = moduleRef;
|
|
24
|
+
this.logger = new common_1.Logger('EventBus');
|
|
25
|
+
this.handlers = new Map();
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* Publish an event to all its consumers
|
|
29
|
+
*
|
|
30
|
+
* Execution flow:
|
|
31
|
+
* 1. Critical consumers run sequentially in order (lower order first)
|
|
32
|
+
* 2. If a critical consumer fails:
|
|
33
|
+
* - Compensations run in reverse order for previously succeeded consumers
|
|
34
|
+
* - Non-critical consumers are NOT dispatched
|
|
35
|
+
* - Original error is thrown after compensations complete
|
|
36
|
+
* 3. If all critical consumers succeed, non-critical consumers are fired in parallel (fire-and-forget)
|
|
37
|
+
*
|
|
38
|
+
* @param event - The event instance
|
|
39
|
+
* @returns Promise with the publish result
|
|
40
|
+
*/
|
|
41
|
+
async publish(event) {
|
|
42
|
+
const eventName = event.constructor.name;
|
|
43
|
+
const consumers = this.handlers.get(eventName) || [];
|
|
44
|
+
if (consumers.length === 0) {
|
|
45
|
+
this.logger.log(`No consumers registered for event: ${eventName}`);
|
|
46
|
+
return {
|
|
47
|
+
totalHandlers: 0,
|
|
48
|
+
criticalSucceeded: 0,
|
|
49
|
+
nonCriticalDispatched: 0,
|
|
50
|
+
compensationsRun: 0,
|
|
51
|
+
};
|
|
52
|
+
}
|
|
53
|
+
// Separate critical and non-critical consumers
|
|
54
|
+
const criticalConsumers = consumers
|
|
55
|
+
.filter((h) => h.criticality === index_js_1.EventCriticality.CRITICAL)
|
|
56
|
+
.sort((a, b) => a.order - b.order);
|
|
57
|
+
const nonCriticalConsumers = consumers.filter((h) => h.criticality === index_js_1.EventCriticality.NON_CRITICAL);
|
|
58
|
+
this.logger.log(`Publishing event: ${eventName} to ${criticalConsumers.length} critical and ${nonCriticalConsumers.length} non-critical consumers`);
|
|
59
|
+
// Phase 1: Execute critical consumers sequentially, tracking those with compensate()
|
|
60
|
+
const succeededWithCompensation = [];
|
|
61
|
+
let criticalSucceeded = 0;
|
|
62
|
+
for (const registeredConsumer of criticalConsumers) {
|
|
63
|
+
const consumer = this.moduleRef.get(registeredConsumer.type, { strict: false });
|
|
64
|
+
try {
|
|
65
|
+
await consumer.handle(event);
|
|
66
|
+
criticalSucceeded++;
|
|
67
|
+
this.logger.log(`Critical consumer ${registeredConsumer.type.name} completed successfully`);
|
|
68
|
+
// Track if it has a compensate method for potential rollback
|
|
69
|
+
if (typeof consumer.compensate === 'function') {
|
|
70
|
+
succeededWithCompensation.push({
|
|
71
|
+
consumer,
|
|
72
|
+
name: registeredConsumer.type.name,
|
|
73
|
+
});
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
catch (error) {
|
|
77
|
+
this.logger.error(`Critical consumer ${registeredConsumer.type.name} failed: ${error.message}`);
|
|
78
|
+
// Run compensations for previously succeeded consumers (in reverse order)
|
|
79
|
+
const compensationsRun = await this.runCompensations(succeededWithCompensation, event);
|
|
80
|
+
this.logger.log(`Ran ${compensationsRun} compensations after failure in ${registeredConsumer.type.name}`);
|
|
81
|
+
throw error;
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
// Phase 2: Fire non-critical consumers in parallel (fire-and-forget)
|
|
85
|
+
let nonCriticalDispatched = 0;
|
|
86
|
+
for (const registeredConsumer of nonCriticalConsumers) {
|
|
87
|
+
nonCriticalDispatched++;
|
|
88
|
+
this.executeNonCriticalConsumer(event, registeredConsumer);
|
|
89
|
+
}
|
|
90
|
+
return {
|
|
91
|
+
totalHandlers: consumers.length,
|
|
92
|
+
criticalSucceeded,
|
|
93
|
+
nonCriticalDispatched,
|
|
94
|
+
compensationsRun: 0,
|
|
95
|
+
};
|
|
96
|
+
}
|
|
97
|
+
/**
|
|
98
|
+
* Run compensations for succeeded consumers in reverse order
|
|
99
|
+
* Continues even if individual compensations fail (logs errors)
|
|
100
|
+
*
|
|
101
|
+
* @param succeededConsumers - Consumers that succeeded and have compensate()
|
|
102
|
+
* @param event - The event to pass to compensate()
|
|
103
|
+
* @returns Number of compensations that were run
|
|
104
|
+
*/
|
|
105
|
+
async runCompensations(succeededConsumers, event) {
|
|
106
|
+
let compensationsRun = 0;
|
|
107
|
+
// Run in reverse order (last succeeded -> first succeeded)
|
|
108
|
+
for (const { consumer, name } of succeededConsumers.reverse()) {
|
|
109
|
+
try {
|
|
110
|
+
this.logger.log(`Running compensation for ${name}...`);
|
|
111
|
+
await consumer.compensate(event);
|
|
112
|
+
compensationsRun++;
|
|
113
|
+
this.logger.log(`Compensation for ${name} completed successfully`);
|
|
114
|
+
}
|
|
115
|
+
catch (compError) {
|
|
116
|
+
// Log but continue with other compensations
|
|
117
|
+
this.logger.error(`Compensation for ${name} failed: ${compError.message}. ` +
|
|
118
|
+
`Manual intervention may be required.`);
|
|
119
|
+
compensationsRun++; // Count as run even if failed
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
return compensationsRun;
|
|
123
|
+
}
|
|
124
|
+
/**
|
|
125
|
+
* Register an event consumer
|
|
126
|
+
* @param event - The event class
|
|
127
|
+
* @param handler - The consumer class
|
|
128
|
+
* @param criticalityMetadata - Criticality metadata
|
|
129
|
+
*/
|
|
130
|
+
registerEventHandler(event, handler, criticalityMetadata) {
|
|
131
|
+
const eventName = event.name;
|
|
132
|
+
const consumers = this.handlers.get(eventName) || [];
|
|
133
|
+
const registeredConsumer = {
|
|
134
|
+
type: handler,
|
|
135
|
+
criticality: criticalityMetadata?.criticality ?? index_js_1.EventCriticality.NON_CRITICAL,
|
|
136
|
+
order: criticalityMetadata?.order ?? 0,
|
|
137
|
+
};
|
|
138
|
+
consumers.push(registeredConsumer);
|
|
139
|
+
this.handlers.set(eventName, consumers);
|
|
140
|
+
this.logger.log(`Registered event consumer: ${handler.name} for event: ${eventName} (criticality: ${registeredConsumer.criticality}, order: ${registeredConsumer.order})`);
|
|
141
|
+
}
|
|
142
|
+
/**
|
|
143
|
+
* Get registered events and their consumers (for debugging)
|
|
144
|
+
*/
|
|
145
|
+
getRegisteredEvents() {
|
|
146
|
+
return Array.from(this.handlers.entries()).map(([event, consumers]) => ({
|
|
147
|
+
event,
|
|
148
|
+
handlers: consumers.map((h) => ({
|
|
149
|
+
name: h.type.name,
|
|
150
|
+
criticality: h.criticality,
|
|
151
|
+
order: h.order,
|
|
152
|
+
})),
|
|
153
|
+
}));
|
|
154
|
+
}
|
|
155
|
+
/**
|
|
156
|
+
* Execute a non-critical consumer in the background
|
|
157
|
+
*/
|
|
158
|
+
executeNonCriticalConsumer(event, registeredConsumer) {
|
|
159
|
+
setImmediate(async () => {
|
|
160
|
+
try {
|
|
161
|
+
const consumer = this.moduleRef.get(registeredConsumer.type, { strict: false });
|
|
162
|
+
await consumer.handle(event);
|
|
163
|
+
this.logger.log(`Non-critical consumer ${registeredConsumer.type.name} completed successfully`);
|
|
164
|
+
}
|
|
165
|
+
catch (error) {
|
|
166
|
+
this.logger.warn(`Non-critical consumer ${registeredConsumer.type.name} failed: ${error.message}`);
|
|
167
|
+
}
|
|
168
|
+
});
|
|
169
|
+
}
|
|
170
|
+
};
|
|
171
|
+
exports.EventBus = EventBus;
|
|
172
|
+
exports.EventBus = EventBus = __decorate([
|
|
173
|
+
(0, common_1.Injectable)(),
|
|
174
|
+
__metadata("design:paramtypes", [core_1.ModuleRef])
|
|
175
|
+
], EventBus);
|
|
176
|
+
//# sourceMappingURL=event.bus.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"event.bus.js","sourceRoot":"","sources":["../../../src/lib/services/event.bus.ts"],"names":[],"mappings":";;;;;;;;;;;;AAAA,2CAA0D;AAC1D,uCAAyC;AACzC,qDAQgC;AAmBhC;;;;GAIG;AAEI,IAAM,QAAQ,GAAd,MAAM,QAAQ;IAInB,YAA6B,SAAoB;QAApB,cAAS,GAAT,SAAS,CAAW;QAHhC,WAAM,GAAG,IAAI,eAAM,CAAC,UAAU,CAAC,CAAC;QAChC,aAAQ,GAAG,IAAI,GAAG,EAAqC,CAAC;IAErB,CAAC;IAErD;;;;;;;;;;;;;OAaG;IACH,KAAK,CAAC,OAAO,CAAwB,KAAa;QAChD,MAAM,SAAS,GAAG,KAAK,CAAC,WAAW,CAAC,IAAI,CAAC;QACzC,MAAM,SAAS,GAAG,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,SAAS,CAAC,IAAI,EAAE,CAAC;QAErD,IAAI,SAAS,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC3B,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,sCAAsC,SAAS,EAAE,CAAC,CAAC;YACnE,OAAO;gBACL,aAAa,EAAE,CAAC;gBAChB,iBAAiB,EAAE,CAAC;gBACpB,qBAAqB,EAAE,CAAC;gBACxB,gBAAgB,EAAE,CAAC;aACpB,CAAC;QACJ,CAAC;QAED,+CAA+C;QAC/C,MAAM,iBAAiB,GAAG,SAAS;aAChC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,WAAW,KAAK,2BAAgB,CAAC,QAAQ,CAAC;aAC1D,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC,KAAK,CAAC,CAAC;QAErC,MAAM,oBAAoB,GAAG,SAAS,CAAC,MAAM,CAC3C,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,WAAW,KAAK,2BAAgB,CAAC,YAAY,CACvD,CAAC;QAEF,IAAI,CAAC,MAAM,CAAC,GAAG,CACb,qBAAqB,SAAS,OAAO,iBAAiB,CAAC,MAAM,iBAAiB,oBAAoB,CAAC,MAAM,yBAAyB,CACnI,CAAC;QAEF,qFAAqF;QACrF,MAAM,yBAAyB,GAAoC,EAAE,CAAC;QACtE,IAAI,iBAAiB,GAAG,CAAC,CAAC;QAE1B,KAAK,MAAM,kBAAkB,IAAI,iBAAiB,EAAE,CAAC;YACnD,MAAM,QAAQ,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CACjC,kBAAkB,CAAC,IAAI,EACvB,EAAE,MAAM,EAAE,KAAK,EAAE,CAClB,CAAC;YAEF,IAAI,CAAC;gBACH,MAAM,QAAQ,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;gBAC7B,iBAAiB,EAAE,CAAC;gBACpB,IAAI,CAAC,MAAM,CAAC,GAAG,CACb,qBAAqB,kBAAkB,CAAC,IAAI,CAAC,IAAI,yBAAyB,CAC3E,CAAC;gBAEF,6DAA6D;gBAC7D,IAAI,OAAO,QAAQ,CAAC,UAAU,KAAK,UAAU,EAAE,CAAC;oBAC9C,yBAAyB,CAAC,IAAI,CAAC;wBAC7B,QAAQ;wBACR,IAAI,EAAE,kBAAkB,CAAC,IAAI,CAAC,IAAI;qBACnC,CAAC,CAAC;gBACL,CAAC;YACH,CAAC;YAAC,OAAO,KAAK,EAAE,CAAC;gBACf,IAAI,CAAC,MAAM,CAAC,KAAK,CACf,qBAAqB,kBAAkB,CAAC,IAAI,CAAC,IAAI,YAAa,KAAe,CAAC,OAAO,EAAE,CACxF,CAAC;gBAEF,0EAA0E;gBAC1E,MAAM,gBAAgB,GAAG,MAAM,IAAI,CAAC,gBAAgB,CAClD,yBAAyB,EACzB,KAAK,CACN,CAAC;gBAEF,IAAI,CAAC,MAAM,CAAC,GAAG,CACb,OAAO,gBAAgB,mCAAmC,kBAAkB,CAAC,IAAI,CAAC,IAAI,EAAE,CACzF,CAAC;gBAEF,MAAM,KAAK,CAAC;YACd,CAAC;QACH,CAAC;QAED,qEAAqE;QACrE,IAAI,qBAAqB,GAAG,CAAC,CAAC;QAC9B,KAAK,MAAM,kBAAkB,IAAI,oBAAoB,EAAE,CAAC;YACtD,qBAAqB,EAAE,CAAC;YACxB,IAAI,CAAC,0BAA0B,CAAC,KAAK,EAAE,kBAAkB,CAAC,CAAC;QAC7D,CAAC;QAED,OAAO;YACL,aAAa,EAAE,SAAS,CAAC,MAAM;YAC/B,iBAAiB;YACjB,qBAAqB;YACrB,gBAAgB,EAAE,CAAC;SACpB,CAAC;IACJ,CAAC;IAED;;;;;;;OAOG;IACK,KAAK,CAAC,gBAAgB,CAC5B,kBAAmD,EACnD,KAAa;QAEb,IAAI,gBAAgB,GAAG,CAAC,CAAC;QAEzB,2DAA2D;QAC3D,KAAK,MAAM,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,kBAAkB,CAAC,OAAO,EAAE,EAAE,CAAC;YAC9D,IAAI,CAAC;gBACH,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,4BAA4B,IAAI,KAAK,CAAC,CAAC;gBACvD,MAAM,QAAQ,CAAC,UAAW,CAAC,KAAK,CAAC,CAAC;gBAClC,gBAAgB,EAAE,CAAC;gBACnB,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,oBAAoB,IAAI,yBAAyB,CAAC,CAAC;YACrE,CAAC;YAAC,OAAO,SAAS,EAAE,CAAC;gBACnB,4CAA4C;gBAC5C,IAAI,CAAC,MAAM,CAAC,KAAK,CACf,oBAAoB,IAAI,YAAa,SAAmB,CAAC,OAAO,IAAI;oBAClE,sCAAsC,CACzC,CAAC;gBACF,gBAAgB,EAAE,CAAC,CAAC,8BAA8B;YACpD,CAAC;QACH,CAAC;QAED,OAAO,gBAAgB,CAAC;IAC1B,CAAC;IAED;;;;;OAKG;IACH,oBAAoB,CAClB,KAAmB,EACnB,OAAkC,EAClC,mBAA8C;QAE9C,MAAM,SAAS,GAAG,KAAK,CAAC,IAAI,CAAC;QAC7B,MAAM,SAAS,GAAG,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,SAAS,CAAC,IAAI,EAAE,CAAC;QAErD,MAAM,kBAAkB,GAA4B;YAClD,IAAI,EAAE,OAAO;YACb,WAAW,EAAE,mBAAmB,EAAE,WAAW,IAAI,2BAAgB,CAAC,YAAY;YAC9E,KAAK,EAAE,mBAAmB,EAAE,KAAK,IAAI,CAAC;SACvC,CAAC;QAEF,SAAS,CAAC,IAAI,CAAC,kBAAkB,CAAC,CAAC;QACnC,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,SAAS,EAAE,SAAS,CAAC,CAAC;QAExC,IAAI,CAAC,MAAM,CAAC,GAAG,CACb,8BAA8B,OAAO,CAAC,IAAI,eAAe,SAAS,kBAAkB,kBAAkB,CAAC,WAAW,YAAY,kBAAkB,CAAC,KAAK,GAAG,CAC1J,CAAC;IACJ,CAAC;IAED;;OAEG;IACH,mBAAmB;QAIjB,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,OAAO,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,KAAK,EAAE,SAAS,CAAC,EAAE,EAAE,CAAC,CAAC;YACtE,KAAK;YACL,QAAQ,EAAE,SAAS,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;gBAC9B,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI;gBACjB,WAAW,EAAE,CAAC,CAAC,WAAW;gBAC1B,KAAK,EAAE,CAAC,CAAC,KAAK;aACf,CAAC,CAAC;SACJ,CAAC,CAAC,CAAC;IACN,CAAC;IAED;;OAEG;IACK,0BAA0B,CAChC,KAAa,EACb,kBAA2C;QAE3C,YAAY,CAAC,KAAK,IAAI,EAAE;YACtB,IAAI,CAAC;gBACH,MAAM,QAAQ,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CACjC,kBAAkB,CAAC,IAAI,EACvB,EAAE,MAAM,EAAE,KAAK,EAAE,CAClB,CAAC;gBACF,MAAM,QAAQ,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;gBAC7B,IAAI,CAAC,MAAM,CAAC,GAAG,CACb,yBAAyB,kBAAkB,CAAC,IAAI,CAAC,IAAI,yBAAyB,CAC/E,CAAC;YACJ,CAAC;YAAC,OAAO,KAAK,EAAE,CAAC;gBACf,IAAI,CAAC,MAAM,CAAC,IAAI,CACd,yBAAyB,kBAAkB,CAAC,IAAI,CAAC,IAAI,YAAa,KAAe,CAAC,OAAO,EAAE,CAC5F,CAAC;YACJ,CAAC;QACH,CAAC,CAAC,CAAC;IACL,CAAC;CACF,CAAA;AAhNY,4BAAQ;mBAAR,QAAQ;IADpB,IAAA,mBAAU,GAAE;qCAK6B,gBAAS;GAJtC,QAAQ,CAgNpB"}
|