@zlink-systems/nestjs 0.10.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.
Files changed (41) hide show
  1. package/LICENSE +105 -0
  2. package/dist/.tsbuildinfo +1 -0
  3. package/dist/auto-discovery-marker.d.ts +3 -0
  4. package/dist/auto-discovery-marker.js +12 -0
  5. package/dist/contracts.d.ts +229 -0
  6. package/dist/contracts.js +4 -0
  7. package/dist/decorators.d.ts +16 -0
  8. package/dist/decorators.js +174 -0
  9. package/dist/dispatch-scope.d.ts +5 -0
  10. package/dist/dispatch-scope.js +19 -0
  11. package/dist/drain-health-indicator.d.ts +9 -0
  12. package/dist/drain-health-indicator.js +32 -0
  13. package/dist/framework-integration-contracts.d.ts +368 -0
  14. package/dist/framework-integration-contracts.js +2 -0
  15. package/dist/framework-loader.d.ts +50 -0
  16. package/dist/framework-loader.js +16 -0
  17. package/dist/handler-adapters.d.ts +13 -0
  18. package/dist/handler-adapters.js +155 -0
  19. package/dist/handler-metadata.d.ts +55 -0
  20. package/dist/handler-metadata.js +84 -0
  21. package/dist/http-client-module.d.ts +28 -0
  22. package/dist/http-client-module.js +96 -0
  23. package/dist/index.d.ts +10 -0
  24. package/dist/index.js +27 -0
  25. package/dist/internal-tokens.d.ts +2 -0
  26. package/dist/internal-tokens.js +5 -0
  27. package/dist/module.d.ts +11 -0
  28. package/dist/module.js +203 -0
  29. package/dist/options-builder.d.ts +2 -0
  30. package/dist/options-builder.js +973 -0
  31. package/dist/provider-discovery.d.ts +36 -0
  32. package/dist/provider-discovery.js +186 -0
  33. package/dist/providers.d.ts +16 -0
  34. package/dist/providers.js +426 -0
  35. package/dist/registration-composer.d.ts +7 -0
  36. package/dist/registration-composer.js +310 -0
  37. package/dist/spot-node-handler-registry.d.ts +24 -0
  38. package/dist/spot-node-handler-registry.js +105 -0
  39. package/dist/tokens.d.ts +19 -0
  40. package/dist/tokens.js +22 -0
  41. package/package.json +26 -0
