@veloxts/core 0.3.3 → 0.3.5
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 +697 -16
- package/dist/app.d.ts +67 -10
- package/dist/app.d.ts.map +1 -1
- package/dist/app.js +79 -12
- package/dist/app.js.map +1 -1
- package/dist/context.d.ts +26 -1
- package/dist/context.d.ts.map +1 -1
- package/dist/context.js +29 -0
- package/dist/context.js.map +1 -1
- package/dist/di/container.d.ts +406 -0
- package/dist/di/container.d.ts.map +1 -0
- package/dist/di/container.js +699 -0
- package/dist/di/container.js.map +1 -0
- package/dist/di/decorators.d.ts +235 -0
- package/dist/di/decorators.d.ts.map +1 -0
- package/dist/di/decorators.js +297 -0
- package/dist/di/decorators.js.map +1 -0
- package/dist/di/index.d.ts +65 -0
- package/dist/di/index.d.ts.map +1 -0
- package/dist/di/index.js +73 -0
- package/dist/di/index.js.map +1 -0
- package/dist/di/providers.d.ts +397 -0
- package/dist/di/providers.d.ts.map +1 -0
- package/dist/di/providers.js +380 -0
- package/dist/di/providers.js.map +1 -0
- package/dist/di/scope.d.ts +230 -0
- package/dist/di/scope.d.ts.map +1 -0
- package/dist/di/scope.js +294 -0
- package/dist/di/scope.js.map +1 -0
- package/dist/di/tokens.d.ts +227 -0
- package/dist/di/tokens.d.ts.map +1 -0
- package/dist/di/tokens.js +192 -0
- package/dist/di/tokens.js.map +1 -0
- package/dist/errors/catalog.d.ts +79 -0
- package/dist/errors/catalog.d.ts.map +1 -0
- package/dist/errors/catalog.js +492 -0
- package/dist/errors/catalog.js.map +1 -0
- package/dist/errors/formatter.d.ts +101 -0
- package/dist/errors/formatter.d.ts.map +1 -0
- package/dist/errors/formatter.js +330 -0
- package/dist/errors/formatter.js.map +1 -0
- package/dist/errors/index.d.ts +14 -0
- package/dist/errors/index.d.ts.map +1 -0
- package/dist/errors/index.js +16 -0
- package/dist/errors/index.js.map +1 -0
- package/dist/errors.d.ts +35 -5
- package/dist/errors.d.ts.map +1 -1
- package/dist/errors.js +57 -4
- package/dist/errors.js.map +1 -1
- package/dist/index.d.ts +10 -6
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +29 -6
- package/dist/index.js.map +1 -1
- package/package.json +14 -2
|
@@ -0,0 +1,380 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Provider types and registration interfaces for dependency injection
|
|
3
|
+
*
|
|
4
|
+
* Providers define how services are created and configured.
|
|
5
|
+
* VeloxTS supports four provider types:
|
|
6
|
+
* - Class providers: Instantiate a class
|
|
7
|
+
* - Factory providers: Use a factory function
|
|
8
|
+
* - Value providers: Use an existing value
|
|
9
|
+
* - Existing providers: Alias another token
|
|
10
|
+
*
|
|
11
|
+
* @module di/providers
|
|
12
|
+
*/
|
|
13
|
+
import { VeloxError } from '../errors.js';
|
|
14
|
+
import { getDefaultScope, isValidScope, Scope } from './scope.js';
|
|
15
|
+
import { getTokenName, validateToken } from './tokens.js';
|
|
16
|
+
// ============================================================================
|
|
17
|
+
// Provider Type Guards
|
|
18
|
+
// ============================================================================
|
|
19
|
+
/**
|
|
20
|
+
* Type guard for class providers
|
|
21
|
+
*/
|
|
22
|
+
export function isClassProvider(provider) {
|
|
23
|
+
return 'useClass' in provider && typeof provider.useClass === 'function';
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Type guard for factory providers
|
|
27
|
+
*/
|
|
28
|
+
export function isFactoryProvider(provider) {
|
|
29
|
+
return 'useFactory' in provider && typeof provider.useFactory === 'function';
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Type guard for value providers
|
|
33
|
+
*/
|
|
34
|
+
export function isValueProvider(provider) {
|
|
35
|
+
return 'useValue' in provider;
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* Type guard for existing/alias providers
|
|
39
|
+
*/
|
|
40
|
+
export function isExistingProvider(provider) {
|
|
41
|
+
return 'useExisting' in provider;
|
|
42
|
+
}
|
|
43
|
+
// ============================================================================
|
|
44
|
+
// Provider Validation
|
|
45
|
+
// ============================================================================
|
|
46
|
+
/**
|
|
47
|
+
* Validates a provider configuration
|
|
48
|
+
*
|
|
49
|
+
* @param provider - The provider to validate
|
|
50
|
+
* @throws {VeloxError} If the provider is invalid
|
|
51
|
+
*/
|
|
52
|
+
export function validateProvider(provider) {
|
|
53
|
+
// Check provider is an object
|
|
54
|
+
if (typeof provider !== 'object' || provider === null) {
|
|
55
|
+
throw new VeloxError('Provider must be an object', 500, 'INVALID_PROVIDER');
|
|
56
|
+
}
|
|
57
|
+
// Check 'provide' token exists
|
|
58
|
+
if (!('provide' in provider)) {
|
|
59
|
+
throw new VeloxError('Provider must have a "provide" token', 500, 'INVALID_PROVIDER');
|
|
60
|
+
}
|
|
61
|
+
// Validate the token
|
|
62
|
+
validateToken(provider.provide);
|
|
63
|
+
const typedProvider = provider;
|
|
64
|
+
// Check that exactly one of the provider type properties exists
|
|
65
|
+
const providerTypes = ['useClass', 'useFactory', 'useValue', 'useExisting'];
|
|
66
|
+
const definedTypes = providerTypes.filter((type) => type in typedProvider);
|
|
67
|
+
if (definedTypes.length === 0) {
|
|
68
|
+
throw new VeloxError('Provider must specify one of: useClass, useFactory, useValue, or useExisting', 500, 'INVALID_PROVIDER');
|
|
69
|
+
}
|
|
70
|
+
if (definedTypes.length > 1) {
|
|
71
|
+
throw new VeloxError(`Provider cannot have multiple types. Found: ${definedTypes.join(', ')}`, 500, 'INVALID_PROVIDER');
|
|
72
|
+
}
|
|
73
|
+
// Validate scope if provided
|
|
74
|
+
if ('scope' in typedProvider && typedProvider.scope !== undefined) {
|
|
75
|
+
if (!isValidScope(typedProvider.scope)) {
|
|
76
|
+
throw new VeloxError(`Invalid scope: ${String(typedProvider.scope)}. Must be one of: singleton, transient, request`, 500, 'INVALID_PROVIDER');
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
// Validate specific provider types
|
|
80
|
+
if ('useClass' in typedProvider) {
|
|
81
|
+
if (typeof typedProvider.useClass !== 'function') {
|
|
82
|
+
throw new VeloxError('useClass must be a class constructor', 500, 'INVALID_PROVIDER');
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
if ('useFactory' in typedProvider) {
|
|
86
|
+
if (typeof typedProvider.useFactory !== 'function') {
|
|
87
|
+
throw new VeloxError('useFactory must be a function', 500, 'INVALID_PROVIDER');
|
|
88
|
+
}
|
|
89
|
+
if ('inject' in typedProvider && typedProvider.inject !== undefined) {
|
|
90
|
+
if (!Array.isArray(typedProvider.inject)) {
|
|
91
|
+
throw new VeloxError('Factory inject must be an array of injection tokens', 500, 'INVALID_PROVIDER');
|
|
92
|
+
}
|
|
93
|
+
// Validate each inject token
|
|
94
|
+
for (const token of typedProvider.inject) {
|
|
95
|
+
validateToken(token);
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
if ('useExisting' in typedProvider) {
|
|
100
|
+
validateToken(typedProvider.useExisting);
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
/**
|
|
104
|
+
* Normalizes a provider to a consistent internal format
|
|
105
|
+
*
|
|
106
|
+
* @param provider - The provider to normalize
|
|
107
|
+
* @returns The normalized provider
|
|
108
|
+
*
|
|
109
|
+
* @internal
|
|
110
|
+
*/
|
|
111
|
+
export function normalizeProvider(provider) {
|
|
112
|
+
const scope = provider.scope ?? getDefaultScope();
|
|
113
|
+
if (isClassProvider(provider)) {
|
|
114
|
+
return {
|
|
115
|
+
provide: provider.provide,
|
|
116
|
+
scope,
|
|
117
|
+
type: 'class',
|
|
118
|
+
implementation: {
|
|
119
|
+
class: provider.useClass,
|
|
120
|
+
},
|
|
121
|
+
};
|
|
122
|
+
}
|
|
123
|
+
if (isFactoryProvider(provider)) {
|
|
124
|
+
return {
|
|
125
|
+
provide: provider.provide,
|
|
126
|
+
scope,
|
|
127
|
+
type: 'factory',
|
|
128
|
+
implementation: {
|
|
129
|
+
factory: provider.useFactory,
|
|
130
|
+
inject: provider.inject,
|
|
131
|
+
},
|
|
132
|
+
};
|
|
133
|
+
}
|
|
134
|
+
if (isValueProvider(provider)) {
|
|
135
|
+
// Value providers are always effectively singleton since they use the same value
|
|
136
|
+
return {
|
|
137
|
+
provide: provider.provide,
|
|
138
|
+
scope: Scope.SINGLETON,
|
|
139
|
+
type: 'value',
|
|
140
|
+
implementation: {
|
|
141
|
+
value: provider.useValue,
|
|
142
|
+
},
|
|
143
|
+
};
|
|
144
|
+
}
|
|
145
|
+
if (isExistingProvider(provider)) {
|
|
146
|
+
return {
|
|
147
|
+
provide: provider.provide,
|
|
148
|
+
scope, // Inherit scope from the aliased provider at resolution time
|
|
149
|
+
type: 'existing',
|
|
150
|
+
implementation: {
|
|
151
|
+
existing: provider.useExisting,
|
|
152
|
+
},
|
|
153
|
+
};
|
|
154
|
+
}
|
|
155
|
+
// This should never happen due to validation, but TypeScript needs it
|
|
156
|
+
throw new VeloxError('Unknown provider type', 500, 'INVALID_PROVIDER');
|
|
157
|
+
}
|
|
158
|
+
// ============================================================================
|
|
159
|
+
// Convenience Provider Builders
|
|
160
|
+
// ============================================================================
|
|
161
|
+
/**
|
|
162
|
+
* Creates a class provider with type inference
|
|
163
|
+
*
|
|
164
|
+
* @param cls - The class to provide
|
|
165
|
+
* @param scope - The lifecycle scope
|
|
166
|
+
* @returns A class provider configuration
|
|
167
|
+
*
|
|
168
|
+
* @example
|
|
169
|
+
* ```typescript
|
|
170
|
+
* container.register(asClass(UserService, Scope.REQUEST));
|
|
171
|
+
* ```
|
|
172
|
+
*/
|
|
173
|
+
export function asClass(cls, scope = Scope.SINGLETON) {
|
|
174
|
+
return {
|
|
175
|
+
provide: cls,
|
|
176
|
+
useClass: cls,
|
|
177
|
+
scope,
|
|
178
|
+
};
|
|
179
|
+
}
|
|
180
|
+
/**
|
|
181
|
+
* Creates a factory provider with type inference
|
|
182
|
+
*
|
|
183
|
+
* @param token - The token to provide
|
|
184
|
+
* @param factory - The factory function
|
|
185
|
+
* @param options - Factory options (inject, scope)
|
|
186
|
+
* @returns A factory provider configuration
|
|
187
|
+
*
|
|
188
|
+
* @example
|
|
189
|
+
* ```typescript
|
|
190
|
+
* container.register(asFactory(
|
|
191
|
+
* DATABASE,
|
|
192
|
+
* (config: ConfigService) => createDb(config.dbUrl),
|
|
193
|
+
* { inject: [ConfigService] }
|
|
194
|
+
* ));
|
|
195
|
+
* ```
|
|
196
|
+
*/
|
|
197
|
+
export function asFactory(token, factory, options = {}) {
|
|
198
|
+
return {
|
|
199
|
+
provide: token,
|
|
200
|
+
useFactory: factory,
|
|
201
|
+
inject: options.inject,
|
|
202
|
+
scope: options.scope ?? Scope.SINGLETON,
|
|
203
|
+
};
|
|
204
|
+
}
|
|
205
|
+
/**
|
|
206
|
+
* Creates a value provider with type inference
|
|
207
|
+
*
|
|
208
|
+
* @param token - The token to provide
|
|
209
|
+
* @param value - The value to use
|
|
210
|
+
* @returns A value provider configuration
|
|
211
|
+
*
|
|
212
|
+
* @example
|
|
213
|
+
* ```typescript
|
|
214
|
+
* container.register(asValue(CONFIG, { port: 3210 }));
|
|
215
|
+
* ```
|
|
216
|
+
*/
|
|
217
|
+
export function asValue(token, value) {
|
|
218
|
+
return {
|
|
219
|
+
provide: token,
|
|
220
|
+
useValue: value,
|
|
221
|
+
};
|
|
222
|
+
}
|
|
223
|
+
/**
|
|
224
|
+
* Creates an existing/alias provider with type inference
|
|
225
|
+
*
|
|
226
|
+
* @param token - The token to provide (alias)
|
|
227
|
+
* @param existing - The token to alias to
|
|
228
|
+
* @returns An existing provider configuration
|
|
229
|
+
*
|
|
230
|
+
* @example
|
|
231
|
+
* ```typescript
|
|
232
|
+
* container.register(asExisting(LOGGER, ConsoleLogger));
|
|
233
|
+
* ```
|
|
234
|
+
*/
|
|
235
|
+
export function asExisting(token, existing) {
|
|
236
|
+
return {
|
|
237
|
+
provide: token,
|
|
238
|
+
useExisting: existing,
|
|
239
|
+
};
|
|
240
|
+
}
|
|
241
|
+
// ============================================================================
|
|
242
|
+
// Succinct Scope Helpers
|
|
243
|
+
// ============================================================================
|
|
244
|
+
/**
|
|
245
|
+
* Creates a singleton class provider
|
|
246
|
+
*
|
|
247
|
+
* Singleton services are instantiated once and shared across all requests.
|
|
248
|
+
* This is the default scope and the most common pattern.
|
|
249
|
+
*
|
|
250
|
+
* @param cls - The class to provide as a singleton
|
|
251
|
+
* @returns A class provider configured as singleton
|
|
252
|
+
*
|
|
253
|
+
* @example
|
|
254
|
+
* ```typescript
|
|
255
|
+
* container.register(singleton(ConfigService));
|
|
256
|
+
* container.register(singleton(DatabasePool));
|
|
257
|
+
* ```
|
|
258
|
+
*/
|
|
259
|
+
export function singleton(cls) {
|
|
260
|
+
return {
|
|
261
|
+
provide: cls,
|
|
262
|
+
useClass: cls,
|
|
263
|
+
scope: Scope.SINGLETON,
|
|
264
|
+
};
|
|
265
|
+
}
|
|
266
|
+
/**
|
|
267
|
+
* Creates a request-scoped class provider
|
|
268
|
+
*
|
|
269
|
+
* Request-scoped services are instantiated once per HTTP request.
|
|
270
|
+
* Ideal for services that need request-specific state.
|
|
271
|
+
*
|
|
272
|
+
* @param cls - The class to provide with request scope
|
|
273
|
+
* @returns A class provider configured as request-scoped
|
|
274
|
+
*
|
|
275
|
+
* @example
|
|
276
|
+
* ```typescript
|
|
277
|
+
* container.register(scoped(RequestContext));
|
|
278
|
+
* container.register(scoped(UserSession));
|
|
279
|
+
* ```
|
|
280
|
+
*/
|
|
281
|
+
export function scoped(cls) {
|
|
282
|
+
return {
|
|
283
|
+
provide: cls,
|
|
284
|
+
useClass: cls,
|
|
285
|
+
scope: Scope.REQUEST,
|
|
286
|
+
};
|
|
287
|
+
}
|
|
288
|
+
/**
|
|
289
|
+
* Creates a transient class provider
|
|
290
|
+
*
|
|
291
|
+
* Transient services are instantiated every time they are resolved.
|
|
292
|
+
* Useful for stateful objects that should not be shared.
|
|
293
|
+
*
|
|
294
|
+
* @param cls - The class to provide as transient
|
|
295
|
+
* @returns A class provider configured as transient
|
|
296
|
+
*
|
|
297
|
+
* @example
|
|
298
|
+
* ```typescript
|
|
299
|
+
* container.register(transient(EmailBuilder));
|
|
300
|
+
* container.register(transient(RequestId));
|
|
301
|
+
* ```
|
|
302
|
+
*/
|
|
303
|
+
export function transient(cls) {
|
|
304
|
+
return {
|
|
305
|
+
provide: cls,
|
|
306
|
+
useClass: cls,
|
|
307
|
+
scope: Scope.TRANSIENT,
|
|
308
|
+
};
|
|
309
|
+
}
|
|
310
|
+
/**
|
|
311
|
+
* Creates a value provider (convenience alias)
|
|
312
|
+
*
|
|
313
|
+
* @param token - The token to provide
|
|
314
|
+
* @param val - The value to use
|
|
315
|
+
* @returns A value provider configuration
|
|
316
|
+
*
|
|
317
|
+
* @example
|
|
318
|
+
* ```typescript
|
|
319
|
+
* container.register(value(CONFIG, { port: 3210 }));
|
|
320
|
+
* ```
|
|
321
|
+
*/
|
|
322
|
+
export function value(token, val) {
|
|
323
|
+
return {
|
|
324
|
+
provide: token,
|
|
325
|
+
useValue: val,
|
|
326
|
+
};
|
|
327
|
+
}
|
|
328
|
+
/**
|
|
329
|
+
* Creates a factory provider (convenience alias)
|
|
330
|
+
*
|
|
331
|
+
* @param token - The token to provide
|
|
332
|
+
* @param factoryFn - The factory function
|
|
333
|
+
* @param deps - Dependencies to inject into the factory
|
|
334
|
+
* @returns A factory provider configuration
|
|
335
|
+
*
|
|
336
|
+
* @example
|
|
337
|
+
* ```typescript
|
|
338
|
+
* container.register(factory(DATABASE, createDb, [ConfigService]));
|
|
339
|
+
* ```
|
|
340
|
+
*/
|
|
341
|
+
export function factory(token, factoryFn, deps) {
|
|
342
|
+
return {
|
|
343
|
+
provide: token,
|
|
344
|
+
useFactory: factoryFn,
|
|
345
|
+
inject: deps,
|
|
346
|
+
scope: Scope.SINGLETON,
|
|
347
|
+
};
|
|
348
|
+
}
|
|
349
|
+
// ============================================================================
|
|
350
|
+
// Provider Description (for debugging)
|
|
351
|
+
// ============================================================================
|
|
352
|
+
/**
|
|
353
|
+
* Gets a human-readable description of a provider
|
|
354
|
+
*
|
|
355
|
+
* @param provider - The provider to describe
|
|
356
|
+
* @returns A string description
|
|
357
|
+
*
|
|
358
|
+
* @internal
|
|
359
|
+
*/
|
|
360
|
+
export function describeProvider(provider) {
|
|
361
|
+
const tokenName = getTokenName(provider.provide);
|
|
362
|
+
const scope = provider.scope ?? 'singleton';
|
|
363
|
+
if (isClassProvider(provider)) {
|
|
364
|
+
const className = provider.useClass.name || 'AnonymousClass';
|
|
365
|
+
return `ClassProvider(${tokenName} => ${className}, ${scope})`;
|
|
366
|
+
}
|
|
367
|
+
if (isFactoryProvider(provider)) {
|
|
368
|
+
const deps = provider.inject?.map(getTokenName).join(', ') ?? 'none';
|
|
369
|
+
return `FactoryProvider(${tokenName}, deps=[${deps}], ${scope})`;
|
|
370
|
+
}
|
|
371
|
+
if (isValueProvider(provider)) {
|
|
372
|
+
return `ValueProvider(${tokenName})`;
|
|
373
|
+
}
|
|
374
|
+
if (isExistingProvider(provider)) {
|
|
375
|
+
const existing = getTokenName(provider.useExisting);
|
|
376
|
+
return `ExistingProvider(${tokenName} => ${existing})`;
|
|
377
|
+
}
|
|
378
|
+
return `Provider(${tokenName})`;
|
|
379
|
+
}
|
|
380
|
+
//# sourceMappingURL=providers.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"providers.js","sourceRoot":"","sources":["../../src/di/providers.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,230 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Lifecycle scope management for dependency injection
|
|
3
|
+
*
|
|
4
|
+
* Defines how service instances are created and shared:
|
|
5
|
+
* - Singleton: One instance for the entire application
|
|
6
|
+
* - Transient: New instance on every resolution
|
|
7
|
+
* - Request: One instance per HTTP request
|
|
8
|
+
*
|
|
9
|
+
* @module di/scope
|
|
10
|
+
*/
|
|
11
|
+
import type { FastifyInstance, FastifyRequest } from 'fastify';
|
|
12
|
+
/**
|
|
13
|
+
* Service lifecycle scope
|
|
14
|
+
*
|
|
15
|
+
* Determines how instances are created and shared across the application.
|
|
16
|
+
*
|
|
17
|
+
* @example
|
|
18
|
+
* ```typescript
|
|
19
|
+
* // Singleton - shared across all requests
|
|
20
|
+
* container.register({
|
|
21
|
+
* provide: ConfigService,
|
|
22
|
+
* useClass: ConfigService,
|
|
23
|
+
* scope: Scope.SINGLETON
|
|
24
|
+
* });
|
|
25
|
+
*
|
|
26
|
+
* // Transient - new instance every time
|
|
27
|
+
* container.register({
|
|
28
|
+
* provide: RequestIdGenerator,
|
|
29
|
+
* useClass: RequestIdGenerator,
|
|
30
|
+
* scope: Scope.TRANSIENT
|
|
31
|
+
* });
|
|
32
|
+
*
|
|
33
|
+
* // Request - shared within a single HTTP request
|
|
34
|
+
* container.register({
|
|
35
|
+
* provide: UserContext,
|
|
36
|
+
* useClass: UserContext,
|
|
37
|
+
* scope: Scope.REQUEST
|
|
38
|
+
* });
|
|
39
|
+
* ```
|
|
40
|
+
*/
|
|
41
|
+
export declare enum Scope {
|
|
42
|
+
/**
|
|
43
|
+
* Singleton scope
|
|
44
|
+
*
|
|
45
|
+
* A single instance is created and shared across the entire application.
|
|
46
|
+
* The instance is created on first resolution and reused for all subsequent
|
|
47
|
+
* resolutions.
|
|
48
|
+
*
|
|
49
|
+
* Best for:
|
|
50
|
+
* - Configuration services
|
|
51
|
+
* - Database connection pools
|
|
52
|
+
* - Cache clients
|
|
53
|
+
* - Stateless utility services
|
|
54
|
+
*/
|
|
55
|
+
SINGLETON = "singleton",
|
|
56
|
+
/**
|
|
57
|
+
* Transient scope
|
|
58
|
+
*
|
|
59
|
+
* A new instance is created every time the service is resolved.
|
|
60
|
+
* No caching or sharing occurs.
|
|
61
|
+
*
|
|
62
|
+
* Best for:
|
|
63
|
+
* - Services that maintain mutable state
|
|
64
|
+
* - Factories that produce unique objects
|
|
65
|
+
* - Services where isolation is critical
|
|
66
|
+
*/
|
|
67
|
+
TRANSIENT = "transient",
|
|
68
|
+
/**
|
|
69
|
+
* Request scope
|
|
70
|
+
*
|
|
71
|
+
* A single instance is created and shared within the lifetime of an HTTP request.
|
|
72
|
+
* Different requests get different instances.
|
|
73
|
+
*
|
|
74
|
+
* Best for:
|
|
75
|
+
* - User context/session data
|
|
76
|
+
* - Request-specific caching
|
|
77
|
+
* - Transaction management
|
|
78
|
+
* - Audit logging with request context
|
|
79
|
+
*
|
|
80
|
+
* Note: Resolving request-scoped services outside of a request context
|
|
81
|
+
* will throw an error.
|
|
82
|
+
*/
|
|
83
|
+
REQUEST = "request"
|
|
84
|
+
}
|
|
85
|
+
/**
|
|
86
|
+
* Request-scoped instance store key
|
|
87
|
+
* Using a symbol prevents collision with user-defined properties
|
|
88
|
+
*/
|
|
89
|
+
declare const REQUEST_SCOPE_KEY: unique symbol;
|
|
90
|
+
/**
|
|
91
|
+
* Type augmentation for Fastify request to store scoped instances
|
|
92
|
+
*/
|
|
93
|
+
declare module 'fastify' {
|
|
94
|
+
interface FastifyRequest {
|
|
95
|
+
/**
|
|
96
|
+
* Request-scoped service instance cache
|
|
97
|
+
* @internal
|
|
98
|
+
*/
|
|
99
|
+
[REQUEST_SCOPE_KEY]?: Map<unknown, unknown>;
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
/**
|
|
103
|
+
* Manages service instance lifecycles
|
|
104
|
+
*
|
|
105
|
+
* Handles creation, caching, and cleanup of service instances
|
|
106
|
+
* based on their configured scope.
|
|
107
|
+
*
|
|
108
|
+
* @internal
|
|
109
|
+
*/
|
|
110
|
+
export declare class ScopeManager {
|
|
111
|
+
/**
|
|
112
|
+
* Singleton instance cache
|
|
113
|
+
* Maps tokens to their singleton instances
|
|
114
|
+
*/
|
|
115
|
+
private readonly singletonCache;
|
|
116
|
+
/**
|
|
117
|
+
* Whether request scope hooks have been set up
|
|
118
|
+
*/
|
|
119
|
+
private requestScopeInitialized;
|
|
120
|
+
/**
|
|
121
|
+
* Attaches the scope manager to a Fastify server
|
|
122
|
+
*
|
|
123
|
+
* This sets up the request lifecycle hooks needed for request-scoped services.
|
|
124
|
+
* Must be called before resolving request-scoped services.
|
|
125
|
+
*
|
|
126
|
+
* @param server - Fastify server instance
|
|
127
|
+
*/
|
|
128
|
+
attachToFastify(server: FastifyInstance): void;
|
|
129
|
+
/**
|
|
130
|
+
* Gets a singleton instance from cache
|
|
131
|
+
*
|
|
132
|
+
* @param token - The service token
|
|
133
|
+
* @returns The cached instance or undefined
|
|
134
|
+
*/
|
|
135
|
+
getSingleton<T>(token: unknown): T | undefined;
|
|
136
|
+
/**
|
|
137
|
+
* Stores a singleton instance in cache
|
|
138
|
+
*
|
|
139
|
+
* @param token - The service token
|
|
140
|
+
* @param instance - The instance to cache
|
|
141
|
+
*/
|
|
142
|
+
setSingleton<T>(token: unknown, instance: T): void;
|
|
143
|
+
/**
|
|
144
|
+
* Checks if a singleton instance exists
|
|
145
|
+
*
|
|
146
|
+
* @param token - The service token
|
|
147
|
+
* @returns true if a singleton instance is cached
|
|
148
|
+
*/
|
|
149
|
+
hasSingleton(token: unknown): boolean;
|
|
150
|
+
/**
|
|
151
|
+
* Gets a singleton instance from cache, throwing if not found
|
|
152
|
+
*
|
|
153
|
+
* Use this when you've already verified with hasSingleton()
|
|
154
|
+
*
|
|
155
|
+
* @param token - The service token
|
|
156
|
+
* @returns The cached instance
|
|
157
|
+
* @throws {VeloxError} If no singleton is cached for this token
|
|
158
|
+
*/
|
|
159
|
+
getSingletonOrThrow<T>(token: unknown): T;
|
|
160
|
+
/**
|
|
161
|
+
* Gets a request-scoped instance from the current request's cache
|
|
162
|
+
*
|
|
163
|
+
* @param token - The service token
|
|
164
|
+
* @param request - The current Fastify request
|
|
165
|
+
* @returns The cached instance or undefined
|
|
166
|
+
*/
|
|
167
|
+
getRequestScoped<T>(token: unknown, request: FastifyRequest): T | undefined;
|
|
168
|
+
/**
|
|
169
|
+
* Stores a request-scoped instance in the current request's cache
|
|
170
|
+
*
|
|
171
|
+
* @param token - The service token
|
|
172
|
+
* @param instance - The instance to cache
|
|
173
|
+
* @param request - The current Fastify request
|
|
174
|
+
*/
|
|
175
|
+
setRequestScoped<T>(token: unknown, instance: T, request: FastifyRequest): void;
|
|
176
|
+
/**
|
|
177
|
+
* Checks if a request-scoped instance exists
|
|
178
|
+
*
|
|
179
|
+
* @param token - The service token
|
|
180
|
+
* @param request - The current Fastify request
|
|
181
|
+
* @returns true if a request-scoped instance is cached
|
|
182
|
+
*/
|
|
183
|
+
hasRequestScoped(token: unknown, request: FastifyRequest): boolean;
|
|
184
|
+
/**
|
|
185
|
+
* Gets a request-scoped instance from cache, throwing if not found
|
|
186
|
+
*
|
|
187
|
+
* Use this when you've already verified with hasRequestScoped()
|
|
188
|
+
*
|
|
189
|
+
* @param token - The service token
|
|
190
|
+
* @param request - The current Fastify request
|
|
191
|
+
* @returns The cached instance
|
|
192
|
+
* @throws {VeloxError} If no request-scoped instance is cached for this token
|
|
193
|
+
*/
|
|
194
|
+
getRequestScopedOrThrow<T>(token: unknown, request: FastifyRequest): T;
|
|
195
|
+
/**
|
|
196
|
+
* Validates that request scope is available and returns the request
|
|
197
|
+
*
|
|
198
|
+
* @param request - The current request (may be undefined outside request context)
|
|
199
|
+
* @returns The validated FastifyRequest
|
|
200
|
+
* @throws {VeloxError} If request scope is not available
|
|
201
|
+
*/
|
|
202
|
+
ensureRequestScope(request: FastifyRequest | undefined): FastifyRequest;
|
|
203
|
+
/**
|
|
204
|
+
* Clears all singleton instances
|
|
205
|
+
*
|
|
206
|
+
* Useful for testing or application shutdown.
|
|
207
|
+
*/
|
|
208
|
+
clearSingletons(): void;
|
|
209
|
+
/**
|
|
210
|
+
* Clears all cached instances and resets state
|
|
211
|
+
*
|
|
212
|
+
* @internal
|
|
213
|
+
*/
|
|
214
|
+
reset(): void;
|
|
215
|
+
}
|
|
216
|
+
/**
|
|
217
|
+
* Validates a scope value
|
|
218
|
+
*
|
|
219
|
+
* @param scope - The scope to validate
|
|
220
|
+
* @returns true if the scope is valid
|
|
221
|
+
*/
|
|
222
|
+
export declare function isValidScope(scope: unknown): scope is Scope;
|
|
223
|
+
/**
|
|
224
|
+
* Gets the default scope for a provider
|
|
225
|
+
*
|
|
226
|
+
* @returns The default scope (SINGLETON)
|
|
227
|
+
*/
|
|
228
|
+
export declare function getDefaultScope(): Scope;
|
|
229
|
+
export {};
|
|
230
|
+
//# sourceMappingURL=scope.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"scope.d.ts","sourceRoot":"","sources":["../../src/di/scope.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,OAAO,KAAK,EAAE,eAAe,EAAE,cAAc,EAAE,MAAM,SAAS,CAAC;AAQ/D;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4BG;AACH,oBAAY,KAAK;IACf;;;;;;;;;;;;OAYG;IACH,SAAS,cAAc;IAEvB;;;;;;;;;;OAUG;IACH,SAAS,cAAc;IAEvB;;;;;;;;;;;;;;OAcG;IACH,OAAO,YAAY;CACpB;AAMD;;;GAGG;AACH,QAAA,MAAM,iBAAiB,eAAmC,CAAC;AAE3D;;GAEG;AACH,OAAO,QAAQ,SAAS,CAAC;IACvB,UAAU,cAAc;QACtB;;;WAGG;QACH,CAAC,iBAAiB,CAAC,CAAC,EAAE,GAAG,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;KAC7C;CACF;AAED;;;;;;;GAOG;AACH,qBAAa,YAAY;IACvB;;;OAGG;IACH,OAAO,CAAC,QAAQ,CAAC,cAAc,CAA+B;IAE9D;;OAEG;IACH,OAAO,CAAC,uBAAuB,CAAS;IAExC;;;;;;;OAOG;IACH,eAAe,CAAC,MAAM,EAAE,eAAe,GAAG,IAAI;IAsB9C;;;;;OAKG;IACH,YAAY,CAAC,CAAC,EAAE,KAAK,EAAE,OAAO,GAAG,CAAC,GAAG,SAAS;IAI9C;;;;;OAKG;IACH,YAAY,CAAC,CAAC,EAAE,KAAK,EAAE,OAAO,EAAE,QAAQ,EAAE,CAAC,GAAG,IAAI;IAIlD;;;;;OAKG;IACH,YAAY,CAAC,KAAK,EAAE,OAAO,GAAG,OAAO;IAIrC;;;;;;;;OAQG;IACH,mBAAmB,CAAC,CAAC,EAAE,KAAK,EAAE,OAAO,GAAG,CAAC;IAOzC;;;;;;OAMG;IACH,gBAAgB,CAAC,CAAC,EAAE,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,cAAc,GAAG,CAAC,GAAG,SAAS;IAQ3E;;;;;;OAMG;IACH,gBAAgB,CAAC,CAAC,EAAE,KAAK,EAAE,OAAO,EAAE,QAAQ,EAAE,CAAC,EAAE,OAAO,EAAE,cAAc,GAAG,IAAI;IAY/E;;;;;;OAMG;IACH,gBAAgB,CAAC,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,cAAc,GAAG,OAAO;IAKlE;;;;;;;;;OASG;IACH,uBAAuB,CAAC,CAAC,EAAE,KAAK,EAAE,OAAO,EAAE,OAAO,EAAE,cAAc,GAAG,CAAC;IAYtE;;;;;;OAMG;IACH,kBAAkB,CAAC,OAAO,EAAE,cAAc,GAAG,SAAS,GAAG,cAAc;IAqBvE;;;;OAIG;IACH,eAAe,IAAI,IAAI;IAIvB;;;;OAIG;IACH,KAAK,IAAI,IAAI;CAId;AAMD;;;;;GAKG;AACH,wBAAgB,YAAY,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,KAAK,CAE3D;AAED;;;;GAIG;AACH,wBAAgB,eAAe,IAAI,KAAK,CAEvC"}
|