@nestjs-transactional/outbox 1.0.0-alpha.5 → 1.1.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 +174 -335
- package/dist/api/failed-event-publications.js.map +1 -1
- package/dist/api/incomplete-event-publications.js +1 -2
- package/dist/api/incomplete-event-publications.js.map +1 -1
- package/dist/decorators/outbox-events-handler.decorator.d.ts +1 -1
- package/dist/decorators/outbox-events-handler.decorator.js.map +1 -1
- package/dist/dispatcher/data-source-outbox-publisher.d.ts +2 -3
- package/dist/dispatcher/data-source-outbox-publisher.js +2 -3
- package/dist/dispatcher/data-source-outbox-publisher.js.map +1 -1
- package/dist/dispatcher/event-publication-processor.d.ts +19 -2
- package/dist/dispatcher/event-publication-processor.js +40 -3
- package/dist/dispatcher/event-publication-processor.js.map +1 -1
- package/dist/dispatcher/outbox-event-publisher.d.ts +1 -1
- package/dist/dispatcher/outbox-event-publisher.js +2 -2
- package/dist/dispatcher/outbox-event-publisher.js.map +1 -1
- package/dist/dispatcher/processor-options.d.ts +13 -1
- package/dist/dispatcher/processor-options.js +4 -1
- package/dist/dispatcher/processor-options.js.map +1 -1
- package/dist/externalization/describe-thrown.d.ts +20 -0
- package/dist/externalization/describe-thrown.js +49 -0
- package/dist/externalization/describe-thrown.js.map +1 -0
- package/dist/externalization/event-externalizer.d.ts +2 -2
- package/dist/externalization/externalization-registry.js.map +1 -1
- package/dist/externalization/externalized.decorator.d.ts +3 -4
- package/dist/externalization/externalized.decorator.js +2 -3
- package/dist/externalization/externalized.decorator.js.map +1 -1
- package/dist/externalization/types.d.ts +2 -2
- package/dist/index.d.ts +6 -0
- package/dist/index.js +11 -1
- package/dist/index.js.map +1 -1
- package/dist/module/outbox-processing.module.d.ts +18 -2
- package/dist/module/outbox-processing.module.js +33 -7
- package/dist/module/outbox-processing.module.js.map +1 -1
- package/dist/module/outbox.module.d.ts +15 -0
- package/dist/module/outbox.module.js +99 -8
- package/dist/module/outbox.module.js.map +1 -1
- package/dist/recovery/outbox-cleanup-scheduler.d.ts +56 -0
- package/dist/recovery/outbox-cleanup-scheduler.js +139 -0
- package/dist/recovery/outbox-cleanup-scheduler.js.map +1 -0
- package/dist/recovery/outbox-retry-scheduler.d.ts +68 -0
- package/dist/recovery/outbox-retry-scheduler.js +163 -0
- package/dist/recovery/outbox-retry-scheduler.js.map +1 -0
- package/dist/recovery/staleness-monitor.d.ts +10 -2
- package/dist/recovery/staleness-monitor.js +28 -3
- package/dist/recovery/staleness-monitor.js.map +1 -1
- package/dist/registry/event-publication-registry.d.ts +1 -1
- package/dist/registry/event-publication-registry.js +1 -1
- package/dist/registry/event-publication-registry.js.map +1 -1
- package/dist/registry/listener-registry.d.ts +2 -2
- package/dist/registry/listener-registry.js +2 -2
- package/dist/registry/multi-ds-listener-registrar.d.ts +10 -4
- package/dist/registry/multi-ds-listener-registrar.js +1 -1
- package/dist/registry/multi-ds-listener-registrar.js.map +1 -1
- package/dist/registry/outbox-listener-scanner.d.ts +1 -1
- package/dist/registry/outbox-listener-scanner.js +1 -1
- package/dist/registry/outbox-listener-scanner.js.map +1 -1
- package/dist/repository/event-publication-repository.d.ts +37 -6
- package/dist/repository/event-publication-repository.js.map +1 -1
- package/dist/serialization/event-type-resolver.d.ts +1 -1
- package/dist/serialization/event-type-resolver.js +1 -1
- package/dist/serialization/json-event-serializer.js.map +1 -1
- package/dist/shutdown/drain.d.ts +32 -0
- package/dist/shutdown/drain.js +56 -0
- package/dist/shutdown/drain.js.map +1 -0
- package/dist/testing/in-memory-repository.js +11 -2
- package/dist/testing/in-memory-repository.js.map +1 -1
- package/dist/testing/published-events.js +6 -2
- package/dist/testing/published-events.js.map +1 -1
- package/dist/tokens/token-utils.js.map +1 -1
- package/dist/types/cleanup-config.d.ts +59 -0
- package/dist/types/cleanup-config.js +17 -0
- package/dist/types/cleanup-config.js.map +1 -0
- package/dist/types/resubmission-options.d.ts +0 -4
- package/dist/types/resubmission-options.js +0 -9
- package/dist/types/resubmission-options.js.map +1 -1
- package/dist/types/retry-config.d.ts +51 -0
- package/dist/types/retry-config.js +16 -0
- package/dist/types/retry-config.js.map +1 -0
- package/dist/types/staleness-config.d.ts +8 -0
- package/dist/types/staleness-config.js +2 -0
- package/dist/types/staleness-config.js.map +1 -1
- package/package.json +25 -13
|
@@ -4,7 +4,7 @@ exports.DataSourceOutboxPublisher = void 0;
|
|
|
4
4
|
const common_1 = require("@nestjs/common");
|
|
5
5
|
const core_1 = require("@nestjs-transactional/core");
|
|
6
6
|
/**
|
|
7
|
-
* Per-dataSource publisher
|
|
7
|
+
* Per-dataSource publisher. Owns the per-transaction
|
|
8
8
|
* buffer, lifecycle hook registration, and delegate calls into the
|
|
9
9
|
* `EventPublicationRegistry` bound to a single dataSource.
|
|
10
10
|
*
|
|
@@ -85,8 +85,7 @@ class DataSourceOutboxPublisher {
|
|
|
85
85
|
* — `transactionManager.registerBeforeCommit` is NOT used because it
|
|
86
86
|
* always targets "the first active transaction on the context",
|
|
87
87
|
* which is the wrong target when multiple dataSources have live
|
|
88
|
-
* transactions in the same async stack
|
|
89
|
-
* simultaneous scenario).
|
|
88
|
+
* transactions in the same async stack.
|
|
90
89
|
*/
|
|
91
90
|
scheduleForPublication(event) {
|
|
92
91
|
const tx = core_1.TransactionContext.getActiveTransactionByDataSource(this.dataSource);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"data-source-outbox-publisher.js","sourceRoot":"","sources":["../../src/dispatcher/data-source-outbox-publisher.ts"],"names":[],"mappings":";;;AAAA,2CAAwC;AACxC,qDAIoC;AAKpC;;;;;;;;;;;;;;;;GAgBG;AACH,MAAa,yBAAyB;IAiBzB;IACQ;IACA;IAlBF,MAAM,CAAS;IAEhC,gEAAgE;IAChE,gEAAgE;IAChE,4DAA4D;IAC5D,6BAA6B;IACZ,OAAO,GAAG,IAAI,OAAO,EAAgC,CAAC;IAEvE;;;;;;OAMG;IACH,YACW,UAAkB,EACV,QAAkC,EAClC,gBAAwC;QAFhD,eAAU,GAAV,UAAU,CAAQ;QACV,aAAQ,GAAR,QAAQ,CAA0B;QAClC,qBAAgB,GAAhB,gBAAgB,CAAwB;QAEzD,IAAI,CAAC,MAAM,GAAG,IAAI,eAAM,CAAC,6BAA6B,UAAU,GAAG,CAAC,CAAC;IACvE,CAAC;IAED;;;;;;;;;;;OAWG;IACH,KAAK,CAAC,OAAO,CAAC,KAAc;QAC1B,IAAI,CAAC,uBAAuB,EAAE,CAAC;QAE/B,MAAM,SAAS,GAAI,KAAgB,CAAC,WAAW,CAAC,IAAI,CAAC;QACrD,MAAM,SAAS,GAAG,IAAI,CAAC,gBAAgB,CAAC,cAAc,CAAC,SAAS,CAAC,CAAC;QAElE,IAAI,SAAS,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC3B,OAAO;QACT,CAAC;QAED,MAAM,WAAW,GAAG,SAAS,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;QAC/C,MAAM,IAAI,CAAC,QAAQ,CAAC,OAAO,CAAC,KAAK,EAAE,WAAW,CAAC,CAAC;IAClD,CAAC;IAED;;;OAGG;IACH,KAAK,CAAC,UAAU,CAAC,MAA0B;QACzC,KAAK,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;YAC3B,MAAM,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;QAC5B,CAAC;IACH,CAAC;IAED
|
|
1
|
+
{"version":3,"file":"data-source-outbox-publisher.js","sourceRoot":"","sources":["../../src/dispatcher/data-source-outbox-publisher.ts"],"names":[],"mappings":"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"}
|
|
@@ -30,11 +30,28 @@ export declare class EventPublicationProcessor {
|
|
|
30
30
|
private readonly logger;
|
|
31
31
|
private running;
|
|
32
32
|
private processingLoop;
|
|
33
|
+
/**
|
|
34
|
+
* The batch currently being processed, or `null` when the worker is
|
|
35
|
+
* idle. Tracked so {@link stop} can drain it instead of leaving it
|
|
36
|
+
* running against providers NestJS is already tearing down.
|
|
37
|
+
*/
|
|
38
|
+
private inFlightBatch;
|
|
33
39
|
constructor(registry: EventPublicationRegistry, listenerRegistry: OutboxListenerRegistry, options: EventPublicationProcessorOptions, externalizer?: EventExternalizer | undefined, externalizationRegistry?: ExternalizationRegistry | undefined);
|
|
34
40
|
/** Start the periodic polling loop. Idempotent. */
|
|
35
41
|
start(): void;
|
|
36
|
-
/**
|
|
37
|
-
|
|
42
|
+
/**
|
|
43
|
+
* Stop the polling loop and drain the batch already in flight.
|
|
44
|
+
*
|
|
45
|
+
* Resolves once no batch is running, or once
|
|
46
|
+
* `options.shutdownTimeout` elapses — whichever comes first. A
|
|
47
|
+
* publication abandoned at the deadline stays in `PROCESSING` and is
|
|
48
|
+
* recovered by the staleness monitor on a later boot; blocking
|
|
49
|
+
* shutdown indefinitely on a stuck listener would be worse.
|
|
50
|
+
*
|
|
51
|
+
* Idempotent, and safe to call while a drain from an earlier call is
|
|
52
|
+
* still in progress. Never rejects.
|
|
53
|
+
*/
|
|
54
|
+
stop(): Promise<void>;
|
|
38
55
|
/**
|
|
39
56
|
* Process a single batch of pending publications. Safe to call
|
|
40
57
|
* directly from tests and one-shot tooling; `start()` triggers it
|
|
@@ -20,6 +20,7 @@ const event_externalizer_1 = require("../externalization/event-externalizer");
|
|
|
20
20
|
const externalization_registry_1 = require("../externalization/externalization-registry");
|
|
21
21
|
const event_publication_registry_1 = require("../registry/event-publication-registry");
|
|
22
22
|
const listener_registry_1 = require("../registry/listener-registry");
|
|
23
|
+
const drain_1 = require("../shutdown/drain");
|
|
23
24
|
/**
|
|
24
25
|
* Async worker that drains the event publication queue:
|
|
25
26
|
*
|
|
@@ -47,6 +48,12 @@ let EventPublicationProcessor = EventPublicationProcessor_1 = class EventPublica
|
|
|
47
48
|
logger = new common_1.Logger(EventPublicationProcessor_1.name);
|
|
48
49
|
running = false;
|
|
49
50
|
processingLoop = null;
|
|
51
|
+
/**
|
|
52
|
+
* The batch currently being processed, or `null` when the worker is
|
|
53
|
+
* idle. Tracked so {@link stop} can drain it instead of leaving it
|
|
54
|
+
* running against providers NestJS is already tearing down.
|
|
55
|
+
*/
|
|
56
|
+
inFlightBatch = null;
|
|
50
57
|
constructor(registry, listenerRegistry, options, externalizer, externalizationRegistry) {
|
|
51
58
|
this.registry = registry;
|
|
52
59
|
this.listenerRegistry = listenerRegistry;
|
|
@@ -63,13 +70,33 @@ let EventPublicationProcessor = EventPublicationProcessor_1 = class EventPublica
|
|
|
63
70
|
this.scheduleNext();
|
|
64
71
|
this.logger.log('EventPublicationProcessor started');
|
|
65
72
|
}
|
|
66
|
-
/**
|
|
67
|
-
|
|
73
|
+
/**
|
|
74
|
+
* Stop the polling loop and drain the batch already in flight.
|
|
75
|
+
*
|
|
76
|
+
* Resolves once no batch is running, or once
|
|
77
|
+
* `options.shutdownTimeout` elapses — whichever comes first. A
|
|
78
|
+
* publication abandoned at the deadline stays in `PROCESSING` and is
|
|
79
|
+
* recovered by the staleness monitor on a later boot; blocking
|
|
80
|
+
* shutdown indefinitely on a stuck listener would be worse.
|
|
81
|
+
*
|
|
82
|
+
* Idempotent, and safe to call while a drain from an earlier call is
|
|
83
|
+
* still in progress. Never rejects.
|
|
84
|
+
*/
|
|
85
|
+
async stop() {
|
|
68
86
|
this.running = false;
|
|
69
87
|
if (this.processingLoop !== null) {
|
|
70
88
|
clearTimeout(this.processingLoop);
|
|
71
89
|
this.processingLoop = null;
|
|
72
90
|
}
|
|
91
|
+
const inFlight = this.inFlightBatch;
|
|
92
|
+
if (inFlight !== null) {
|
|
93
|
+
const drained = await (0, drain_1.drainWithTimeout)(inFlight, this.options.shutdownTimeout);
|
|
94
|
+
if (!drained) {
|
|
95
|
+
this.logger.warn(`EventPublicationProcessor drain timed out after ${this.options.shutdownTimeout}ms — ` +
|
|
96
|
+
'the in-flight batch was abandoned. Publications left in PROCESSING ' +
|
|
97
|
+
'will be recovered by the staleness monitor.');
|
|
98
|
+
}
|
|
99
|
+
}
|
|
73
100
|
this.logger.log('EventPublicationProcessor stopped');
|
|
74
101
|
}
|
|
75
102
|
/**
|
|
@@ -101,7 +128,17 @@ let EventPublicationProcessor = EventPublicationProcessor_1 = class EventPublica
|
|
|
101
128
|
return;
|
|
102
129
|
}
|
|
103
130
|
this.processingLoop = setTimeout(() => {
|
|
104
|
-
|
|
131
|
+
this.processingLoop = null;
|
|
132
|
+
const batch = this.processBatch();
|
|
133
|
+
this.inFlightBatch = batch;
|
|
134
|
+
void batch.finally(() => {
|
|
135
|
+
// Guard against clearing a newer batch's handle: `stop()` may
|
|
136
|
+
// have already replaced or read it.
|
|
137
|
+
if (this.inFlightBatch === batch) {
|
|
138
|
+
this.inFlightBatch = null;
|
|
139
|
+
}
|
|
140
|
+
this.scheduleNext();
|
|
141
|
+
});
|
|
105
142
|
}, this.options.pollingInterval);
|
|
106
143
|
}
|
|
107
144
|
async processOne(publication) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"event-publication-processor.js","sourceRoot":"","sources":["../../src/dispatcher/event-publication-processor.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,2CAAsE;AAEtE,sDAAiE;AACjE,
|
|
1
|
+
{"version":3,"file":"event-publication-processor.js","sourceRoot":"","sources":["../../src/dispatcher/event-publication-processor.ts"],"names":[],"mappings":"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"}
|
|
@@ -32,7 +32,7 @@ export interface OutboxPublishOptions {
|
|
|
32
32
|
*
|
|
33
33
|
* **Cross-dataSource publishing** is allowed: the routing decision is
|
|
34
34
|
* about the event's *registered* dataSource, NOT about which
|
|
35
|
-
* transactions are currently active. With
|
|
35
|
+
* transactions are currently active. With cross-DS
|
|
36
36
|
* simultaneous transactions, a billing event published from inside an
|
|
37
37
|
* outer-billing / inner-inventory async stack still routes to billing
|
|
38
38
|
* (because that's where the event class is registered) and validates
|
|
@@ -34,7 +34,7 @@ const errors_1 = require("../types/errors");
|
|
|
34
34
|
*
|
|
35
35
|
* **Cross-dataSource publishing** is allowed: the routing decision is
|
|
36
36
|
* about the event's *registered* dataSource, NOT about which
|
|
37
|
-
* transactions are currently active. With
|
|
37
|
+
* transactions are currently active. With cross-DS
|
|
38
38
|
* simultaneous transactions, a billing event published from inside an
|
|
39
39
|
* outer-billing / inner-inventory async stack still routes to billing
|
|
40
40
|
* (because that's where the event class is registered) and validates
|
|
@@ -147,7 +147,7 @@ let OutboxEventPublisher = OutboxEventPublisher_1 = class OutboxEventPublisher {
|
|
|
147
147
|
if (options.dataSource !== undefined) {
|
|
148
148
|
return options.dataSource;
|
|
149
149
|
}
|
|
150
|
-
//
|
|
150
|
+
// same helper used by `OutboxListenerScanner` and
|
|
151
151
|
// `MultiDsOutboxListenerRegistrar` so the routing policy (one
|
|
152
152
|
// owning DS per event class, throw on 0 or many matches) stays
|
|
153
153
|
// consistent across publish and listener-registration paths.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"outbox-event-publisher.js","sourceRoot":"","sources":["../../src/dispatcher/outbox-event-publisher.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,2CAA+E;AAC/E,uCAAyC;AAGzC,8EAAwF;AACxF,
|
|
1
|
+
{"version":3,"file":"outbox-event-publisher.js","sourceRoot":"","sources":["../../src/dispatcher/outbox-event-publisher.ts"],"names":[],"mappings":"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"}
|
|
@@ -15,10 +15,22 @@ export interface EventPublicationProcessorOptions {
|
|
|
15
15
|
readonly maxConcurrent: number;
|
|
16
16
|
/** How a successfully-delivered publication is finalized. */
|
|
17
17
|
readonly completionMode: CompletionMode;
|
|
18
|
+
/**
|
|
19
|
+
* How long (ms) `stop()` waits for an in-flight batch to finish
|
|
20
|
+
* before abandoning it. Set it below the platform's shutdown grace
|
|
21
|
+
* period so the rest of the teardown still has room.
|
|
22
|
+
*
|
|
23
|
+
* A publication abandoned mid-flight stays in `PROCESSING` and is
|
|
24
|
+
* recovered by the staleness monitor on a later boot, so this is a
|
|
25
|
+
* latency/consistency trade-off rather than a data-loss one. `0`
|
|
26
|
+
* disables the wait entirely.
|
|
27
|
+
*/
|
|
28
|
+
readonly shutdownTimeout: number;
|
|
18
29
|
}
|
|
19
30
|
/**
|
|
20
31
|
* Reasonable defaults for local development — a 1-second poll, 100 rows
|
|
21
|
-
* per batch, 10 parallel listener invocations,
|
|
32
|
+
* per batch, 10 parallel listener invocations, `UPDATE` completion, and
|
|
33
|
+
* a 10-second shutdown drain.
|
|
22
34
|
*/
|
|
23
35
|
export declare const DEFAULT_PROCESSOR_OPTIONS: EventPublicationProcessorOptions;
|
|
24
36
|
//# sourceMappingURL=processor-options.d.ts.map
|
|
@@ -1,15 +1,18 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.DEFAULT_PROCESSOR_OPTIONS = void 0;
|
|
4
|
+
const drain_1 = require("../shutdown/drain");
|
|
4
5
|
const completion_mode_1 = require("../types/completion-mode");
|
|
5
6
|
/**
|
|
6
7
|
* Reasonable defaults for local development — a 1-second poll, 100 rows
|
|
7
|
-
* per batch, 10 parallel listener invocations,
|
|
8
|
+
* per batch, 10 parallel listener invocations, `UPDATE` completion, and
|
|
9
|
+
* a 10-second shutdown drain.
|
|
8
10
|
*/
|
|
9
11
|
exports.DEFAULT_PROCESSOR_OPTIONS = {
|
|
10
12
|
pollingInterval: 1000,
|
|
11
13
|
batchSize: 100,
|
|
12
14
|
maxConcurrent: 10,
|
|
13
15
|
completionMode: completion_mode_1.CompletionMode.UPDATE,
|
|
16
|
+
shutdownTimeout: drain_1.DEFAULT_DRAIN_TIMEOUT_MS,
|
|
14
17
|
};
|
|
15
18
|
//# sourceMappingURL=processor-options.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"processor-options.js","sourceRoot":"","sources":["../../src/dispatcher/processor-options.ts"],"names":[],"mappings":";;;AAAA,8DAA0D;
|
|
1
|
+
{"version":3,"file":"processor-options.js","sourceRoot":"","sources":["../../src/dispatcher/processor-options.ts"],"names":[],"mappings":";;;AAAA,6CAA6D;AAC7D,8DAA0D;AA+B1D;;;;GAIG;AACU,QAAA,yBAAyB,GAAqC;IACzE,eAAe,EAAE,IAAI;IACrB,SAAS,EAAE,GAAG;IACd,aAAa,EAAE,EAAE;IACjB,cAAc,EAAE,gCAAc,CAAC,MAAM;IACrC,eAAe,EAAE,gCAAwB;CAC1C,CAAC"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Render an unknown thrown value as something an operator can read.
|
|
3
|
+
*
|
|
4
|
+
* `String(err)` is the obvious thing to reach for and it is wrong here.
|
|
5
|
+
* Broker clients reject with values that are not `Error` instances, and
|
|
6
|
+
* `String()` turns those into `[object Object]`. Measured against the
|
|
7
|
+
* current libraries: `@nestjs/microservices` rejects a RabbitMQ publish
|
|
8
|
+
* with a plain object carrying no `message`, and rejects a publish to a
|
|
9
|
+
* stopped broker with a bare string. Both end up as the failure reason
|
|
10
|
+
* recorded on a `FAILED` publication, which is precisely the field an
|
|
11
|
+
* operator reads when deciding whether to resubmit.
|
|
12
|
+
*
|
|
13
|
+
* The order below is "most specific thing that carries meaning first":
|
|
14
|
+
* an `Error`'s message, a string as itself, any object exposing a
|
|
15
|
+
* string `message`, then a JSON rendering, and only then the
|
|
16
|
+
* `[object Object]` of last resort for something with a throwing or
|
|
17
|
+
* circular shape.
|
|
18
|
+
*/
|
|
19
|
+
export declare function describeThrown(err: unknown): string;
|
|
20
|
+
//# sourceMappingURL=describe-thrown.d.ts.map
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.describeThrown = describeThrown;
|
|
4
|
+
/**
|
|
5
|
+
* Render an unknown thrown value as something an operator can read.
|
|
6
|
+
*
|
|
7
|
+
* `String(err)` is the obvious thing to reach for and it is wrong here.
|
|
8
|
+
* Broker clients reject with values that are not `Error` instances, and
|
|
9
|
+
* `String()` turns those into `[object Object]`. Measured against the
|
|
10
|
+
* current libraries: `@nestjs/microservices` rejects a RabbitMQ publish
|
|
11
|
+
* with a plain object carrying no `message`, and rejects a publish to a
|
|
12
|
+
* stopped broker with a bare string. Both end up as the failure reason
|
|
13
|
+
* recorded on a `FAILED` publication, which is precisely the field an
|
|
14
|
+
* operator reads when deciding whether to resubmit.
|
|
15
|
+
*
|
|
16
|
+
* The order below is "most specific thing that carries meaning first":
|
|
17
|
+
* an `Error`'s message, a string as itself, any object exposing a
|
|
18
|
+
* string `message`, then a JSON rendering, and only then the
|
|
19
|
+
* `[object Object]` of last resort for something with a throwing or
|
|
20
|
+
* circular shape.
|
|
21
|
+
*/
|
|
22
|
+
function describeThrown(err) {
|
|
23
|
+
if (err instanceof Error) {
|
|
24
|
+
return err.message;
|
|
25
|
+
}
|
|
26
|
+
if (typeof err === 'string') {
|
|
27
|
+
return err;
|
|
28
|
+
}
|
|
29
|
+
if (typeof err === 'object' && err !== null) {
|
|
30
|
+
const message = err.message;
|
|
31
|
+
if (typeof message === 'string' && message.length > 0) {
|
|
32
|
+
return message;
|
|
33
|
+
}
|
|
34
|
+
try {
|
|
35
|
+
const json = JSON.stringify(err);
|
|
36
|
+
// `JSON.stringify` returns `undefined` for a value it cannot
|
|
37
|
+
// represent, and `{}` for an object whose own properties are all
|
|
38
|
+
// non-enumerable, neither of which tells anyone anything.
|
|
39
|
+
if (json !== undefined && json !== '{}') {
|
|
40
|
+
return json;
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
catch {
|
|
44
|
+
// Circular, or a throwing `toJSON`. Fall through.
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
return String(err);
|
|
48
|
+
}
|
|
49
|
+
//# sourceMappingURL=describe-thrown.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"describe-thrown.js","sourceRoot":"","sources":["../../src/externalization/describe-thrown.ts"],"names":[],"mappings":";;AAkBA,wCAyBC;AA3CD;;;;;;;;;;;;;;;;;GAiBG;AACH,SAAgB,cAAc,CAAC,GAAY;IACzC,IAAI,GAAG,YAAY,KAAK,EAAE,CAAC;QACzB,OAAO,GAAG,CAAC,OAAO,CAAC;IACrB,CAAC;IACD,IAAI,OAAO,GAAG,KAAK,QAAQ,EAAE,CAAC;QAC5B,OAAO,GAAG,CAAC;IACb,CAAC;IACD,IAAI,OAAO,GAAG,KAAK,QAAQ,IAAI,GAAG,KAAK,IAAI,EAAE,CAAC;QAC5C,MAAM,OAAO,GAAI,GAA6B,CAAC,OAAO,CAAC;QACvD,IAAI,OAAO,OAAO,KAAK,QAAQ,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACtD,OAAO,OAAO,CAAC;QACjB,CAAC;QACD,IAAI,CAAC;YACH,MAAM,IAAI,GAAG,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC;YACjC,6DAA6D;YAC7D,iEAAiE;YACjE,0DAA0D;YAC1D,IAAI,IAAI,KAAK,SAAS,IAAI,IAAI,KAAK,IAAI,EAAE,CAAC;gBACxC,OAAO,IAAI,CAAC;YACd,CAAC;QACH,CAAC;QAAC,MAAM,CAAC;YACP,kDAAkD;QACpD,CAAC;IACH,CAAC;IACD,OAAO,MAAM,CAAC,GAAG,CAAC,CAAC;AACrB,CAAC"}
|
|
@@ -4,7 +4,7 @@ import type { ExternalizationMetadata } from './types';
|
|
|
4
4
|
* external message broker.
|
|
5
5
|
*
|
|
6
6
|
* Implementations are provided by extension packages — primarily
|
|
7
|
-
* `@nestjs-transactional/outbox-microservices
|
|
7
|
+
* `@nestjs-transactional/outbox-microservices`, which
|
|
8
8
|
* delegates to `@nestjs/microservices` `ClientProxy` and therefore
|
|
9
9
|
* covers every transport that NestJS already supports (Kafka,
|
|
10
10
|
* RabbitMQ, NATS, JMS, gRPC, custom). Future native (broker-specific)
|
|
@@ -32,7 +32,7 @@ export interface EventExternalizer {
|
|
|
32
32
|
* was passed to the local listener).
|
|
33
33
|
* @param metadata Resolved routing metadata for this event. The
|
|
34
34
|
* processor obtains it from the `ExternalizationRegistry`
|
|
35
|
-
*
|
|
35
|
+
* .
|
|
36
36
|
*/
|
|
37
37
|
externalize(event: unknown, metadata: ExternalizationMetadata): Promise<void>;
|
|
38
38
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"externalization-registry.js","sourceRoot":"","sources":["../../src/externalization/externalization-registry.ts"],"names":[],"mappings":";;;;;;;;;;;;;AAAA,2CAAuE;AAEvE,8EAAyE;AAEzE,
|
|
1
|
+
{"version":3,"file":"externalization-registry.js","sourceRoot":"","sources":["../../src/externalization/externalization-registry.ts"],"names":[],"mappings":";;;;;;;;;;;;;AAAA,2CAAuE;AAEvE,8EAAyE;AAEzE,qEAA8F;AAG9F;;;;;;;;;;;;;;;;;;;;;GAqBG;AAEI,IAAM,uBAAuB,+BAA7B,MAAM,uBAAuB;IAIL;IAHZ,MAAM,GAAG,IAAI,eAAM,CAAC,yBAAuB,CAAC,IAAI,CAAC,CAAC;IAClD,OAAO,GAAG,IAAI,GAAG,EAAgC,CAAC;IAEnE,YAA6B,iBAAoC;QAApC,sBAAiB,GAAjB,iBAAiB,CAAmB;IAAG,CAAC;IAErE,YAAY;QACV,KAAK,MAAM,CAAC,IAAI,EAAE,IAAI,CAAC,IAAI,IAAI,CAAC,iBAAiB,CAAC,MAAM,EAAE,EAAE,CAAC;YAC3D,MAAM,QAAQ,GAAG,IAAA,gDAAuB,EAAC,IAAI,CAAC,CAAC;YAC/C,IAAI,QAAQ,KAAK,SAAS,EAAE,CAAC;gBAC3B,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,IAAI,EAAE,QAAQ,CAAC,CAAC;gBACjC,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,kCAAkC,IAAI,MAAM,QAAQ,CAAC,MAAM,EAAE,CAAC,CAAC;YACnF,CAAC;QACH,CAAC;QAED,IAAI,IAAI,CAAC,OAAO,CAAC,IAAI,GAAG,CAAC,EAAE,CAAC;YAC1B,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,kCAAkC,IAAI,CAAC,OAAO,CAAC,IAAI,gBAAgB,CAAC,CAAC;QACvF,CAAC;IACH,CAAC;IAED,8EAA8E;IAC9E,GAAG,CAAC,SAAiB;QACnB,OAAO,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC;IACrC,CAAC;IAED,mEAAmE;IACnE,GAAG,CAAC,SAAiB;QACnB,OAAO,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC;IACrC,CAAC;IAED;;;;;;;;;OASG;IACH,aAAa,CAAC,SAAiB,EAAE,KAAc;QAC7C,MAAM,MAAM,GAAG,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC;QAC3C,IAAI,MAAM,KAAK,SAAS,EAAE,CAAC;YACzB,OAAO,SAAS,CAAC;QACnB,CAAC;QAED,MAAM,OAAO,GAAG,OAAO,MAAM,CAAC,OAAO,KAAK,UAAU,CAAC,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC;QAE9F,OAAO;YACL,SAAS;YACT,MAAM,EAAE,MAAM,CAAC,MAAM;YACrB,MAAM,EAAE,MAAM,CAAC,MAAM;YACrB,UAAU,EAAE,MAAM,CAAC,UAAU,EAAE,CAAC,KAAK,CAAC;YACtC,OAAO;SACR,CAAC;IACJ,CAAC;CACF,CAAA;AAxDY,0DAAuB;kCAAvB,uBAAuB;IADnC,IAAA,mBAAU,GAAE;qCAKqC,uCAAiB;GAJtD,uBAAuB,CAwDnC;AAED;;;;;GAKG;AACU,QAAA,wBAAwB,GAAG,MAAM,CAAC,0BAA0B,CAAC,CAAC"}
|
|
@@ -37,7 +37,7 @@ export interface ExternalizedOptions<TEvent = unknown> {
|
|
|
37
37
|
* Optional override for which `ClientProxy` registration the
|
|
38
38
|
* externalizer should use when more than one is bound. Resolution
|
|
39
39
|
* semantics are owned by the externalizer; `outbox-microservices`
|
|
40
|
-
*
|
|
40
|
+
* interprets it as a token in the user's
|
|
41
41
|
* `ClientsModule` registration (DD-017).
|
|
42
42
|
*/
|
|
43
43
|
readonly client?: string | symbol;
|
|
@@ -75,10 +75,9 @@ export interface ExternalizedMetadata {
|
|
|
75
75
|
* `EventExternalizer` (see DD-018) with the resolved
|
|
76
76
|
* {@link ExternalizationMetadata}. Reliability — retry on broker
|
|
77
77
|
* failure, recovery on restart — is provided by the existing outbox
|
|
78
|
-
* machinery (single-unit atomicity per DD-019).
|
|
79
|
-
* the actual broker delivery requires a concrete externalizer
|
|
78
|
+
* machinery (single-unit atomicity per DD-019). The actual broker delivery requires a concrete externalizer
|
|
80
79
|
* implementation (e.g.
|
|
81
|
-
* `@nestjs-transactional/outbox-microservices
|
|
80
|
+
* `@nestjs-transactional/outbox-microservices`); without
|
|
82
81
|
* one, decorated events are processed locally and the externalization
|
|
83
82
|
* step is skipped without error.
|
|
84
83
|
*
|
|
@@ -22,10 +22,9 @@ exports.EXTERNALIZED_METADATA = Symbol('EXTERNALIZED_METADATA');
|
|
|
22
22
|
* `EventExternalizer` (see DD-018) with the resolved
|
|
23
23
|
* {@link ExternalizationMetadata}. Reliability — retry on broker
|
|
24
24
|
* failure, recovery on restart — is provided by the existing outbox
|
|
25
|
-
* machinery (single-unit atomicity per DD-019).
|
|
26
|
-
* the actual broker delivery requires a concrete externalizer
|
|
25
|
+
* machinery (single-unit atomicity per DD-019). The actual broker delivery requires a concrete externalizer
|
|
27
26
|
* implementation (e.g.
|
|
28
|
-
* `@nestjs-transactional/outbox-microservices
|
|
27
|
+
* `@nestjs-transactional/outbox-microservices`); without
|
|
29
28
|
* one, decorated events are processed locally and the externalization
|
|
30
29
|
* step is skipped without error.
|
|
31
30
|
*
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"externalized.decorator.js","sourceRoot":"","sources":["../../src/externalization/externalized.decorator.ts"],"names":[],"mappings":";;;
|
|
1
|
+
{"version":3,"file":"externalized.decorator.js","sourceRoot":"","sources":["../../src/externalization/externalized.decorator.ts"],"names":[],"mappings":";;;AAoHA,oCAqBC;AAOD,0DAGC;AAnJD,4BAA0B;AAE1B;;;;;;;GAOG;AACU,QAAA,qBAAqB,GAAG,MAAM,CAAC,uBAAuB,CAAC,CAAC;AA8DrE;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2CG;AACH,SAAgB,YAAY,CAC1B,OAAoC;IAEpC,IAAI,OAAO,OAAO,CAAC,MAAM,KAAK,QAAQ,IAAI,OAAO,CAAC,MAAM,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACtE,MAAM,IAAI,KAAK,CAAC,8DAA8D,CAAC,CAAC;IAClF,CAAC;IAED,mEAAmE;IACnE,kEAAkE;IAClE,4BAA4B;IAC5B,MAAM,QAAQ,GAAyB;QACrC,MAAM,EAAE,OAAO,CAAC,MAAM;QACtB,MAAM,EAAE,OAAO,CAAC,MAAM;QACtB,UAAU,EAAE,OAAO,CAAC,UAAsD;QAC1E,OAAO,EAAE,OAAO,CAAC,OACkE;KACpF,CAAC;IAEF,OAAO,CAAC,MAAc,EAAQ,EAAE;QAC9B,OAAO,CAAC,cAAc,CAAC,6BAAqB,EAAE,QAAQ,EAAE,MAAM,CAAC,CAAC;IAClE,CAAC,CAAC;AACJ,CAAC;AAED;;;;GAIG;AACH,SAAgB,uBAAuB,CAAC,MAAc;IACpD,MAAM,KAAK,GAAY,OAAO,CAAC,WAAW,CAAC,6BAAqB,EAAE,MAAM,CAAC,CAAC;IAC1E,OAAO,KAAyC,CAAC;AACnD,CAAC"}
|
|
@@ -2,11 +2,11 @@
|
|
|
2
2
|
* Metadata describing how a single event should be routed to an
|
|
3
3
|
* external message broker.
|
|
4
4
|
*
|
|
5
|
-
* Produced by the `ExternalizationRegistry`
|
|
5
|
+
* Produced by the `ExternalizationRegistry` by resolving
|
|
6
6
|
* the event's class against the metadata stored by the `@Externalized`
|
|
7
7
|
* decorator. Consumed by an {@link EventExternalizer} implementation
|
|
8
8
|
* (e.g. `MicroservicesEventExternalizer` from
|
|
9
|
-
* `@nestjs-transactional/outbox-microservices
|
|
9
|
+
* `@nestjs-transactional/outbox-microservices`) which
|
|
10
10
|
* translates the abstract `target` / `routingKey` / `headers` shape
|
|
11
11
|
* into transport-specific calls.
|
|
12
12
|
*
|
package/dist/index.d.ts
CHANGED
|
@@ -3,7 +3,10 @@ export * from './types/event-publication';
|
|
|
3
3
|
export * from './types/completion-mode';
|
|
4
4
|
export * from './types/resubmission-options';
|
|
5
5
|
export * from './types/staleness-config';
|
|
6
|
+
export * from './types/cleanup-config';
|
|
7
|
+
export * from './types/retry-config';
|
|
6
8
|
export * from './types/errors';
|
|
9
|
+
export { DEFAULT_DRAIN_TIMEOUT_MS } from './shutdown/drain';
|
|
7
10
|
export * from './serialization/event-serializer';
|
|
8
11
|
export * from './serialization/event-type-registry';
|
|
9
12
|
export * from './serialization/event-type-resolver';
|
|
@@ -25,10 +28,13 @@ export type { ExternalizationMetadata } from './externalization/types';
|
|
|
25
28
|
export type { EventExternalizer } from './externalization/event-externalizer';
|
|
26
29
|
export { EVENT_EXTERNALIZER } from './externalization/event-externalizer';
|
|
27
30
|
export { ExternalizationError } from './externalization/errors';
|
|
31
|
+
export { describeThrown } from './externalization/describe-thrown';
|
|
28
32
|
export { Externalized, getExternalizedMetadata, EXTERNALIZED_METADATA, } from './externalization/externalized.decorator';
|
|
29
33
|
export type { ExternalizedOptions, ExternalizedMetadata, } from './externalization/externalized.decorator';
|
|
30
34
|
export { ExternalizationRegistry, EXTERNALIZATION_REGISTRY, } from './externalization/externalization-registry';
|
|
31
35
|
export * from './recovery/staleness-monitor';
|
|
36
|
+
export * from './recovery/outbox-cleanup-scheduler';
|
|
37
|
+
export * from './recovery/outbox-retry-scheduler';
|
|
32
38
|
export * from './api/failed-event-publications';
|
|
33
39
|
export * from './api/incomplete-event-publications';
|
|
34
40
|
export * from './api/completed-event-publications';
|
package/dist/index.js
CHANGED
|
@@ -14,13 +14,17 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
|
14
14
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
15
15
|
};
|
|
16
16
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
17
|
-
exports.EXTERNALIZATION_REGISTRY = exports.ExternalizationRegistry = exports.EXTERNALIZED_METADATA = exports.getExternalizedMetadata = exports.Externalized = exports.ExternalizationError = exports.EVENT_EXTERNALIZER = void 0;
|
|
17
|
+
exports.EXTERNALIZATION_REGISTRY = exports.ExternalizationRegistry = exports.EXTERNALIZED_METADATA = exports.getExternalizedMetadata = exports.Externalized = exports.describeThrown = exports.ExternalizationError = exports.EVENT_EXTERNALIZER = exports.DEFAULT_DRAIN_TIMEOUT_MS = void 0;
|
|
18
18
|
__exportStar(require("./types/publication-status"), exports);
|
|
19
19
|
__exportStar(require("./types/event-publication"), exports);
|
|
20
20
|
__exportStar(require("./types/completion-mode"), exports);
|
|
21
21
|
__exportStar(require("./types/resubmission-options"), exports);
|
|
22
22
|
__exportStar(require("./types/staleness-config"), exports);
|
|
23
|
+
__exportStar(require("./types/cleanup-config"), exports);
|
|
24
|
+
__exportStar(require("./types/retry-config"), exports);
|
|
23
25
|
__exportStar(require("./types/errors"), exports);
|
|
26
|
+
var drain_1 = require("./shutdown/drain");
|
|
27
|
+
Object.defineProperty(exports, "DEFAULT_DRAIN_TIMEOUT_MS", { enumerable: true, get: function () { return drain_1.DEFAULT_DRAIN_TIMEOUT_MS; } });
|
|
24
28
|
__exportStar(require("./serialization/event-serializer"), exports);
|
|
25
29
|
__exportStar(require("./serialization/event-type-registry"), exports);
|
|
26
30
|
__exportStar(require("./serialization/event-type-resolver"), exports);
|
|
@@ -41,6 +45,10 @@ var event_externalizer_1 = require("./externalization/event-externalizer");
|
|
|
41
45
|
Object.defineProperty(exports, "EVENT_EXTERNALIZER", { enumerable: true, get: function () { return event_externalizer_1.EVENT_EXTERNALIZER; } });
|
|
42
46
|
var errors_1 = require("./externalization/errors");
|
|
43
47
|
Object.defineProperty(exports, "ExternalizationError", { enumerable: true, get: function () { return errors_1.ExternalizationError; } });
|
|
48
|
+
// Exported because every externalizer implementation faces the same
|
|
49
|
+
// problem: broker clients reject with values that are not `Error`s.
|
|
50
|
+
var describe_thrown_1 = require("./externalization/describe-thrown");
|
|
51
|
+
Object.defineProperty(exports, "describeThrown", { enumerable: true, get: function () { return describe_thrown_1.describeThrown; } });
|
|
44
52
|
var externalized_decorator_1 = require("./externalization/externalized.decorator");
|
|
45
53
|
Object.defineProperty(exports, "Externalized", { enumerable: true, get: function () { return externalized_decorator_1.Externalized; } });
|
|
46
54
|
Object.defineProperty(exports, "getExternalizedMetadata", { enumerable: true, get: function () { return externalized_decorator_1.getExternalizedMetadata; } });
|
|
@@ -49,6 +57,8 @@ var externalization_registry_1 = require("./externalization/externalization-regi
|
|
|
49
57
|
Object.defineProperty(exports, "ExternalizationRegistry", { enumerable: true, get: function () { return externalization_registry_1.ExternalizationRegistry; } });
|
|
50
58
|
Object.defineProperty(exports, "EXTERNALIZATION_REGISTRY", { enumerable: true, get: function () { return externalization_registry_1.EXTERNALIZATION_REGISTRY; } });
|
|
51
59
|
__exportStar(require("./recovery/staleness-monitor"), exports);
|
|
60
|
+
__exportStar(require("./recovery/outbox-cleanup-scheduler"), exports);
|
|
61
|
+
__exportStar(require("./recovery/outbox-retry-scheduler"), exports);
|
|
52
62
|
__exportStar(require("./api/failed-event-publications"), exports);
|
|
53
63
|
__exportStar(require("./api/incomplete-event-publications"), exports);
|
|
54
64
|
__exportStar(require("./api/completed-event-publications"), exports);
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AAAA,6DAA2C;AAC3C,4DAA0C;AAC1C,0DAAwC;AACxC,+DAA6C;AAC7C,2DAAyC;AACzC,iDAA+B;AAE/B,mEAAiD;AACjD,sEAAoD;AACpD,sEAAoD;AACpD,wEAAsD;AAEtD,4EAA0D;AAE1D,wEAAsD;AACtD,+DAA6C;AAC7C,yEAAuD;AACvD,qEAAmD;AAEnD,+EAA6D;AAC7D,iEAA+C;AAE/C,2CAAyB;AAIzB,sEAAoD;AACpD,4EAA0D;AAC1D,2EAAyD;AACzD,iEAA+C;AAI/C,2EAA0E;AAAjE,wHAAA,kBAAkB,OAAA;AAC3B,mDAAgE;AAAvD,8GAAA,oBAAoB,OAAA;AAC7B,mFAIkD;AAHhD,sHAAA,YAAY,OAAA;AACZ,iIAAA,uBAAuB,OAAA;AACvB,+HAAA,qBAAqB,OAAA;AAMvB,uFAGoD;AAFlD,mIAAA,uBAAuB,OAAA;AACvB,oIAAA,wBAAwB,OAAA;AAG1B,+DAA6C;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AAAA,6DAA2C;AAC3C,4DAA0C;AAC1C,0DAAwC;AACxC,+DAA6C;AAC7C,2DAAyC;AACzC,yDAAuC;AACvC,uDAAqC;AACrC,iDAA+B;AAE/B,0CAA4D;AAAnD,iHAAA,wBAAwB,OAAA;AAEjC,mEAAiD;AACjD,sEAAoD;AACpD,sEAAoD;AACpD,wEAAsD;AAEtD,4EAA0D;AAE1D,wEAAsD;AACtD,+DAA6C;AAC7C,yEAAuD;AACvD,qEAAmD;AAEnD,+EAA6D;AAC7D,iEAA+C;AAE/C,2CAAyB;AAIzB,sEAAoD;AACpD,4EAA0D;AAC1D,2EAAyD;AACzD,iEAA+C;AAI/C,2EAA0E;AAAjE,wHAAA,kBAAkB,OAAA;AAC3B,mDAAgE;AAAvD,8GAAA,oBAAoB,OAAA;AAC7B,oEAAoE;AACpE,oEAAoE;AACpE,qEAAmE;AAA1D,iHAAA,cAAc,OAAA;AACvB,mFAIkD;AAHhD,sHAAA,YAAY,OAAA;AACZ,iIAAA,uBAAuB,OAAA;AACvB,+HAAA,qBAAqB,OAAA;AAMvB,uFAGoD;AAFlD,mIAAA,uBAAuB,OAAA;AACvB,oIAAA,wBAAwB,OAAA;AAG1B,+DAA6C;AAC7C,sEAAoD;AACpD,oEAAkD;AAElD,kEAAgD;AAChD,sEAAoD;AACpD,qEAAmD;AAEnD,8DAA4C;AAE5C,yDAAuC;AACvC,oEAAkD"}
|
|
@@ -5,7 +5,7 @@ import { type OutboxProcessingBundle } from './outbox.module';
|
|
|
5
5
|
* {@link EventPublicationProcessor} and {@link StalenessMonitor} on
|
|
6
6
|
* application bootstrap and stops them on shutdown.
|
|
7
7
|
*
|
|
8
|
-
*
|
|
8
|
+
* This is generalised to multi-dataSource: the module reads
|
|
9
9
|
* {@link OUTBOX_PROCESSING_BUNDLE} provided by `OutboxModule.forRoot`
|
|
10
10
|
* — the bundle contains arrays of per-dataSource processors and
|
|
11
11
|
* monitors. Single-dataSource deployments see the bundle with
|
|
@@ -24,6 +24,22 @@ export declare class OutboxProcessingModule implements OnApplicationBootstrap, O
|
|
|
24
24
|
private readonly bundle;
|
|
25
25
|
constructor(bundle: OutboxProcessingBundle);
|
|
26
26
|
onApplicationBootstrap(): void;
|
|
27
|
-
|
|
27
|
+
/**
|
|
28
|
+
* Drain every worker before NestJS proceeds with the rest of the
|
|
29
|
+
* teardown.
|
|
30
|
+
*
|
|
31
|
+
* Awaited on purpose: the hook used to be synchronous, so NestJS moved
|
|
32
|
+
* straight on to destroying providers — the DataSource among them —
|
|
33
|
+
* while a batch dispatched by the previous tick was still running.
|
|
34
|
+
* That could interrupt a publication's `PROCESSING → COMPLETED`
|
|
35
|
+
* transition and strand the row until the staleness monitor found it.
|
|
36
|
+
*
|
|
37
|
+
* Each worker's drain is individually bounded (`shutdownTimeout`), so
|
|
38
|
+
* a stuck listener delays shutdown by at most that budget. Drains run
|
|
39
|
+
* concurrently rather than in sequence: they are independent, and
|
|
40
|
+
* serialising them would add up the budgets in multi-dataSource
|
|
41
|
+
* deployments.
|
|
42
|
+
*/
|
|
43
|
+
onApplicationShutdown(): Promise<void>;
|
|
28
44
|
}
|
|
29
45
|
//# sourceMappingURL=outbox-processing.module.d.ts.map
|
|
@@ -20,7 +20,7 @@ const outbox_module_1 = require("./outbox.module");
|
|
|
20
20
|
* {@link EventPublicationProcessor} and {@link StalenessMonitor} on
|
|
21
21
|
* application bootstrap and stops them on shutdown.
|
|
22
22
|
*
|
|
23
|
-
*
|
|
23
|
+
* This is generalised to multi-dataSource: the module reads
|
|
24
24
|
* {@link OUTBOX_PROCESSING_BUNDLE} provided by `OutboxModule.forRoot`
|
|
25
25
|
* — the bundle contains arrays of per-dataSource processors and
|
|
26
26
|
* monitors. Single-dataSource deployments see the bundle with
|
|
@@ -47,15 +47,41 @@ let OutboxProcessingModule = class OutboxProcessingModule {
|
|
|
47
47
|
for (const monitor of this.bundle.monitors) {
|
|
48
48
|
monitor.start();
|
|
49
49
|
}
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
for (const
|
|
53
|
-
|
|
50
|
+
// No-op unless the dataSource configured `retry.maxAttempts > 0`
|
|
51
|
+
// (DD-026) — automatic retry is opt-in.
|
|
52
|
+
for (const scheduler of this.bundle.retrySchedulers) {
|
|
53
|
+
scheduler.start();
|
|
54
54
|
}
|
|
55
|
-
|
|
56
|
-
|
|
55
|
+
// Likewise a no-op unless `cleanup.interval > 0` (C4) — retention
|
|
56
|
+
// of completed publications is opt-in, and stays manual otherwise.
|
|
57
|
+
for (const scheduler of this.bundle.cleanupSchedulers) {
|
|
58
|
+
scheduler.start();
|
|
57
59
|
}
|
|
58
60
|
}
|
|
61
|
+
/**
|
|
62
|
+
* Drain every worker before NestJS proceeds with the rest of the
|
|
63
|
+
* teardown.
|
|
64
|
+
*
|
|
65
|
+
* Awaited on purpose: the hook used to be synchronous, so NestJS moved
|
|
66
|
+
* straight on to destroying providers — the DataSource among them —
|
|
67
|
+
* while a batch dispatched by the previous tick was still running.
|
|
68
|
+
* That could interrupt a publication's `PROCESSING → COMPLETED`
|
|
69
|
+
* transition and strand the row until the staleness monitor found it.
|
|
70
|
+
*
|
|
71
|
+
* Each worker's drain is individually bounded (`shutdownTimeout`), so
|
|
72
|
+
* a stuck listener delays shutdown by at most that budget. Drains run
|
|
73
|
+
* concurrently rather than in sequence: they are independent, and
|
|
74
|
+
* serialising them would add up the budgets in multi-dataSource
|
|
75
|
+
* deployments.
|
|
76
|
+
*/
|
|
77
|
+
async onApplicationShutdown() {
|
|
78
|
+
await Promise.all([
|
|
79
|
+
...this.bundle.processors.map((processor) => processor.stop()),
|
|
80
|
+
...this.bundle.monitors.map((monitor) => monitor.stop()),
|
|
81
|
+
...this.bundle.retrySchedulers.map((scheduler) => scheduler.stop()),
|
|
82
|
+
...this.bundle.cleanupSchedulers.map((scheduler) => scheduler.stop()),
|
|
83
|
+
]);
|
|
84
|
+
}
|
|
59
85
|
};
|
|
60
86
|
exports.OutboxProcessingModule = OutboxProcessingModule;
|
|
61
87
|
exports.OutboxProcessingModule = OutboxProcessingModule = __decorate([
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"outbox-processing.module.js","sourceRoot":"","sources":["../../src/module/outbox-processing.module.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;AAAA,2CAKwB;AAExB,
|
|
1
|
+
{"version":3,"file":"outbox-processing.module.js","sourceRoot":"","sources":["../../src/module/outbox-processing.module.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;AAAA,2CAKwB;AAExB,mDAAwF;AAExF;;;;;;;;;;;;;;;;;;;GAmBG;AAEI,IAAM,sBAAsB,GAA5B,MAAM,sBAAsB;IAGd;IAFnB,YAEmB,MAA8B;QAA9B,WAAM,GAAN,MAAM,CAAwB;IAC9C,CAAC;IAEJ,sBAAsB;QACpB,KAAK,MAAM,SAAS,IAAI,IAAI,CAAC,MAAM,CAAC,UAAU,EAAE,CAAC;YAC/C,SAAS,CAAC,KAAK,EAAE,CAAC;QACpB,CAAC;QACD,KAAK,MAAM,OAAO,IAAI,IAAI,CAAC,MAAM,CAAC,QAAQ,EAAE,CAAC;YAC3C,OAAO,CAAC,KAAK,EAAE,CAAC;QAClB,CAAC;QACD,iEAAiE;QACjE,wCAAwC;QACxC,KAAK,MAAM,SAAS,IAAI,IAAI,CAAC,MAAM,CAAC,eAAe,EAAE,CAAC;YACpD,SAAS,CAAC,KAAK,EAAE,CAAC;QACpB,CAAC;QACD,kEAAkE;QAClE,mEAAmE;QACnE,KAAK,MAAM,SAAS,IAAI,IAAI,CAAC,MAAM,CAAC,iBAAiB,EAAE,CAAC;YACtD,SAAS,CAAC,KAAK,EAAE,CAAC;QACpB,CAAC;IACH,CAAC;IAED;;;;;;;;;;;;;;;OAeG;IACH,KAAK,CAAC,qBAAqB;QACzB,MAAM,OAAO,CAAC,GAAG,CAAC;YAChB,GAAG,IAAI,CAAC,MAAM,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC,SAAS,EAAE,EAAE,CAAC,SAAS,CAAC,IAAI,EAAE,CAAC;YAC9D,GAAG,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,OAAO,EAAE,EAAE,CAAC,OAAO,CAAC,IAAI,EAAE,CAAC;YACxD,GAAG,IAAI,CAAC,MAAM,CAAC,eAAe,CAAC,GAAG,CAAC,CAAC,SAAS,EAAE,EAAE,CAAC,SAAS,CAAC,IAAI,EAAE,CAAC;YACnE,GAAG,IAAI,CAAC,MAAM,CAAC,iBAAiB,CAAC,GAAG,CAAC,CAAC,SAAS,EAAE,EAAE,CAAC,SAAS,CAAC,IAAI,EAAE,CAAC;SACtE,CAAC,CAAC;IACL,CAAC;CACF,CAAA;AAjDY,wDAAsB;iCAAtB,sBAAsB;IADlC,IAAA,eAAM,EAAC,EAAE,CAAC;IAGN,WAAA,IAAA,eAAM,EAAC,wCAAwB,CAAC,CAAA;;GAFxB,sBAAsB,CAiDlC"}
|