@@ -0,0 +1,36 @@
1
+ import type { InjectionToken } from '@nestjs/common';
2
+ import type { DiscoveryService, ModuleRef } from '@nestjs/core';
3
+ import type { Type } from '@zlink-systems/framework';
4
+ import { type ZLinkNestHandlerMetadata, type ZLinkNestSpotActorHandlerMetadata, type ZLinkNestSpotHandlerMetadata, type ZLinkNestSpotTimerHandlerMetadata } from './handler-metadata';
5
+ export interface DiscoveredNestProvider {
6
+ readonly handlerKey: InjectionToken;
7
+ readonly handlerName: string;
8
+ readonly token: InjectionToken;
9
+ readonly metadata: ZLinkNestHandlerMetadata;
10
+ }
11
+ export interface DiscoveredNestSpotActorProvider {
12
+ readonly handlerKey: Type;
13
+ readonly handlerName: string;
14
+ readonly token: InjectionToken;
15
+ readonly metadata: ZLinkNestSpotActorHandlerMetadata;
16
+ }
17
+ export interface DiscoveredNestSpotProvider {
18
+ readonly handlerKey: Type;
19
+ readonly handlerName: string;
20
+ readonly token: InjectionToken;
21
+ readonly metadata: ZLinkNestSpotHandlerMetadata;
22
+ }
23
+ export interface DiscoveredNestSpotTimerProvider {
24
+ readonly handlerKey: Type;
25
+ readonly handlerName: string;
26
+ readonly token: InjectionToken;
27
+ readonly metadata: ZLinkNestSpotTimerHandlerMetadata;
28
+ }
29
+ export interface DiscoveredNestSessionProvider {
30
+ readonly handlerKey: Type;
31
+ }
32
+ export declare function discoverSessionProviderRefs(discovery: DiscoveryService, moduleRef: ModuleRef): DiscoveredNestSessionProvider[];
33
+ export declare function discoverProviderRefs(discovery: DiscoveryService, moduleRef: ModuleRef): DiscoveredNestProvider[];
34
+ export declare function discoverSpotProviderRefs(discovery: DiscoveryService, moduleRef: ModuleRef): DiscoveredNestSpotProvider[];
35
+ export declare function discoverSpotActorProviderRefs(discovery: DiscoveryService, moduleRef: ModuleRef): DiscoveredNestSpotActorProvider[];
36
+ export declare function discoverSpotTimerProviderRefs(discovery: DiscoveryService, moduleRef: ModuleRef): DiscoveredNestSpotTimerProvider[];
@@ -0,0 +1,186 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.discoverSessionProviderRefs = discoverSessionProviderRefs;
4
+ exports.discoverProviderRefs = discoverProviderRefs;
5
+ exports.discoverSpotProviderRefs = discoverSpotProviderRefs;
6
+ exports.discoverSpotActorProviderRefs = discoverSpotActorProviderRefs;
7
+ exports.discoverSpotTimerProviderRefs = discoverSpotTimerProviderRefs;
8
+ const framework_loader_1 = require("./framework-loader");
9
+ const auto_discovery_marker_1 = require("./auto-discovery-marker");
10
+ const handler_metadata_1 = require("./handler-metadata");
11
+ function discoverSessionProviderRefs(discovery, moduleRef) {
12
+ const refs = [];
13
+ const seen = new Set();
14
+ const metadataSymbol = Symbol.for('@zlink-systems/framework:decorator');
15
+ for (const wrapper of discovery.getProviders()) {
16
+ const handlerType = wrapper.metatype;
17
+ if (typeof handlerType !== 'function'
18
+ || seen.has(handlerType)
19
+ || !(0, auto_discovery_marker_1.isAutoDiscoveredProvider)(handlerType)) {
20
+ continue;
21
+ }
22
+ // The symbol is only present on decorated handlers, so the lookup has to
23
+ // admit undefined for the fallback to mean anything.
24
+ const metadata = handlerType[metadataSymbol] ?? [];
25
+ if (metadata.some((entry) => entry.kind === 'packet')
26
+ && typeof handlerType.prototype?.handle === 'function'
27
+ && tryGetProviderInstance(moduleRef, handlerType) !== undefined) {
28
+ seen.add(handlerType);
29
+ refs.push({ handlerKey: handlerType });
30
+ }
31
+ }
32
+ return refs;
33
+ }
34
+ function discoverProviderRefs(discovery, moduleRef) {
35
+ return discoverDecoratedProviderRefs({
36
+ discovery,
37
+ moduleRef,
38
+ metadataEntries: (0, handler_metadata_1.nestHandlerMetadataEntries)(),
39
+ readMetadata: handler_metadata_1.readNestHandlerMetadata,
40
+ metadataKey: (metadata) => `${metadata.groupName}:${metadata.kind}:${metadata.packetName}`,
41
+ createRef: ({ handlerKey, handlerName, token, metadata }) => ({
42
+ handlerKey,
43
+ handlerName,
44
+ token,
45
+ metadata
46
+ })
47
+ });
48
+ }
49
+ function discoverSpotProviderRefs(discovery, moduleRef) {
50
+ return discoverDecoratedClassProviderRefs({
51
+ discovery,
52
+ moduleRef,
53
+ metadataEntries: (0, handler_metadata_1.nestSpotHandlerMetadataEntries)(),
54
+ readMetadata: handler_metadata_1.readNestSpotHandlerMetadata,
55
+ metadataKey: (metadata) => `${metadata.kind}:${metadata.packetName ?? metadata.topic ?? ''}`,
56
+ invalidClassMessage: 'ZLink SPOT handler decorators must be applied to class providers.',
57
+ createRef: ({ handlerKey, handlerName, token, metadata }) => ({
58
+ handlerKey,
59
+ handlerName,
60
+ token,
61
+ metadata
62
+ })
63
+ });
64
+ }
65
+ function discoverSpotActorProviderRefs(discovery, moduleRef) {
66
+ return discoverDecoratedClassProviderRefs({
67
+ discovery,
68
+ moduleRef,
69
+ metadataEntries: (0, handler_metadata_1.nestSpotActorHandlerMetadataEntries)(),
70
+ readMetadata: handler_metadata_1.readNestSpotActorHandlerMetadata,
71
+ metadataKey: (metadata) => `${metadata.kind}:${metadata.packetName}`,
72
+ invalidClassMessage: 'ZLink SPOT actor handler decorators must be applied to class providers.',
73
+ createRef: ({ handlerKey, handlerName, token, metadata }) => ({
74
+ handlerKey,
75
+ handlerName,
76
+ token,
77
+ metadata
78
+ })
79
+ });
80
+ }
81
+ function discoverSpotTimerProviderRefs(discovery, moduleRef) {
82
+ return discoverDecoratedClassProviderRefs({
83
+ discovery,
84
+ moduleRef,
85
+ metadataEntries: (0, handler_metadata_1.nestSpotTimerHandlerMetadataEntries)(),
86
+ readMetadata: handler_metadata_1.readNestSpotTimerHandlerMetadata,
87
+ metadataKey: (metadata) => metadata.name,
88
+ invalidClassMessage: 'ZLink SPOT timer handler decorators must be applied to class providers.',
89
+ createRef: ({ handlerKey, handlerName, token, metadata }) => ({
90
+ handlerKey,
91
+ handlerName,
92
+ token,
93
+ metadata
94
+ })
95
+ });
96
+ }
97
+ function discoverDecoratedProviderRefs(options) {
98
+ const refs = [];
99
+ const seen = new Set();
100
+ for (const wrapper of options.discovery.getProviders()) {
101
+ const token = wrapper.token;
102
+ if (token === undefined) {
103
+ continue;
104
+ }
105
+ const instance = wrapper.instance === undefined ? undefined : wrapper.instance;
106
+ for (const handlerKey of providerMetadataCandidateTokens(wrapper.metatype, instance, token)) {
107
+ appendDiscoveredProviderRefs(refs, seen, {
108
+ handlerKey,
109
+ token,
110
+ instance,
111
+ metadataList: options.readMetadata(handlerKey),
112
+ metadataKey: options.metadataKey,
113
+ createRef: options.createRef
114
+ });
115
+ }
116
+ }
117
+ for (const [handlerKey, metadataList] of options.metadataEntries) {
118
+ const instance = tryGetProviderInstance(options.moduleRef, handlerKey);
119
+ if (instance === undefined) {
120
+ continue;
121
+ }
122
+ appendDiscoveredProviderRefs(refs, seen, {
123
+ handlerKey,
124
+ token: handlerKey,
125
+ instance,
126
+ metadataList,
127
+ metadataKey: options.metadataKey,
128
+ createRef: options.createRef
129
+ });
130
+ }
131
+ return refs;
132
+ }
133
+ function discoverDecoratedClassProviderRefs(options) {
134
+ return discoverDecoratedProviderRefs({
135
+ ...options,
136
+ createRef: (input) => {
137
+ if (typeof input.handlerKey !== 'function') {
138
+ throw new framework_loader_1.framework.ZLinkConfigurationException(options.invalidClassMessage);
139
+ }
140
+ return options.createRef({
141
+ ...input,
142
+ handlerKey: input.handlerKey
143
+ });
144
+ }
145
+ });
146
+ }
147
+ function appendDiscoveredProviderRefs(refs, seen, options) {
148
+ const handlerName = handlerKeyName(options.handlerKey);
149
+ for (const metadata of options.metadataList) {
150
+ const key = `${String(options.token)}:${handlerName}:${options.metadataKey(metadata)}`;
151
+ if (seen.has(key)) {
152
+ continue;
153
+ }
154
+ seen.add(key);
155
+ refs.push(options.createRef({
156
+ handlerKey: options.handlerKey,
157
+ handlerName,
158
+ token: options.token,
159
+ instance: options.instance,
160
+ metadata
161
+ }));
162
+ }
163
+ }
164
+ function providerMetadataCandidateTokens(metatype, instance, token) {
165
+ return [...new Set([metatype, instance?.constructor, token].filter(isInjectionToken))];
166
+ }
167
+ function isInjectionToken(value) {
168
+ return typeof value === 'function' || typeof value === 'string' || typeof value === 'symbol';
169
+ }
170
+ function tryGetProviderInstance(moduleRef, token) {
171
+ try {
172
+ return moduleRef.get(token, { strict: false });
173
+ }
174
+ catch {
175
+ return undefined;
176
+ }
177
+ }
178
+ function handlerKeyName(handlerKey) {
179
+ if (typeof handlerKey === 'function') {
180
+ return handlerKey.name;
181
+ }
182
+ if (typeof handlerKey === 'symbol') {
183
+ return handlerKey.description ?? handlerKey.toString();
184
+ }
185
+ return handlerKey;
186
+ }
@@ -0,0 +1,16 @@
1
+ import type { InjectionToken, OnModuleDestroy, OnModuleInit, Provider } from '@nestjs/common';
2
+ import { DiscoveryService, ModuleRef } from '@nestjs/core';
3
+ import type { Type } from '@zlink-systems/framework';
4
+ import type { ZLinkFrameworkRegistration } from './framework-integration-contracts';
5
+ import { type FrameworkRuntimeHost } from './framework-loader';
6
+ type RuntimeHostWithNestLifecycle = FrameworkRuntimeHost & OnModuleInit & OnModuleDestroy;
7
+ export declare function alwaysAvailableClientProviders(registration?: ZLinkFrameworkRegistration): Provider[];
8
+ export declare function alwaysAvailableClientTokens(): InjectionToken[];
9
+ export declare function conditionalClientProviders(registration: ZLinkFrameworkRegistration): Provider[];
10
+ export declare function conditionalClientProvidersForFactory(): Provider[];
11
+ export declare function conditionalClientTokens(): InjectionToken[];
12
+ export declare function createRuntimeHost(registration: ZLinkFrameworkRegistration, moduleRef: ModuleRef, discovery: DiscoveryService): RuntimeHostWithNestLifecycle;
13
+ export declare function disposeNestOwnedHandler(instance: unknown): Promise<void>;
14
+ export declare function createNestHandlerInstance<T>(moduleRef: ModuleRef, contextId: import('@nestjs/core').ContextId, dependencies: Map<unknown, Promise<unknown>>, type: Type<T>): Promise<T>;
15
+ export declare function providerToken(provider: Provider): InjectionToken;
16
+ export {};
@@ -0,0 +1,426 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.alwaysAvailableClientProviders = alwaysAvailableClientProviders;
4
+ exports.alwaysAvailableClientTokens = alwaysAvailableClientTokens;
5
+ exports.conditionalClientProviders = conditionalClientProviders;
6
+ exports.conditionalClientProvidersForFactory = conditionalClientProvidersForFactory;
7
+ exports.conditionalClientTokens = conditionalClientTokens;
8
+ exports.createRuntimeHost = createRuntimeHost;
9
+ exports.disposeNestOwnedHandler = disposeNestOwnedHandler;
10
+ exports.createNestHandlerInstance = createNestHandlerInstance;
11
+ exports.providerToken = providerToken;
12
+ const constants_1 = require("@nestjs/common/constants");
13
+ const core_1 = require("@nestjs/core");
14
+ const tokens_1 = require("./tokens");
15
+ const internal_tokens_1 = require("./internal-tokens");
16
+ const framework_loader_1 = require("./framework-loader");
17
+ const dispatch_scope_1 = require("./dispatch-scope");
18
+ const ALWAYS_AVAILABLE_CLIENT_PROVIDER_SPECS = [
19
+ {
20
+ token: tokens_1.ZLINK_CHANNEL_CLIENT,
21
+ create: (registration, runtime) => framework_loader_1.framework.createIntegrationChannelClient(registration, runtime)
22
+ },
23
+ {
24
+ token: tokens_1.ZLINK_CHANNEL_RUNTIME_OPTIONS,
25
+ create: (_registration, runtime) => runtime.channelRuntimeOptions
26
+ },
27
+ {
28
+ token: tokens_1.ZLINK_FANOUT_CLIENT,
29
+ create: (registration, runtime) => framework_loader_1.framework.createIntegrationFanoutClient(registration, runtime)
30
+ },
31
+ {
32
+ token: tokens_1.ZLINK_ROUTE_CLIENT,
33
+ create: (registration, runtime) => framework_loader_1.framework.createIntegrationRouteClient(registration, runtime)
34
+ },
35
+ {
36
+ token: tokens_1.ZLINK_BOUND_SESSION_FACTORY,
37
+ create: (_registration, runtime) => runtime.boundSessionFactory
38
+ }
39
+ ];
40
+ function alwaysAvailableClientProviders(registration) {
41
+ return [
42
+ ...ALWAYS_AVAILABLE_CLIENT_PROVIDER_SPECS.map((spec) => createAlwaysAvailableClientProvider(spec, registration)),
43
+ { provide: tokens_1.ZLINK_MESSAGE_METADATA_POLICY, useValue: Object.freeze({ forward: true }) }
44
+ ];
45
+ }
46
+ function createAlwaysAvailableClientProvider(spec, registration) {
47
+ if (registration !== undefined) {
48
+ return {
49
+ provide: spec.token,
50
+ inject: [tokens_1.ZLINK_FRAMEWORK_RUNTIME],
51
+ useFactory: (runtime) => spec.create(registration, runtime)
52
+ };
53
+ }
54
+ return {
55
+ provide: spec.token,
56
+ inject: [tokens_1.ZLINK_FRAMEWORK_REGISTRATION, tokens_1.ZLINK_FRAMEWORK_RUNTIME],
57
+ useFactory: (resolved, runtime) => spec.create(resolved, runtime)
58
+ };
59
+ }
60
+ function alwaysAvailableClientTokens() {
61
+ return [
62
+ tokens_1.ZLINK_CHANNEL_CLIENT,
63
+ tokens_1.ZLINK_ROUTE_CLIENT,
64
+ tokens_1.ZLINK_FANOUT_CLIENT,
65
+ tokens_1.ZLINK_BOUND_SESSION_FACTORY,
66
+ tokens_1.ZLINK_MESSAGE_METADATA_POLICY,
67
+ ];
68
+ }
69
+ function conditionalClientProviders(registration) {
70
+ return CONDITIONAL_CLIENT_PROVIDER_SPECS
71
+ .filter((spec) => spec.isEnabled(registration))
72
+ .map((spec) => createConditionalClientProvider(spec, registration));
73
+ }
74
+ const CONDITIONAL_CLIENT_PROVIDER_SPECS = [
75
+ {
76
+ token: tokens_1.ZLINK_CLIENT_SERVER_RUNTIME,
77
+ requiresRuntime: true,
78
+ isEnabled: (registration) => [...registration.channels.values()]
79
+ .some(channel => channel.client !== undefined || channel.server !== undefined),
80
+ create: (_registration, runtime) => requireRuntime(runtime).clientServerRuntime
81
+ },
82
+ {
83
+ token: tokens_1.ZLINK_FANOUT_RUNTIME,
84
+ requiresRuntime: true,
85
+ isEnabled: (registration) => [...registration.channels.values()]
86
+ .some(channel => channel.subscriber !== undefined
87
+ && (channel.subscriber.manualConnections?.length ?? 0) === 0),
88
+ create: (_registration, runtime) => requireRuntime(runtime).fanoutRuntime
89
+ },
90
+ {
91
+ token: tokens_1.ZLINK_ROUTE_MESH_RUNTIME_OPTIONS,
92
+ requiresRuntime: true,
93
+ isEnabled: (registration) => registration.spotNodes.size > 0,
94
+ create: (_registration, runtime) => requireRuntime(runtime).routeMeshRuntimeOptions
95
+ },
96
+ {
97
+ token: tokens_1.ZLINK_ROUTE_MESH_RUNTIME,
98
+ requiresRuntime: true,
99
+ isEnabled: (registration) => registration.spotNodes.size > 0,
100
+ create: (_registration, runtime) => requireRuntime(runtime).routeMeshRuntime
101
+ },
102
+ {
103
+ token: tokens_1.ZLINK_SPOT_MANAGER,
104
+ requiresRuntime: true,
105
+ isEnabled: (registration) => framework_loader_1.framework.hasSpotNode(registration) && hasLocationStores(registration),
106
+ create: (registration, runtime, moduleRef, discovery) => createSpotManager(registration, requireRuntime(runtime), moduleRef, discovery)
107
+ },
108
+ {
109
+ token: tokens_1.ZLINK_SPOT_OUTBOUND,
110
+ requiresRuntime: true,
111
+ isEnabled: (registration) => framework_loader_1.framework.hasSpotNode(registration),
112
+ create: (registration, runtime, moduleRef, discovery) => createSpotOutbound(registration, requireRuntime(runtime), moduleRef, discovery)
113
+ },
114
+ {
115
+ token: tokens_1.ZLINK_SPOT_PUBLISHER_CLIENT,
116
+ requiresRuntime: true,
117
+ isEnabled: (registration) => framework_loader_1.framework.hasSpotPublisherClient(registration),
118
+ create: (registration, runtime) => framework_loader_1.framework.createIntegrationSpotPublisherClient(registration, requireRuntime(runtime))
119
+ },
120
+ {
121
+ token: tokens_1.ZLINK_ACTOR_CLIENT,
122
+ requiresRuntime: true,
123
+ isEnabled: (registration) => framework_loader_1.framework.hasSpotNode(registration) && hasLocationStores(registration),
124
+ create: (_registration, runtime) => framework_loader_1.framework.createIntegrationActorClient(requireRuntime(runtime))
125
+ },
126
+ {
127
+ token: tokens_1.ZLINK_ACTOR_MANAGER,
128
+ requiresRuntime: true,
129
+ isEnabled: (registration) => framework_loader_1.framework.hasActorManager(registration),
130
+ create: async (registration, runtime, moduleRef, discovery) => {
131
+ const host = requireRuntime(runtime);
132
+ return framework_loader_1.framework.createIntegrationActorManager(registration, host, moduleRef === undefined ? undefined : createProviderResolver(moduleRef, discovery));
133
+ }
134
+ },
135
+ {
136
+ token: tokens_1.ZLINK_LOCATION_RUNTIME_QUERY,
137
+ requiresRuntime: true,
138
+ isEnabled: (registration) => hasLocationStores(registration),
139
+ create: (_registration, runtime) => {
140
+ const query = requireRuntime(runtime).locationRuntimeQuery;
141
+ if (query === undefined) {
142
+ throw new framework_loader_1.framework.ZLinkConfigurationException('Location runtime query requires location stores.');
143
+ }
144
+ return query;
145
+ }
146
+ },
147
+ {
148
+ token: internal_tokens_1.ZLINK_SPOT_HANDLE_RESOLVER,
149
+ requiresRuntime: true,
150
+ isEnabled: (registration) => hasLocationStores(registration),
151
+ create: (_registration, runtime) => {
152
+ const resolver = requireRuntime(runtime).createLocationHandleResolver();
153
+ if (resolver === undefined) {
154
+ throw new framework_loader_1.framework.ZLinkConfigurationException('SpotHandle resolver requires location stores.');
155
+ }
156
+ return resolver;
157
+ }
158
+ },
159
+ {
160
+ token: internal_tokens_1.ZLINK_ACTOR_SPOT_HANDLE_RESOLVER,
161
+ requiresRuntime: true,
162
+ isEnabled: (registration) => hasLocationStores(registration),
163
+ create: (_registration, runtime) => {
164
+ const resolver = requireRuntime(runtime).createLocationHandleResolver();
165
+ if (resolver === undefined) {
166
+ throw new framework_loader_1.framework.ZLinkConfigurationException('Actor SpotHandle resolver requires location stores.');
167
+ }
168
+ return resolver;
169
+ }
170
+ }
171
+ ];
172
+ function conditionalClientProvidersForFactory() {
173
+ return CONDITIONAL_CLIENT_PROVIDER_SPECS.map(createConditionalClientProviderForFactory);
174
+ }
175
+ function createConditionalClientProviderForFactory(spec) {
176
+ return createConditionalClientProviderFromSpec(spec, { checkEnabled: true });
177
+ }
178
+ function createConditionalClientProvider(spec, registration) {
179
+ return createConditionalClientProviderFromSpec(spec, { registration, checkEnabled: false });
180
+ }
181
+ function createConditionalClientProviderFromSpec(spec, options) {
182
+ return {
183
+ provide: spec.token,
184
+ inject: conditionalClientProviderInject(spec, options),
185
+ useFactory: (...args) => {
186
+ const { registration, runtime, moduleRef, discovery } = conditionalClientProviderArgs(spec, options, args);
187
+ if (options.checkEnabled && !spec.isEnabled(registration)) {
188
+ return null;
189
+ }
190
+ return spec.create(registration, runtime, moduleRef, discovery);
191
+ }
192
+ };
193
+ }
194
+ function conditionalClientProviderInject(spec, options) {
195
+ return [
196
+ ...(options.registration === undefined ? [tokens_1.ZLINK_FRAMEWORK_REGISTRATION] : []),
197
+ ...(spec.requiresRuntime ? [tokens_1.ZLINK_FRAMEWORK_RUNTIME] : []),
198
+ core_1.ModuleRef,
199
+ core_1.DiscoveryService
200
+ ];
201
+ }
202
+ function conditionalClientProviderArgs(spec, options, args) {
203
+ let index = 0;
204
+ const registration = options.registration ?? args[index++];
205
+ const runtime = spec.requiresRuntime ? args[index++] : undefined;
206
+ const moduleRef = args[index++];
207
+ const discovery = args[index++];
208
+ return { registration, runtime, moduleRef, discovery };
209
+ }
210
+ function requireRuntime(runtime) {
211
+ if (runtime === undefined) {
212
+ throw new framework_loader_1.framework.ZLinkConfigurationException('ZLink runtime host is not available.');
213
+ }
214
+ return runtime;
215
+ }
216
+ function conditionalClientTokens() {
217
+ return [
218
+ tokens_1.ZLINK_CLIENT_SERVER_RUNTIME,
219
+ tokens_1.ZLINK_FANOUT_RUNTIME,
220
+ tokens_1.ZLINK_ROUTE_MESH_RUNTIME_OPTIONS,
221
+ tokens_1.ZLINK_ROUTE_MESH_RUNTIME,
222
+ tokens_1.ZLINK_SPOT_MANAGER,
223
+ tokens_1.ZLINK_SPOT_OUTBOUND,
224
+ tokens_1.ZLINK_SPOT_PUBLISHER_CLIENT,
225
+ tokens_1.ZLINK_ACTOR_CLIENT,
226
+ tokens_1.ZLINK_ACTOR_MANAGER,
227
+ tokens_1.ZLINK_LOCATION_RUNTIME_QUERY
228
+ ];
229
+ }
230
+ function hasLocationStores(registration) {
231
+ return registration.locations.useInMemoryStores
232
+ || registration.locations.storeInstance !== undefined;
233
+ }
234
+ function createRuntimeHost(registration, moduleRef, discovery) {
235
+ const runtime = framework_loader_1.framework.createIntegrationRuntimeHost(registration, createProviderResolver(moduleRef, discovery));
236
+ runtime.onModuleInit = async () => {
237
+ await runtime.start();
238
+ };
239
+ runtime.onModuleDestroy = async () => {
240
+ await runtime.shutdown();
241
+ };
242
+ runtime.onApplicationBootstrap = async () => { };
243
+ return runtime;
244
+ }
245
+ function createProviderResolver(moduleRef, discovery) {
246
+ const resolver = {
247
+ get(type) {
248
+ const discovered = findDiscoveredProviderInstance(discovery, type);
249
+ if (discovered !== undefined) {
250
+ return discovered;
251
+ }
252
+ try {
253
+ return moduleRef.get(type, { strict: false });
254
+ }
255
+ catch {
256
+ return undefined;
257
+ }
258
+ },
259
+ async create(type) {
260
+ try {
261
+ // Spot and actor lifecycles request a fresh application object for
262
+ // each activation. ModuleRef.resolve() returns the registered
263
+ // singleton when the application also lists that class as a Nest
264
+ // provider, which would make later Spot contexts overwrite earlier
265
+ // activations. ModuleRef.create() preserves dependency injection
266
+ // while creating an independent object.
267
+ return await moduleRef.create(type);
268
+ }
269
+ catch {
270
+ // Fall back to direct construction through Nest for classes that are
271
+ // not registered as providers.
272
+ }
273
+ return await moduleRef.resolve(type, undefined, { strict: false });
274
+ }
275
+ };
276
+ Object.defineProperty(resolver, Symbol.for('@zlink-systems/framework.handler-instance-scope-factory'), {
277
+ value: {
278
+ create(context) {
279
+ const currentContextId = (0, dispatch_scope_1.currentNestDispatchContext)();
280
+ const contextId = currentContextId ?? core_1.ContextIdFactory.create();
281
+ if (context !== undefined && currentContextId === undefined) {
282
+ moduleRef.registerRequestByContextId({ zlinkContext: context }, contextId);
283
+ }
284
+ const instances = new Map();
285
+ const dependencies = new Map();
286
+ const owned = [];
287
+ let disposed = false;
288
+ return {
289
+ async resolve(type) {
290
+ if (disposed) {
291
+ throw new Error('Handler instance scope is already disposed.');
292
+ }
293
+ let instance = instances.get(type);
294
+ if (instance === undefined) {
295
+ instance = createNestHandlerInstance(moduleRef, contextId, dependencies, type)
296
+ .then(async (created) => {
297
+ if (disposed) {
298
+ await disposeNestOwnedHandler(created);
299
+ throw new Error('Handler instance scope was disposed during activation.');
300
+ }
301
+ owned.push(created);
302
+ return created;
303
+ });
304
+ instances.set(type, instance);
305
+ }
306
+ return await instance;
307
+ },
308
+ async dispose() {
309
+ if (disposed)
310
+ return;
311
+ disposed = true;
312
+ const pending = [...instances.values()];
313
+ await Promise.allSettled(pending);
314
+ for (let index = owned.length - 1; index >= 0; index -= 1) {
315
+ await disposeNestOwnedHandler(owned[index]);
316
+ }
317
+ owned.length = 0;
318
+ instances.clear();
319
+ dependencies.clear();
320
+ }
321
+ };
322
+ }
323
+ },
324
+ enumerable: false
325
+ });
326
+ framework_loader_1.framework.registerIntegrationHandlerFilterScope(resolver, (context, callback) => (0, dispatch_scope_1.runInNestDispatchScope)(moduleRef, context, async () => {
327
+ const contextId = (0, dispatch_scope_1.currentNestDispatchContext)();
328
+ const dependencies = new Map();
329
+ const owned = [];
330
+ try {
331
+ return await callback({
332
+ async resolve(type) {
333
+ const instance = await createNestHandlerInstance(moduleRef, contextId, dependencies, type);
334
+ owned.push(instance);
335
+ return instance;
336
+ }
337
+ });
338
+ }
339
+ finally {
340
+ for (let index = owned.length - 1; index >= 0; index -= 1) {
341
+ await disposeNestOwnedHandler(owned[index]);
342
+ }
343
+ }
344
+ }));
345
+ return resolver;
346
+ }
347
+ async function disposeNestOwnedHandler(instance) {
348
+ if (instance === null || instance === undefined)
349
+ return;
350
+ const value = instance;
351
+ if (typeof value.dispose === 'function') {
352
+ await value.dispose();
353
+ }
354
+ else if (typeof value.close === 'function') {
355
+ await value.close();
356
+ }
357
+ else if (typeof value.onModuleDestroy === 'function') {
358
+ await value.onModuleDestroy();
359
+ }
360
+ }
361
+ async function createNestHandlerInstance(moduleRef, contextId, dependencies, type) {
362
+ const reflected = [
363
+ ...(Reflect.getMetadata(constants_1.PARAMTYPES_METADATA, type) ?? [])
364
+ ];
365
+ const declared = Reflect.getMetadata(constants_1.SELF_DECLARED_DEPS_METADATA, type);
366
+ for (const dependency of declared ?? []) {
367
+ reflected[dependency.index] = dependency.param;
368
+ }
369
+ const optional = new Set(Reflect.getMetadata(constants_1.OPTIONAL_DEPS_METADATA, type) ?? []);
370
+ const parameters = await Promise.all(reflected.map((token, index) => resolveNestHandlerDependency(moduleRef, contextId, dependencies, token, optional.has(index))));
371
+ const instance = new type(...parameters);
372
+ const properties = Reflect.getMetadata(constants_1.PROPERTY_DEPS_METADATA, type);
373
+ const optionalProperties = new Set(Reflect.getMetadata(constants_1.OPTIONAL_PROPERTY_DEPS_METADATA, type) ?? []);
374
+ for (const property of properties ?? []) {
375
+ const dependency = await resolveNestHandlerDependency(moduleRef, contextId, dependencies, property.type, optionalProperties.has(property.key));
376
+ if (dependency !== undefined) {
377
+ instance[property.key] = dependency;
378
+ }
379
+ }
380
+ return instance;
381
+ }
382
+ async function resolveNestHandlerDependency(moduleRef, contextId, dependencies, token, optional) {
383
+ const forwardReference = typeof token === 'object'
384
+ && token !== null
385
+ && 'forwardRef' in token
386
+ ? token
387
+ : undefined;
388
+ const resolvedToken = typeof forwardReference?.forwardRef === 'function'
389
+ ? forwardReference.forwardRef()
390
+ : token;
391
+ let dependency = dependencies.get(resolvedToken);
392
+ if (dependency === undefined) {
393
+ dependency = moduleRef.resolve(resolvedToken, contextId, { strict: false });
394
+ dependencies.set(resolvedToken, dependency);
395
+ }
396
+ try {
397
+ return await dependency;
398
+ }
399
+ catch (error) {
400
+ dependencies.delete(resolvedToken);
401
+ if (optional)
402
+ return undefined;
403
+ throw error;
404
+ }
405
+ }
406
+ function findDiscoveredProviderInstance(discovery, type) {
407
+ for (const wrapper of discovery?.getProviders() ?? []) {
408
+ if (wrapper.instance !== undefined
409
+ && wrapper.instance !== null
410
+ && (wrapper.token === type
411
+ || wrapper.metatype === type
412
+ || wrapper.instance.constructor === type)) {
413
+ return wrapper.instance;
414
+ }
415
+ }
416
+ return undefined;
417
+ }
418
+ function providerToken(provider) {
419
+ return typeof provider === 'function' ? provider : provider.provide;
420
+ }
421
+ async function createSpotManager(registration, runtime, moduleRef, discovery) {
422
+ return framework_loader_1.framework.createIntegrationSpotManager(registration, runtime, moduleRef === undefined ? undefined : createProviderResolver(moduleRef, discovery));
423
+ }
424
+ async function createSpotOutbound(_registration, runtime, _moduleRef, _discovery) {
425
+ return framework_loader_1.framework.createIntegrationSpotOutbound(runtime);
426
+ }
@@ -0,0 +1,7 @@
1
+ import type { DiscoveryService, ModuleRef } from '@nestjs/core';
2
+ import type { ZLinkFrameworkRegistrationOptions } from './framework-integration-contracts';
3
+ import { type ZLinkModuleOptions, type ZLinkNestModuleRegistrationOptions } from './contracts';
4
+ export declare function hasNestHandlerDiscovery(options: ZLinkNestModuleRegistrationOptions): boolean;
5
+ export declare function createDiscoveredOptions(options: ZLinkNestModuleRegistrationOptions, discovery: DiscoveryService, moduleRef: ModuleRef): ZLinkFrameworkRegistrationOptions;
6
+ export declare function createRegistrationOptions(options: ZLinkNestModuleRegistrationOptions): ZLinkFrameworkRegistrationOptions;
7
+ export declare function assertBuiltModuleOptions(options: ZLinkModuleOptions): ZLinkNestModuleRegistrationOptions;