@codefast/di 0.3.16-canary.1 → 0.3.16-canary.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +18 -0
- package/README.md +4 -4
- package/dist/binding-select.d.mts +1 -1
- package/dist/binding-select.mjs +5 -5
- package/dist/binding.d.mts +28 -28
- package/dist/binding.mjs +8 -8
- package/dist/constraints.d.mts +3 -3
- package/dist/constraints.mjs +2 -2
- package/dist/container.mjs +146 -214
- package/dist/decorators/inject.d.mts +4 -3
- package/dist/decorators/inject.mjs +21 -48
- package/dist/decorators/injectable.mjs +4 -12
- package/dist/decorators/lifecycle-decorators.mjs +11 -72
- package/dist/dependency-graph.mjs +17 -15
- package/dist/environment.d.mts +15 -15
- package/dist/environment.mjs +21 -21
- package/dist/graph-adapters/cytoscape.d.mts +12 -12
- package/dist/graph-adapters/cytoscape.mjs +7 -7
- package/dist/graph-adapters/reactflow.d.mts +15 -15
- package/dist/graph-adapters/reactflow.mjs +6 -9
- package/dist/index.d.mts +4 -4
- package/dist/index.mjs +2 -2
- package/dist/inspector.d.mts +3 -2
- package/dist/inspector.mjs +19 -22
- package/dist/lifecycle.mjs +2 -12
- package/dist/metadata/metadata-keys.d.mts +8 -33
- package/dist/metadata/metadata-keys.mjs +8 -21
- package/dist/metadata/metadata-types.d.mts +5 -0
- package/dist/metadata/symbol-metadata-reader.d.mts +1 -0
- package/dist/metadata/symbol-metadata-reader.mjs +11 -33
- package/dist/module.d.mts +1 -1
- package/dist/module.mjs +2 -2
- package/dist/registry.d.mts +4 -4
- package/dist/registry.mjs +26 -45
- package/dist/resolve-options.d.mts +7 -7
- package/dist/resolve-options.mjs +14 -12
- package/dist/resolver.d.mts +15 -10
- package/dist/resolver.mjs +167 -173
- package/dist/token.d.mts +1 -1
- package/dist/token.mjs +4 -4
- package/dist/types.d.mts +14 -8
- package/package.json +40 -13
- package/src/binding-scope.ts +26 -0
- package/src/binding-select.ts +167 -0
- package/src/binding.ts +281 -0
- package/src/constraints.ts +149 -0
- package/src/constructor-type.ts +19 -0
- package/src/container.ts +1213 -0
- package/src/decorators/inject.ts +233 -0
- package/src/decorators/injectable.ts +85 -0
- package/src/decorators/lifecycle-decorators.ts +55 -0
- package/src/dependency-graph.ts +116 -0
- package/src/environment.ts +232 -0
- package/src/errors.ts +262 -0
- package/src/graph-adapters/cytoscape.ts +64 -0
- package/src/graph-adapters/dot.ts +22 -0
- package/src/graph-adapters/reactflow.ts +58 -0
- package/src/index.ts +101 -0
- package/src/inspector.ts +133 -0
- package/src/lifecycle.ts +238 -0
- package/src/metadata/metadata-keys.ts +25 -0
- package/src/metadata/metadata-reader-token.ts +8 -0
- package/src/metadata/metadata-types.ts +53 -0
- package/src/metadata/symbol-metadata-reader.ts +57 -0
- package/src/module.ts +93 -0
- package/src/registry.ts +241 -0
- package/src/resolve-options.ts +42 -0
- package/src/resolver.ts +1837 -0
- package/src/scope.ts +77 -0
- package/src/token.ts +40 -0
- package/src/types.ts +145 -0
- package/dist/graph-adapters/types.d.mts +0 -2
- package/dist/graph-adapters/types.mjs +0 -1
package/dist/resolver.mjs
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { AsyncResolutionError, CircularDependencyError, InternalError, MissingMetadataError, MissingScopeContextError, NoMatchingBindingError, TokenNotBoundError } from "./errors.mjs";
|
|
2
2
|
import { selectAllBindings, selectBinding } from "./binding-select.mjs";
|
|
3
3
|
import { tokenName } from "./token.mjs";
|
|
4
|
-
import { DefaultResolutionContext,
|
|
5
|
-
import {
|
|
4
|
+
import { DefaultResolutionContext, buildResolutionFrame, runWithContainer } from "./environment.mjs";
|
|
5
|
+
import { injectionSlotToResolveOptions } from "./resolve-options.mjs";
|
|
6
6
|
//#region src/resolver.ts
|
|
7
7
|
const RESOLUTION_SET_KEY = Symbol("di:resolution-set");
|
|
8
8
|
const RESOLUTION_SET_THRESHOLD = 32;
|
|
@@ -10,7 +10,7 @@ const EMPTY_STRING_LIST = [];
|
|
|
10
10
|
const EMPTY_FRAME_LIST = [];
|
|
11
11
|
const ROOT_CONSTRAINT_CONTEXT = {
|
|
12
12
|
resolutionPath: EMPTY_STRING_LIST,
|
|
13
|
-
|
|
13
|
+
resolutionStack: EMPTY_FRAME_LIST,
|
|
14
14
|
parent: void 0,
|
|
15
15
|
ancestors: EMPTY_FRAME_LIST,
|
|
16
16
|
currentResolveHint: void 0
|
|
@@ -48,7 +48,7 @@ var DependencyResolver = class {
|
|
|
48
48
|
this._container = _container;
|
|
49
49
|
this._parent = _parent;
|
|
50
50
|
}
|
|
51
|
-
_findBinding(token, hint, resolutionPath,
|
|
51
|
+
_findBinding(token, hint, resolutionPath, resolutionStack) {
|
|
52
52
|
if (hint === void 0) {
|
|
53
53
|
const fastDefaultBinding = this._registry.getFastDefault(token);
|
|
54
54
|
if (fastDefaultBinding !== void 0) return {
|
|
@@ -58,7 +58,7 @@ var DependencyResolver = class {
|
|
|
58
58
|
}
|
|
59
59
|
if (hint?.name !== void 0 && hint.tag === void 0 && (hint.tags?.length ?? 0) === 0) {
|
|
60
60
|
const namedBinding = this._registry.getSimpleNamed(token, hint.name);
|
|
61
|
-
if (namedBinding !== void 0 && this._matchesBindingFast(namedBinding, hint, resolutionPath,
|
|
61
|
+
if (namedBinding !== void 0 && this._matchesBindingFast(namedBinding, hint, resolutionPath, resolutionStack)) return {
|
|
62
62
|
binding: namedBinding,
|
|
63
63
|
owner: this
|
|
64
64
|
};
|
|
@@ -80,18 +80,18 @@ var DependencyResolver = class {
|
|
|
80
80
|
binding: onlyBinding,
|
|
81
81
|
owner: this
|
|
82
82
|
};
|
|
83
|
-
if (this._matchesBindingFast(onlyBinding, hint, resolutionPath,
|
|
83
|
+
if (this._matchesBindingFast(onlyBinding, hint, resolutionPath, resolutionStack)) return {
|
|
84
84
|
binding: onlyBinding,
|
|
85
85
|
owner: this
|
|
86
86
|
};
|
|
87
87
|
}
|
|
88
|
-
const binding = selectBinding(bindings, hint, this._makeConstraintContext(resolutionPath,
|
|
88
|
+
const binding = selectBinding(bindings, hint, this._makeConstraintContext(resolutionPath, resolutionStack, hint), this._getTokenName(token));
|
|
89
89
|
if (binding !== void 0) return {
|
|
90
90
|
binding,
|
|
91
91
|
owner: this
|
|
92
92
|
};
|
|
93
93
|
}
|
|
94
|
-
if (this._parent !== void 0) return this._parent._findBinding(token, hint, resolutionPath,
|
|
94
|
+
if (this._parent !== void 0) return this._parent._findBinding(token, hint, resolutionPath, resolutionStack);
|
|
95
95
|
}
|
|
96
96
|
/**
|
|
97
97
|
* Binding lookup aligned with `resolve` — used by `Container.validate` without instantiating.
|
|
@@ -108,33 +108,33 @@ var DependencyResolver = class {
|
|
|
108
108
|
if (allBindings.length === 0) return [];
|
|
109
109
|
return selectAllBindings(allBindings, hint, this._makeConstraintContext([], [], hint));
|
|
110
110
|
}
|
|
111
|
-
resolveFromContext(token, resolutionPath,
|
|
111
|
+
resolveFromContext(token, resolutionPath, resolutionStack) {
|
|
112
112
|
const fastBinding = this._registry.getFastDefault(token);
|
|
113
113
|
if (fastBinding !== void 0) {
|
|
114
|
-
if (fastBinding.kind === "alias") return this.resolveFromContext(fastBinding.target, resolutionPath,
|
|
114
|
+
if (fastBinding.kind === "alias") return this.resolveFromContext(fastBinding.target, resolutionPath, resolutionStack);
|
|
115
115
|
const scope = fastBinding.scope ?? "transient";
|
|
116
|
-
if (scope === "transient" && fastBinding.kind === "dynamic" && fastBinding.onActivation === void 0 && (this._lifecycle.activationVersion === 0 || !this._lifecycle.hasActivationHandlers(fastBinding.token))) return this._resolveTransientDynamicSyncFromContext(fastBinding, resolutionPath,
|
|
116
|
+
if (scope === "transient" && fastBinding.kind === "dynamic" && fastBinding.onActivation === void 0 && (this._lifecycle.activationVersion === 0 || !this._lifecycle.hasActivationHandlers(fastBinding.token))) return this._resolveTransientDynamicSyncFromContext(fastBinding, resolutionPath, resolutionStack);
|
|
117
117
|
if (scope === "singleton" && this._scope.hasSingleton(fastBinding.id)) return this._scope.getSingleton(fastBinding.id);
|
|
118
118
|
if (scope === "scoped") {
|
|
119
119
|
if (!this._scope.isChild) throw new MissingScopeContextError(this._getTokenName(fastBinding.token));
|
|
120
120
|
if (this._scope.hasScoped(fastBinding.id)) return this._scope.getScoped(fastBinding.id);
|
|
121
121
|
}
|
|
122
|
-
return this._resolveBinding(fastBinding, void 0, resolutionPath,
|
|
122
|
+
return this._resolveBinding(fastBinding, void 0, resolutionPath, resolutionStack);
|
|
123
123
|
}
|
|
124
|
-
return this.resolve(token, void 0, resolutionPath,
|
|
124
|
+
return this.resolve(token, void 0, resolutionPath, resolutionStack);
|
|
125
125
|
}
|
|
126
|
-
resolve(token, hint, resolutionPath,
|
|
127
|
-
const found = this._findBinding(token, hint, resolutionPath,
|
|
126
|
+
resolve(token, hint, resolutionPath, resolutionStack) {
|
|
127
|
+
const found = this._findBinding(token, hint, resolutionPath, resolutionStack);
|
|
128
128
|
if (found === void 0) {
|
|
129
129
|
if (this._registry.getAll(token).length > 0) throw new NoMatchingBindingError(this._getTokenName(token), hint ?? {}, this._getAvailableSlots(token));
|
|
130
130
|
throw new TokenNotBoundError(this._getTokenName(token));
|
|
131
131
|
}
|
|
132
132
|
const { binding, owner } = found;
|
|
133
|
-
if (binding.kind === "alias") return this.resolve(binding.target, hint, resolutionPath,
|
|
134
|
-
if ((binding.scope ?? "transient") === "singleton" && owner !== this) return owner._resolveBinding(binding, hint, resolutionPath,
|
|
135
|
-
return this._resolveBinding(binding, hint, resolutionPath,
|
|
133
|
+
if (binding.kind === "alias") return this.resolve(binding.target, hint, resolutionPath, resolutionStack);
|
|
134
|
+
if ((binding.scope ?? "transient") === "singleton" && owner !== this) return owner._resolveBinding(binding, hint, resolutionPath, resolutionStack);
|
|
135
|
+
return this._resolveBinding(binding, hint, resolutionPath, resolutionStack);
|
|
136
136
|
}
|
|
137
|
-
_resolveBinding(binding, hint, resolutionPath,
|
|
137
|
+
_resolveBinding(binding, hint, resolutionPath, resolutionStack) {
|
|
138
138
|
if (binding.kind === "constant" && binding.onActivation === void 0 && !this._lifecycle.hasActivationHandlers(binding.token)) return binding.value;
|
|
139
139
|
const scope = binding.scope ?? "transient";
|
|
140
140
|
if (scope === "singleton") {
|
|
@@ -144,7 +144,7 @@ var DependencyResolver = class {
|
|
|
144
144
|
if (!this._scope.isChild) throw new MissingScopeContextError(this._getTokenName(binding.token));
|
|
145
145
|
if (this._scope.hasScoped(binding.id)) return this._scope.getScoped(binding.id);
|
|
146
146
|
}
|
|
147
|
-
const frame = this.
|
|
147
|
+
const frame = this._getResolutionFrame(binding);
|
|
148
148
|
const tokenDisplayName = frame.tokenName;
|
|
149
149
|
const pathWithSet = resolutionPath;
|
|
150
150
|
let resolutionSet = pathWithSet[RESOLUTION_SET_KEY];
|
|
@@ -155,44 +155,38 @@ var DependencyResolver = class {
|
|
|
155
155
|
if (resolutionSet !== void 0 ? resolutionSet.has(tokenDisplayName) : resolutionPath.includes(tokenDisplayName)) throw new CircularDependencyError([...resolutionPath, tokenDisplayName]);
|
|
156
156
|
resolutionPath.push(tokenDisplayName);
|
|
157
157
|
resolutionSet?.add(tokenDisplayName);
|
|
158
|
-
|
|
158
|
+
resolutionStack.push(frame);
|
|
159
159
|
const needsActivation = this._needsActivation(binding);
|
|
160
160
|
if (!needsActivation && scope === "transient" && binding.kind === "dynamic") {
|
|
161
|
-
const resolutionCtx = this._acquireSyncResolutionContext(resolutionPath,
|
|
161
|
+
const resolutionCtx = this._acquireSyncResolutionContext(resolutionPath, resolutionStack, hint);
|
|
162
162
|
try {
|
|
163
163
|
const dynamicResult = binding.factory(resolutionCtx);
|
|
164
164
|
if (dynamicResult instanceof Promise) throw new AsyncResolutionError(tokenName(binding.token), tokenName(binding.token));
|
|
165
|
-
|
|
165
|
+
resolutionStack.pop();
|
|
166
166
|
resolutionPath.pop();
|
|
167
167
|
resolutionSet?.delete(tokenDisplayName);
|
|
168
168
|
return dynamicResult;
|
|
169
169
|
} catch (error) {
|
|
170
|
-
|
|
170
|
+
resolutionStack.pop();
|
|
171
171
|
resolutionPath.pop();
|
|
172
172
|
resolutionSet?.delete(tokenDisplayName);
|
|
173
173
|
throw error;
|
|
174
174
|
}
|
|
175
175
|
}
|
|
176
176
|
try {
|
|
177
|
-
const resolutionCtx = needsActivation || this._requiresResolutionContext(binding) ? this._acquireSyncResolutionContext(resolutionPath,
|
|
178
|
-
const instance = this._instantiateSync(binding, resolutionCtx, resolutionPath,
|
|
179
|
-
|
|
180
|
-
if (binding.kind === "class" && this._classHasPostConstruct.get(binding.target) === void 0) {
|
|
181
|
-
this._refreshClassPostConstructCache(binding.target);
|
|
182
|
-
this._activationNeedByBindingId.delete(binding.id);
|
|
183
|
-
shouldActivate = this._needsActivation(binding);
|
|
184
|
-
}
|
|
185
|
-
const activated = shouldActivate ? this._lifecycle.runActivationSync(resolutionCtx, binding, instance, this._metadataReader) : instance;
|
|
177
|
+
const resolutionCtx = needsActivation || this._requiresResolutionContext(binding) ? this._acquireSyncResolutionContext(resolutionPath, resolutionStack, hint) : void 0;
|
|
178
|
+
const instance = this._instantiateSync(binding, resolutionCtx, resolutionPath, resolutionStack);
|
|
179
|
+
const activated = this._refreshActivationCacheIfNeeded(binding, needsActivation) ? this._lifecycle.runActivationSync(resolutionCtx, binding, instance, this._metadataReader) : instance;
|
|
186
180
|
if (scope === "singleton") this._scope.setSingleton(binding.id, activated);
|
|
187
181
|
else if (scope === "scoped") this._scope.setScoped(binding.id, activated);
|
|
188
182
|
return activated;
|
|
189
183
|
} finally {
|
|
190
|
-
|
|
184
|
+
resolutionStack.pop();
|
|
191
185
|
resolutionPath.pop();
|
|
192
186
|
resolutionSet?.delete(tokenDisplayName);
|
|
193
187
|
}
|
|
194
188
|
}
|
|
195
|
-
_instantiateSync(binding, ctx, resolutionPath,
|
|
189
|
+
_instantiateSync(binding, ctx, resolutionPath, resolutionStack) {
|
|
196
190
|
switch (binding.kind) {
|
|
197
191
|
case "constant": return binding.value;
|
|
198
192
|
case "dynamic": {
|
|
@@ -203,20 +197,20 @@ var DependencyResolver = class {
|
|
|
203
197
|
}
|
|
204
198
|
case "dynamic-async": throw new AsyncResolutionError(tokenName(binding.token), tokenName(binding.token));
|
|
205
199
|
case "class": {
|
|
206
|
-
const deps = this._resolveClassDeps(binding.target, resolutionPath,
|
|
200
|
+
const deps = this._resolveClassDeps(binding.target, resolutionPath, resolutionStack);
|
|
207
201
|
return this._instantiateClass(binding.target, deps);
|
|
208
202
|
}
|
|
209
203
|
case "resolved": {
|
|
210
|
-
const deps = this._resolveDescriptorDeps(binding.deps, resolutionPath,
|
|
211
|
-
const
|
|
212
|
-
if (
|
|
213
|
-
return
|
|
204
|
+
const deps = this._resolveDescriptorDeps(binding.deps, resolutionPath, resolutionStack);
|
|
205
|
+
const factoryResult = binding.factory(...deps);
|
|
206
|
+
if (factoryResult instanceof Promise) throw new AsyncResolutionError(tokenName(binding.token), tokenName(binding.token));
|
|
207
|
+
return factoryResult;
|
|
214
208
|
}
|
|
215
209
|
case "resolved-async": throw new AsyncResolutionError(tokenName(binding.token), tokenName(binding.token));
|
|
216
210
|
case "alias": throw new InternalError("alias should have been followed before instantiation");
|
|
217
211
|
}
|
|
218
212
|
}
|
|
219
|
-
_resolveClassDeps(target, resolutionPath,
|
|
213
|
+
_resolveClassDeps(target, resolutionPath, resolutionStack) {
|
|
220
214
|
const meta = this._getConstructorMetadata(target);
|
|
221
215
|
if (meta === void 0) {
|
|
222
216
|
if (target.length === 0) return [];
|
|
@@ -225,91 +219,91 @@ var DependencyResolver = class {
|
|
|
225
219
|
if (meta.params.length === 0) return [];
|
|
226
220
|
if (meta.params.length === 1) {
|
|
227
221
|
const param = meta.params[0];
|
|
228
|
-
const paramHint =
|
|
229
|
-
if (param.multi) return [this.resolveAll(param.token, paramHint, resolutionPath,
|
|
230
|
-
if (param.optional) return [this.resolveOptional(param.token, paramHint, resolutionPath,
|
|
231
|
-
if (paramHint === void 0) return [this.resolveFromContext(param.token, resolutionPath,
|
|
232
|
-
return [this.resolve(param.token, paramHint, resolutionPath,
|
|
222
|
+
const paramHint = injectionSlotToResolveOptions(param);
|
|
223
|
+
if (param.multi) return [this.resolveAll(param.token, paramHint, resolutionPath, resolutionStack)];
|
|
224
|
+
if (param.optional) return [this.resolveOptional(param.token, paramHint, resolutionPath, resolutionStack)];
|
|
225
|
+
if (paramHint === void 0) return [this.resolveFromContext(param.token, resolutionPath, resolutionStack)];
|
|
226
|
+
return [this.resolve(param.token, paramHint, resolutionPath, resolutionStack)];
|
|
233
227
|
}
|
|
234
228
|
const deps = new Array(meta.params.length);
|
|
235
229
|
for (let index = 0; index < meta.params.length; index += 1) {
|
|
236
230
|
const param = meta.params[index];
|
|
237
|
-
const paramHint =
|
|
231
|
+
const paramHint = injectionSlotToResolveOptions(param);
|
|
238
232
|
if (param.multi) {
|
|
239
|
-
deps[index] = this.resolveAll(param.token, paramHint, resolutionPath,
|
|
233
|
+
deps[index] = this.resolveAll(param.token, paramHint, resolutionPath, resolutionStack);
|
|
240
234
|
continue;
|
|
241
235
|
}
|
|
242
236
|
if (param.optional) {
|
|
243
|
-
deps[index] = this.resolveOptional(param.token, paramHint, resolutionPath,
|
|
237
|
+
deps[index] = this.resolveOptional(param.token, paramHint, resolutionPath, resolutionStack);
|
|
244
238
|
continue;
|
|
245
239
|
}
|
|
246
|
-
deps[index] = paramHint === void 0 ? this.resolveFromContext(param.token, resolutionPath,
|
|
240
|
+
deps[index] = paramHint === void 0 ? this.resolveFromContext(param.token, resolutionPath, resolutionStack) : this.resolve(param.token, paramHint, resolutionPath, resolutionStack);
|
|
247
241
|
}
|
|
248
242
|
return deps;
|
|
249
243
|
}
|
|
250
|
-
_resolveDescriptorDeps(deps, resolutionPath,
|
|
244
|
+
_resolveDescriptorDeps(deps, resolutionPath, resolutionStack) {
|
|
251
245
|
const resolved = new Array(deps.length);
|
|
252
246
|
for (let index = 0; index < deps.length; index += 1) {
|
|
253
247
|
const dep = deps[index];
|
|
254
|
-
const depHint =
|
|
248
|
+
const depHint = injectionSlotToResolveOptions(dep);
|
|
255
249
|
if (dep.multi) {
|
|
256
|
-
resolved[index] = this.resolveAll(dep.token, depHint, resolutionPath,
|
|
250
|
+
resolved[index] = this.resolveAll(dep.token, depHint, resolutionPath, resolutionStack);
|
|
257
251
|
continue;
|
|
258
252
|
}
|
|
259
253
|
if (dep.optional) {
|
|
260
|
-
resolved[index] = this.resolveOptional(dep.token, depHint, resolutionPath,
|
|
254
|
+
resolved[index] = this.resolveOptional(dep.token, depHint, resolutionPath, resolutionStack);
|
|
261
255
|
continue;
|
|
262
256
|
}
|
|
263
|
-
resolved[index] = depHint === void 0 ? this.resolveFromContext(dep.token, resolutionPath,
|
|
257
|
+
resolved[index] = depHint === void 0 ? this.resolveFromContext(dep.token, resolutionPath, resolutionStack) : this.resolve(dep.token, depHint, resolutionPath, resolutionStack);
|
|
264
258
|
}
|
|
265
259
|
return resolved;
|
|
266
260
|
}
|
|
267
|
-
resolveOptional(token, hint, resolutionPath,
|
|
268
|
-
if (this._findBinding(token, hint, resolutionPath,
|
|
269
|
-
return this.resolve(token, hint, resolutionPath,
|
|
261
|
+
resolveOptional(token, hint, resolutionPath, resolutionStack) {
|
|
262
|
+
if (this._findBinding(token, hint, resolutionPath, resolutionStack) === void 0) return;
|
|
263
|
+
return this.resolve(token, hint, resolutionPath, resolutionStack);
|
|
270
264
|
}
|
|
271
|
-
resolveAll(token, hint, resolutionPath,
|
|
265
|
+
resolveAll(token, hint, resolutionPath, resolutionStack) {
|
|
272
266
|
if (hint?.name !== void 0 && hint.tag === void 0 && (hint.tags?.length ?? 0) === 0) {
|
|
273
267
|
const namedCandidates = this._getSimpleNamedBindingsFromChain(token, hint.name);
|
|
274
268
|
if (namedCandidates.length === 0) return [];
|
|
275
269
|
const resolved = new Array(namedCandidates.length);
|
|
276
|
-
for (let index = 0; index < namedCandidates.length; index += 1) resolved[index] = this._resolveCandidateSync(namedCandidates[index], hint, resolutionPath,
|
|
270
|
+
for (let index = 0; index < namedCandidates.length; index += 1) resolved[index] = this._resolveCandidateSync(namedCandidates[index], hint, resolutionPath, resolutionStack);
|
|
277
271
|
return resolved;
|
|
278
272
|
}
|
|
279
273
|
const allBindings = this._getAllBindingsFromChain(token);
|
|
280
274
|
if (allBindings.length === 0) return [];
|
|
281
|
-
const candidates = selectAllBindings(allBindings, hint, this._makeConstraintContext(resolutionPath,
|
|
275
|
+
const candidates = selectAllBindings(allBindings, hint, this._makeConstraintContext(resolutionPath, resolutionStack, hint));
|
|
282
276
|
const resolved = new Array(candidates.length);
|
|
283
|
-
for (let index = 0; index < candidates.length; index += 1) resolved[index] = this._resolveCandidateSync(candidates[index], hint, resolutionPath,
|
|
277
|
+
for (let index = 0; index < candidates.length; index += 1) resolved[index] = this._resolveCandidateSync(candidates[index], hint, resolutionPath, resolutionStack);
|
|
284
278
|
return resolved;
|
|
285
279
|
}
|
|
286
|
-
resolveAsyncFromContext(token, resolutionPath,
|
|
280
|
+
resolveAsyncFromContext(token, resolutionPath, resolutionStack) {
|
|
287
281
|
const fastBinding = this._registry.getFastDefault(token);
|
|
288
282
|
if (fastBinding !== void 0) {
|
|
289
|
-
if (fastBinding.kind === "alias") return this.resolveAsyncFromContext(fastBinding.target, resolutionPath,
|
|
283
|
+
if (fastBinding.kind === "alias") return this.resolveAsyncFromContext(fastBinding.target, resolutionPath, resolutionStack);
|
|
290
284
|
const scope = fastBinding.scope ?? "transient";
|
|
291
|
-
if (scope === "transient" && (fastBinding.kind === "dynamic" || fastBinding.kind === "dynamic-async") && fastBinding.onActivation === void 0 && (this._lifecycle.activationVersion === 0 || !this._lifecycle.hasActivationHandlers(fastBinding.token))) return this._resolveTransientDynamicAsyncFromContext(fastBinding, resolutionPath,
|
|
285
|
+
if (scope === "transient" && (fastBinding.kind === "dynamic" || fastBinding.kind === "dynamic-async") && fastBinding.onActivation === void 0 && (this._lifecycle.activationVersion === 0 || !this._lifecycle.hasActivationHandlers(fastBinding.token))) return this._resolveTransientDynamicAsyncFromContext(fastBinding, resolutionPath, resolutionStack);
|
|
292
286
|
if (scope === "singleton" && this._scope.hasSingleton(fastBinding.id)) return Promise.resolve(this._scope.getSingleton(fastBinding.id));
|
|
293
287
|
if (scope === "scoped") {
|
|
294
288
|
if (!this._scope.isChild) return Promise.reject(new MissingScopeContextError(this._getTokenName(fastBinding.token)));
|
|
295
289
|
if (this._scope.hasScoped(fastBinding.id)) return Promise.resolve(this._scope.getScoped(fastBinding.id));
|
|
296
290
|
}
|
|
297
|
-
return this._resolveBindingAsync(fastBinding, void 0, resolutionPath,
|
|
291
|
+
return this._resolveBindingAsync(fastBinding, void 0, resolutionPath, resolutionStack);
|
|
298
292
|
}
|
|
299
|
-
return this.resolveAsync(token, void 0, resolutionPath,
|
|
293
|
+
return this.resolveAsync(token, void 0, resolutionPath, resolutionStack);
|
|
300
294
|
}
|
|
301
|
-
async resolveAsync(token, hint, resolutionPath,
|
|
302
|
-
const found = this._findBinding(token, hint, resolutionPath,
|
|
295
|
+
async resolveAsync(token, hint, resolutionPath, resolutionStack) {
|
|
296
|
+
const found = this._findBinding(token, hint, resolutionPath, resolutionStack);
|
|
303
297
|
if (found === void 0) {
|
|
304
298
|
if (this._registry.getAll(token).length > 0) throw new NoMatchingBindingError(this._getTokenName(token), hint ?? {}, this._getAvailableSlots(token));
|
|
305
299
|
throw new TokenNotBoundError(this._getTokenName(token));
|
|
306
300
|
}
|
|
307
301
|
const { binding, owner } = found;
|
|
308
|
-
if (binding.kind === "alias") return this.resolveAsync(binding.target, hint, resolutionPath,
|
|
309
|
-
if ((binding.scope ?? "transient") === "singleton" && owner !== this) return owner._resolveBindingAsync(binding, hint, resolutionPath,
|
|
310
|
-
return this._resolveBindingAsync(binding, hint, resolutionPath,
|
|
302
|
+
if (binding.kind === "alias") return this.resolveAsync(binding.target, hint, resolutionPath, resolutionStack);
|
|
303
|
+
if ((binding.scope ?? "transient") === "singleton" && owner !== this) return owner._resolveBindingAsync(binding, hint, resolutionPath, resolutionStack);
|
|
304
|
+
return this._resolveBindingAsync(binding, hint, resolutionPath, resolutionStack);
|
|
311
305
|
}
|
|
312
|
-
async _resolveBindingAsync(binding, hint, resolutionPath,
|
|
306
|
+
async _resolveBindingAsync(binding, hint, resolutionPath, resolutionStack) {
|
|
313
307
|
if (binding.kind === "constant" && binding.onActivation === void 0 && !this._lifecycle.hasActivationHandlers(binding.token)) return binding.value;
|
|
314
308
|
const scope = binding.scope ?? "transient";
|
|
315
309
|
if (scope === "singleton") {
|
|
@@ -321,43 +315,37 @@ var DependencyResolver = class {
|
|
|
321
315
|
if (!this._scope.isChild) throw new MissingScopeContextError(this._getTokenName(binding.token));
|
|
322
316
|
if (this._scope.hasScoped(binding.id)) return this._scope.getScoped(binding.id);
|
|
323
317
|
}
|
|
324
|
-
const frame = this.
|
|
325
|
-
const
|
|
318
|
+
const frame = this._getResolutionFrame(binding);
|
|
319
|
+
const frameName = frame.tokenName;
|
|
326
320
|
const pathWithSet = resolutionPath;
|
|
327
321
|
let resolutionSet = pathWithSet[RESOLUTION_SET_KEY];
|
|
328
322
|
if (resolutionSet === void 0 && resolutionPath.length >= RESOLUTION_SET_THRESHOLD) {
|
|
329
323
|
resolutionSet = new Set(resolutionPath);
|
|
330
324
|
pathWithSet[RESOLUTION_SET_KEY] = resolutionSet;
|
|
331
325
|
}
|
|
332
|
-
if (resolutionSet !== void 0 ? resolutionSet.has(
|
|
333
|
-
resolutionPath.push(
|
|
334
|
-
resolutionSet?.add(
|
|
335
|
-
|
|
326
|
+
if (resolutionSet !== void 0 ? resolutionSet.has(frameName) : resolutionPath.includes(frameName)) throw new CircularDependencyError([...resolutionPath, frameName]);
|
|
327
|
+
resolutionPath.push(frameName);
|
|
328
|
+
resolutionSet?.add(frameName);
|
|
329
|
+
resolutionStack.push(frame);
|
|
336
330
|
const needsActivation = this._needsActivation(binding);
|
|
337
331
|
if (!needsActivation && scope === "transient" && (binding.kind === "dynamic" || binding.kind === "dynamic-async")) {
|
|
338
|
-
const resolutionCtx = new DefaultResolutionContext(this, resolutionPath,
|
|
332
|
+
const resolutionCtx = new DefaultResolutionContext(this, resolutionPath, resolutionStack, hint);
|
|
339
333
|
try {
|
|
340
334
|
if (binding.kind === "dynamic-async") return await binding.factory(resolutionCtx);
|
|
341
335
|
const dynamicResult = binding.factory(resolutionCtx);
|
|
342
336
|
return dynamicResult instanceof Promise ? await dynamicResult : dynamicResult;
|
|
343
337
|
} finally {
|
|
344
|
-
|
|
338
|
+
resolutionStack.pop();
|
|
345
339
|
resolutionPath.pop();
|
|
346
|
-
resolutionSet?.delete(
|
|
340
|
+
resolutionSet?.delete(frameName);
|
|
347
341
|
}
|
|
348
342
|
}
|
|
349
|
-
const resolutionCtx = needsActivation || this._requiresResolutionContext(binding) ? new DefaultResolutionContext(this, resolutionPath,
|
|
343
|
+
const resolutionCtx = needsActivation || this._requiresResolutionContext(binding) ? new DefaultResolutionContext(this, resolutionPath, resolutionStack, hint) : void 0;
|
|
350
344
|
try {
|
|
351
345
|
if (scope === "singleton") {
|
|
352
346
|
const createSingletonPromise = async () => {
|
|
353
|
-
const instance = await this._instantiateAsync(binding, resolutionCtx, resolutionPath,
|
|
354
|
-
|
|
355
|
-
if (binding.kind === "class" && this._classHasPostConstruct.get(binding.target) === void 0) {
|
|
356
|
-
this._refreshClassPostConstructCache(binding.target);
|
|
357
|
-
this._activationNeedByBindingId.delete(binding.id);
|
|
358
|
-
shouldActivate = this._needsActivation(binding);
|
|
359
|
-
}
|
|
360
|
-
const activated = shouldActivate ? await this._lifecycle.runActivation(resolutionCtx, binding, instance, this._metadataReader) : instance;
|
|
347
|
+
const instance = await this._instantiateAsync(binding, resolutionCtx, resolutionPath, resolutionStack);
|
|
348
|
+
const activated = this._refreshActivationCacheIfNeeded(binding, needsActivation) ? await this._lifecycle.runActivation(resolutionCtx, binding, instance, this._metadataReader) : instance;
|
|
361
349
|
this._scope.setSingleton(binding.id, activated);
|
|
362
350
|
this._scope.clearInflight(binding.id);
|
|
363
351
|
return activated;
|
|
@@ -369,51 +357,45 @@ var DependencyResolver = class {
|
|
|
369
357
|
this._scope.setInflight(binding.id, singletonPromise);
|
|
370
358
|
return await singletonPromise;
|
|
371
359
|
}
|
|
372
|
-
const instance = await this._instantiateAsync(binding, resolutionCtx, resolutionPath,
|
|
373
|
-
|
|
374
|
-
if (binding.kind === "class" && this._classHasPostConstruct.get(binding.target) === void 0) {
|
|
375
|
-
this._refreshClassPostConstructCache(binding.target);
|
|
376
|
-
this._activationNeedByBindingId.delete(binding.id);
|
|
377
|
-
shouldActivate = this._needsActivation(binding);
|
|
378
|
-
}
|
|
379
|
-
const activated = shouldActivate ? await this._lifecycle.runActivation(resolutionCtx, binding, instance, this._metadataReader) : instance;
|
|
360
|
+
const instance = await this._instantiateAsync(binding, resolutionCtx, resolutionPath, resolutionStack);
|
|
361
|
+
const activated = this._refreshActivationCacheIfNeeded(binding, needsActivation) ? await this._lifecycle.runActivation(resolutionCtx, binding, instance, this._metadataReader) : instance;
|
|
380
362
|
if (scope === "scoped") this._scope.setScoped(binding.id, activated);
|
|
381
363
|
return activated;
|
|
382
364
|
} finally {
|
|
383
|
-
|
|
365
|
+
resolutionStack.pop();
|
|
384
366
|
resolutionPath.pop();
|
|
385
|
-
resolutionSet?.delete(
|
|
367
|
+
resolutionSet?.delete(frameName);
|
|
386
368
|
}
|
|
387
369
|
}
|
|
388
|
-
async _instantiateAsync(binding, ctx, resolutionPath,
|
|
370
|
+
async _instantiateAsync(binding, ctx, resolutionPath, resolutionStack) {
|
|
389
371
|
switch (binding.kind) {
|
|
390
372
|
case "constant": return binding.value;
|
|
391
373
|
case "dynamic": {
|
|
392
374
|
if (ctx === void 0) throw new InternalError("dynamic binding requires resolution context");
|
|
393
|
-
const
|
|
394
|
-
return
|
|
375
|
+
const factoryResult = binding.factory(ctx);
|
|
376
|
+
return factoryResult instanceof Promise ? factoryResult : Promise.resolve(factoryResult);
|
|
395
377
|
}
|
|
396
378
|
case "dynamic-async":
|
|
397
379
|
if (ctx === void 0) throw new InternalError("dynamic-async binding requires resolution context");
|
|
398
380
|
return binding.factory(ctx);
|
|
399
381
|
case "class": {
|
|
400
|
-
const deps = await this._resolveClassDepsAsync(binding.target, resolutionPath,
|
|
382
|
+
const deps = await this._resolveClassDepsAsync(binding.target, resolutionPath, resolutionStack);
|
|
401
383
|
return this._instantiateClass(binding.target, deps);
|
|
402
384
|
}
|
|
403
385
|
case "resolved": {
|
|
404
386
|
if (ctx === void 0) throw new InternalError("resolved binding requires resolution context");
|
|
405
|
-
const deps = await this._resolveDescriptorDepsAsync(binding.deps, resolutionPath,
|
|
406
|
-
const
|
|
407
|
-
return
|
|
387
|
+
const deps = await this._resolveDescriptorDepsAsync(binding.deps, resolutionPath, resolutionStack);
|
|
388
|
+
const factoryResult = binding.factory(...deps);
|
|
389
|
+
return factoryResult instanceof Promise ? factoryResult : Promise.resolve(factoryResult);
|
|
408
390
|
}
|
|
409
391
|
case "resolved-async": {
|
|
410
|
-
const deps = await this._resolveDescriptorDepsAsync(binding.deps, resolutionPath,
|
|
392
|
+
const deps = await this._resolveDescriptorDepsAsync(binding.deps, resolutionPath, resolutionStack);
|
|
411
393
|
return binding.factory(...deps);
|
|
412
394
|
}
|
|
413
395
|
case "alias": throw new InternalError("alias should have been followed before instantiation");
|
|
414
396
|
}
|
|
415
397
|
}
|
|
416
|
-
async _resolveClassDepsAsync(target, resolutionPath,
|
|
398
|
+
async _resolveClassDepsAsync(target, resolutionPath, resolutionStack) {
|
|
417
399
|
const meta = this._getConstructorMetadata(target);
|
|
418
400
|
if (meta === void 0) {
|
|
419
401
|
if (target.length === 0) return [];
|
|
@@ -422,52 +404,52 @@ var DependencyResolver = class {
|
|
|
422
404
|
if (meta.params.length === 0) return [];
|
|
423
405
|
if (meta.params.length === 1) {
|
|
424
406
|
const param = meta.params[0];
|
|
425
|
-
const paramHint =
|
|
426
|
-
if (param.multi) return [await this.resolveAllAsync(param.token, paramHint, resolutionPath,
|
|
427
|
-
if (param.optional) return [await this.resolveOptionalAsync(param.token, paramHint, resolutionPath,
|
|
428
|
-
if (paramHint === void 0) return [await this.resolveAsyncFromContext(param.token, resolutionPath,
|
|
429
|
-
return [await this.resolveAsync(param.token, paramHint, resolutionPath,
|
|
407
|
+
const paramHint = injectionSlotToResolveOptions(param);
|
|
408
|
+
if (param.multi) return [await this.resolveAllAsync(param.token, paramHint, resolutionPath, resolutionStack)];
|
|
409
|
+
if (param.optional) return [await this.resolveOptionalAsync(param.token, paramHint, resolutionPath, resolutionStack)];
|
|
410
|
+
if (paramHint === void 0) return [await this.resolveAsyncFromContext(param.token, resolutionPath, resolutionStack)];
|
|
411
|
+
return [await this.resolveAsync(param.token, paramHint, resolutionPath, resolutionStack)];
|
|
430
412
|
}
|
|
431
413
|
const pending = new Array(meta.params.length);
|
|
432
414
|
const shouldCloneContext = meta.params.length > 1;
|
|
433
415
|
for (let index = 0; index < meta.params.length; index += 1) {
|
|
434
416
|
const param = meta.params[index];
|
|
435
|
-
const paramHint =
|
|
436
|
-
if (param.multi) pending[index] = this.resolveAllAsync(param.token, paramHint, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...
|
|
437
|
-
else if (param.optional) pending[index] = this.resolveOptionalAsync(param.token, paramHint, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...
|
|
438
|
-
else pending[index] = paramHint === void 0 ? this.resolveAsyncFromContext(param.token, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...
|
|
417
|
+
const paramHint = injectionSlotToResolveOptions(param);
|
|
418
|
+
if (param.multi) pending[index] = this.resolveAllAsync(param.token, paramHint, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...resolutionStack] : resolutionStack);
|
|
419
|
+
else if (param.optional) pending[index] = this.resolveOptionalAsync(param.token, paramHint, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...resolutionStack] : resolutionStack);
|
|
420
|
+
else pending[index] = paramHint === void 0 ? this.resolveAsyncFromContext(param.token, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...resolutionStack] : resolutionStack) : this.resolveAsync(param.token, paramHint, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...resolutionStack] : resolutionStack);
|
|
439
421
|
}
|
|
440
422
|
return Promise.all(pending);
|
|
441
423
|
}
|
|
442
|
-
async _resolveDescriptorDepsAsync(deps, resolutionPath,
|
|
424
|
+
async _resolveDescriptorDepsAsync(deps, resolutionPath, resolutionStack) {
|
|
443
425
|
const pending = new Array(deps.length);
|
|
444
426
|
const shouldCloneContext = deps.length > 1;
|
|
445
427
|
for (let index = 0; index < deps.length; index += 1) {
|
|
446
428
|
const dep = deps[index];
|
|
447
|
-
const depHint =
|
|
448
|
-
if (dep.multi) pending[index] = this.resolveAllAsync(dep.token, depHint, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...
|
|
449
|
-
else if (dep.optional) pending[index] = this.resolveOptionalAsync(dep.token, depHint, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...
|
|
450
|
-
else pending[index] = depHint === void 0 ? this.resolveAsyncFromContext(dep.token, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...
|
|
429
|
+
const depHint = injectionSlotToResolveOptions(dep);
|
|
430
|
+
if (dep.multi) pending[index] = this.resolveAllAsync(dep.token, depHint, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...resolutionStack] : resolutionStack);
|
|
431
|
+
else if (dep.optional) pending[index] = this.resolveOptionalAsync(dep.token, depHint, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...resolutionStack] : resolutionStack);
|
|
432
|
+
else pending[index] = depHint === void 0 ? this.resolveAsyncFromContext(dep.token, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...resolutionStack] : resolutionStack) : this.resolveAsync(dep.token, depHint, shouldCloneContext ? [...resolutionPath] : resolutionPath, shouldCloneContext ? [...resolutionStack] : resolutionStack);
|
|
451
433
|
}
|
|
452
434
|
return Promise.all(pending);
|
|
453
435
|
}
|
|
454
|
-
async resolveOptionalAsync(token, hint, resolutionPath,
|
|
455
|
-
if (this._findBinding(token, hint, resolutionPath,
|
|
456
|
-
return this.resolveAsync(token, hint, resolutionPath,
|
|
436
|
+
async resolveOptionalAsync(token, hint, resolutionPath, resolutionStack) {
|
|
437
|
+
if (this._findBinding(token, hint, resolutionPath, resolutionStack) === void 0) return;
|
|
438
|
+
return this.resolveAsync(token, hint, resolutionPath, resolutionStack);
|
|
457
439
|
}
|
|
458
|
-
async resolveAllAsync(token, hint, resolutionPath,
|
|
440
|
+
async resolveAllAsync(token, hint, resolutionPath, resolutionStack) {
|
|
459
441
|
if (hint?.name !== void 0 && hint.tag === void 0 && (hint.tags?.length ?? 0) === 0) {
|
|
460
442
|
const namedCandidates = this._getSimpleNamedBindingsFromChain(token, hint.name);
|
|
461
443
|
if (namedCandidates.length === 0) return [];
|
|
462
444
|
const pending = new Array(namedCandidates.length);
|
|
463
|
-
for (let index = 0; index < namedCandidates.length; index += 1) pending[index] = this._resolveCandidateAsync(namedCandidates[index], hint, resolutionPath,
|
|
445
|
+
for (let index = 0; index < namedCandidates.length; index += 1) pending[index] = this._resolveCandidateAsync(namedCandidates[index], hint, resolutionPath, resolutionStack);
|
|
464
446
|
return Promise.all(pending);
|
|
465
447
|
}
|
|
466
448
|
const allBindings = this._getAllBindingsFromChain(token);
|
|
467
449
|
if (allBindings.length === 0) return [];
|
|
468
|
-
const candidates = selectAllBindings(allBindings, hint, this._makeConstraintContext(resolutionPath,
|
|
450
|
+
const candidates = selectAllBindings(allBindings, hint, this._makeConstraintContext(resolutionPath, resolutionStack, hint));
|
|
469
451
|
const pending = new Array(candidates.length);
|
|
470
|
-
for (let index = 0; index < candidates.length; index += 1) pending[index] = this._resolveCandidateAsync(candidates[index], hint, resolutionPath,
|
|
452
|
+
for (let index = 0; index < candidates.length; index += 1) pending[index] = this._resolveCandidateAsync(candidates[index], hint, resolutionPath, resolutionStack);
|
|
471
453
|
return Promise.all(pending);
|
|
472
454
|
}
|
|
473
455
|
_getAllBindingsFromChain(token) {
|
|
@@ -498,20 +480,20 @@ var DependencyResolver = class {
|
|
|
498
480
|
_getAvailableSlots(token) {
|
|
499
481
|
return this._registry.availableSlotStrings(token);
|
|
500
482
|
}
|
|
501
|
-
_makeConstraintContext(resolutionPath,
|
|
502
|
-
if (hint === void 0 && resolutionPath.length === 0 &&
|
|
483
|
+
_makeConstraintContext(resolutionPath, resolutionStack, hint) {
|
|
484
|
+
if (hint === void 0 && resolutionPath.length === 0 && resolutionStack.length === 0) return ROOT_CONSTRAINT_CONTEXT;
|
|
503
485
|
return {
|
|
504
486
|
resolutionPath,
|
|
505
|
-
|
|
506
|
-
parent:
|
|
507
|
-
ancestors:
|
|
487
|
+
resolutionStack,
|
|
488
|
+
parent: resolutionStack.at(-1),
|
|
489
|
+
ancestors: resolutionStack.length > 1 ? resolutionStack.slice(0, -1) : [],
|
|
508
490
|
currentResolveHint: hint
|
|
509
491
|
};
|
|
510
492
|
}
|
|
511
|
-
_matchesBindingFast(binding, hint, resolutionPath,
|
|
493
|
+
_matchesBindingFast(binding, hint, resolutionPath, resolutionStack) {
|
|
512
494
|
if (!this._matchesSlotFast(binding.slot, hint)) return false;
|
|
513
495
|
if (binding.predicate === void 0) return true;
|
|
514
|
-
const ctx = this._makeConstraintContext(resolutionPath,
|
|
496
|
+
const ctx = this._makeConstraintContext(resolutionPath, resolutionStack, hint);
|
|
515
497
|
return binding.predicate(ctx);
|
|
516
498
|
}
|
|
517
499
|
_matchesSlotFast(slot, hint) {
|
|
@@ -557,32 +539,32 @@ var DependencyResolver = class {
|
|
|
557
539
|
}
|
|
558
540
|
return false;
|
|
559
541
|
}
|
|
560
|
-
_resolveTransientDynamicSyncFromContext(binding, resolutionPath,
|
|
542
|
+
_resolveTransientDynamicSyncFromContext(binding, resolutionPath, resolutionStack) {
|
|
561
543
|
if (resolutionPath.length < RESOLUTION_SET_THRESHOLD) {
|
|
562
|
-
const frame = this.
|
|
544
|
+
const frame = this._getResolutionFrame(binding);
|
|
563
545
|
const tokenDisplayName = frame.tokenName;
|
|
564
546
|
if (resolutionPath.includes(tokenDisplayName)) throw new CircularDependencyError([...resolutionPath, tokenDisplayName]);
|
|
565
547
|
resolutionPath.push(tokenDisplayName);
|
|
566
|
-
|
|
567
|
-
const resolutionCtx = this._acquireSyncResolutionContext(resolutionPath,
|
|
548
|
+
resolutionStack.push(frame);
|
|
549
|
+
const resolutionCtx = this._acquireSyncResolutionContext(resolutionPath, resolutionStack, void 0);
|
|
568
550
|
try {
|
|
569
551
|
const dynamicResult = binding.factory(resolutionCtx);
|
|
570
552
|
if (dynamicResult instanceof Promise) throw new AsyncResolutionError(tokenDisplayName, tokenDisplayName);
|
|
571
553
|
return dynamicResult;
|
|
572
554
|
} finally {
|
|
573
|
-
|
|
555
|
+
resolutionStack.pop();
|
|
574
556
|
resolutionPath.pop();
|
|
575
557
|
}
|
|
576
558
|
}
|
|
577
|
-
if (this._deepActiveLevels > 0 && this._deepSyncCtxPath !== resolutionPath) return this._resolveTransientDynamicSyncSlow(binding, resolutionPath,
|
|
559
|
+
if (this._deepActiveLevels > 0 && this._deepSyncCtxPath !== resolutionPath) return this._resolveTransientDynamicSyncSlow(binding, resolutionPath, resolutionStack);
|
|
578
560
|
if (this._deepActiveLevels === 0) {
|
|
579
561
|
const gen = ++this._deepCycleGen;
|
|
580
|
-
for (const stackFrame of
|
|
562
|
+
for (const stackFrame of resolutionStack) this._deepCycleMarks.set(stackFrame.bindingId, gen);
|
|
581
563
|
let ctx = this._deepSyncCtx;
|
|
582
564
|
if (ctx === void 0) {
|
|
583
|
-
ctx = new DefaultResolutionContext(this, resolutionPath,
|
|
565
|
+
ctx = new DefaultResolutionContext(this, resolutionPath, resolutionStack, void 0);
|
|
584
566
|
this._deepSyncCtx = ctx;
|
|
585
|
-
} else ctx.reset(this, resolutionPath,
|
|
567
|
+
} else ctx.reset(this, resolutionPath, resolutionStack, void 0);
|
|
586
568
|
this._deepSyncCtxPath = resolutionPath;
|
|
587
569
|
}
|
|
588
570
|
if (this._deepCycleMarks.get(binding.id) === this._deepCycleGen) throw new CircularDependencyError([...resolutionPath, tokenName(binding.token)]);
|
|
@@ -596,8 +578,8 @@ var DependencyResolver = class {
|
|
|
596
578
|
if (--this._deepActiveLevels === 0) this._deepSyncCtxPath = void 0;
|
|
597
579
|
}
|
|
598
580
|
}
|
|
599
|
-
_resolveTransientDynamicSyncSlow(binding, resolutionPath,
|
|
600
|
-
const frame = this.
|
|
581
|
+
_resolveTransientDynamicSyncSlow(binding, resolutionPath, resolutionStack) {
|
|
582
|
+
const frame = this._getResolutionFrame(binding);
|
|
601
583
|
const tokenDisplayName = frame.tokenName;
|
|
602
584
|
const pathWithSet = resolutionPath;
|
|
603
585
|
let resolutionSet = pathWithSet[RESOLUTION_SET_KEY];
|
|
@@ -608,19 +590,19 @@ var DependencyResolver = class {
|
|
|
608
590
|
if (resolutionSet.has(tokenDisplayName)) throw new CircularDependencyError([...resolutionPath, tokenDisplayName]);
|
|
609
591
|
resolutionPath.push(tokenDisplayName);
|
|
610
592
|
resolutionSet.add(tokenDisplayName);
|
|
611
|
-
|
|
612
|
-
const resolutionCtx = this._acquireSyncResolutionContext(resolutionPath,
|
|
593
|
+
resolutionStack.push(frame);
|
|
594
|
+
const resolutionCtx = this._acquireSyncResolutionContext(resolutionPath, resolutionStack, void 0);
|
|
613
595
|
try {
|
|
614
596
|
const dynamicResult = binding.factory(resolutionCtx);
|
|
615
597
|
if (dynamicResult instanceof Promise) throw new AsyncResolutionError(tokenDisplayName, tokenDisplayName);
|
|
616
598
|
return dynamicResult;
|
|
617
599
|
} finally {
|
|
618
|
-
|
|
600
|
+
resolutionStack.pop();
|
|
619
601
|
resolutionPath.pop();
|
|
620
602
|
resolutionSet.delete(tokenDisplayName);
|
|
621
603
|
}
|
|
622
604
|
}
|
|
623
|
-
_resolveTransientDynamicAsyncFromContext(binding, resolutionPath,
|
|
605
|
+
_resolveTransientDynamicAsyncFromContext(binding, resolutionPath, resolutionStack) {
|
|
624
606
|
if (resolutionPath.length < RESOLUTION_SET_THRESHOLD) {
|
|
625
607
|
const tokenDisplayName = tokenName(binding.token);
|
|
626
608
|
if (resolutionPath.includes(tokenDisplayName)) return Promise.reject(new CircularDependencyError([...resolutionPath, tokenDisplayName]));
|
|
@@ -633,16 +615,16 @@ var DependencyResolver = class {
|
|
|
633
615
|
} else if (this._deepAsyncCtxPath === void 0) {
|
|
634
616
|
const existing = this._deepAsyncCtx;
|
|
635
617
|
if (existing === void 0) {
|
|
636
|
-
ctx = new DefaultResolutionContext(this, resolutionPath,
|
|
618
|
+
ctx = new DefaultResolutionContext(this, resolutionPath, resolutionStack, void 0);
|
|
637
619
|
this._deepAsyncCtx = ctx;
|
|
638
620
|
} else {
|
|
639
|
-
existing.reset(this, resolutionPath,
|
|
621
|
+
existing.reset(this, resolutionPath, resolutionStack, void 0);
|
|
640
622
|
ctx = existing;
|
|
641
623
|
}
|
|
642
624
|
this._deepAsyncCtxPath = resolutionPath;
|
|
643
625
|
isOwnerLevel = true;
|
|
644
626
|
} else {
|
|
645
|
-
ctx = new DefaultResolutionContext(this, resolutionPath,
|
|
627
|
+
ctx = new DefaultResolutionContext(this, resolutionPath, resolutionStack, void 0);
|
|
646
628
|
isOwnerLevel = false;
|
|
647
629
|
}
|
|
648
630
|
if (isOwnerLevel) this._deepAsyncActiveLevels++;
|
|
@@ -668,10 +650,10 @@ var DependencyResolver = class {
|
|
|
668
650
|
throw err;
|
|
669
651
|
});
|
|
670
652
|
}
|
|
671
|
-
return this._resolveTransientDynamicAsyncSlow(binding, resolutionPath,
|
|
653
|
+
return this._resolveTransientDynamicAsyncSlow(binding, resolutionPath, resolutionStack);
|
|
672
654
|
}
|
|
673
|
-
async _resolveTransientDynamicAsyncSlow(binding, resolutionPath,
|
|
674
|
-
const frame = this.
|
|
655
|
+
async _resolveTransientDynamicAsyncSlow(binding, resolutionPath, resolutionStack) {
|
|
656
|
+
const frame = this._getResolutionFrame(binding);
|
|
675
657
|
const tokenDisplayName = frame.tokenName;
|
|
676
658
|
const pathWithSet = resolutionPath;
|
|
677
659
|
let resolutionSet = pathWithSet[RESOLUTION_SET_KEY];
|
|
@@ -682,33 +664,33 @@ var DependencyResolver = class {
|
|
|
682
664
|
if (resolutionSet.has(tokenDisplayName)) throw new CircularDependencyError([...resolutionPath, tokenDisplayName]);
|
|
683
665
|
resolutionPath.push(tokenDisplayName);
|
|
684
666
|
resolutionSet.add(tokenDisplayName);
|
|
685
|
-
|
|
686
|
-
const resolutionCtx = new DefaultResolutionContext(this, resolutionPath,
|
|
667
|
+
resolutionStack.push(frame);
|
|
668
|
+
const resolutionCtx = new DefaultResolutionContext(this, resolutionPath, resolutionStack, void 0);
|
|
687
669
|
try {
|
|
688
670
|
if (binding.kind === "dynamic-async") return await binding.factory(resolutionCtx);
|
|
689
671
|
const dynamicResult = binding.factory(resolutionCtx);
|
|
690
672
|
return dynamicResult instanceof Promise ? await dynamicResult : dynamicResult;
|
|
691
673
|
} finally {
|
|
692
|
-
|
|
674
|
+
resolutionStack.pop();
|
|
693
675
|
resolutionPath.pop();
|
|
694
676
|
resolutionSet.delete(tokenDisplayName);
|
|
695
677
|
}
|
|
696
678
|
}
|
|
697
|
-
_resolveCandidateSync(binding, hint, resolutionPath,
|
|
679
|
+
_resolveCandidateSync(binding, hint, resolutionPath, resolutionStack) {
|
|
698
680
|
if (binding.kind === "constant" && binding.onActivation === void 0 && !this._lifecycle.hasActivationHandlers(binding.token)) return binding.value;
|
|
699
|
-
if (binding.kind === "alias") return this.resolve(binding.target, hint, resolutionPath,
|
|
681
|
+
if (binding.kind === "alias") return this.resolve(binding.target, hint, resolutionPath, resolutionStack);
|
|
700
682
|
const scope = binding.scope ?? "transient";
|
|
701
683
|
if (scope === "singleton" && this._scope.hasSingleton(binding.id)) return this._scope.getSingleton(binding.id);
|
|
702
684
|
if (scope === "scoped") {
|
|
703
685
|
if (!this._scope.isChild) throw new MissingScopeContextError(this._getTokenName(binding.token));
|
|
704
686
|
if (this._scope.hasScoped(binding.id)) return this._scope.getScoped(binding.id);
|
|
705
687
|
}
|
|
706
|
-
return this._resolveBinding(binding, hint, resolutionPath,
|
|
688
|
+
return this._resolveBinding(binding, hint, resolutionPath, resolutionStack);
|
|
707
689
|
}
|
|
708
|
-
_resolveCandidateAsync(binding, hint, resolutionPath,
|
|
690
|
+
_resolveCandidateAsync(binding, hint, resolutionPath, resolutionStack) {
|
|
709
691
|
if (binding.kind === "constant" && binding.onActivation === void 0 && !this._lifecycle.hasActivationHandlers(binding.token)) return Promise.resolve(binding.value);
|
|
710
692
|
const isolatedPath = [...resolutionPath];
|
|
711
|
-
const isolatedStack = [...
|
|
693
|
+
const isolatedStack = [...resolutionStack];
|
|
712
694
|
if (binding.kind === "alias") return this.resolveAsync(binding.target, hint, isolatedPath, isolatedStack);
|
|
713
695
|
const scope = binding.scope ?? "transient";
|
|
714
696
|
if (scope === "singleton" && this._scope.hasSingleton(binding.id)) return Promise.resolve(this._scope.getSingleton(binding.id));
|
|
@@ -718,11 +700,11 @@ var DependencyResolver = class {
|
|
|
718
700
|
}
|
|
719
701
|
return this._resolveBindingAsync(binding, hint, isolatedPath, isolatedStack);
|
|
720
702
|
}
|
|
721
|
-
|
|
703
|
+
_getResolutionFrame(binding) {
|
|
722
704
|
const existing = this._frameByBindingId.get(binding.id);
|
|
723
705
|
if (existing !== void 0) return existing;
|
|
724
706
|
const scope = binding.scope ?? "transient";
|
|
725
|
-
const frame =
|
|
707
|
+
const frame = buildResolutionFrame(tokenName(binding.token), scope, binding.id, binding.kind, binding.slot);
|
|
726
708
|
this._frameByBindingId.set(binding.id, frame);
|
|
727
709
|
return frame;
|
|
728
710
|
}
|
|
@@ -754,17 +736,29 @@ var DependencyResolver = class {
|
|
|
754
736
|
const hasPostConstruct = lifecycle !== void 0 && lifecycle.postConstruct !== void 0 && lifecycle.postConstruct.length > 0;
|
|
755
737
|
this._classHasPostConstruct.set(target, hasPostConstruct);
|
|
756
738
|
}
|
|
739
|
+
/**
|
|
740
|
+
* Refreshes the post-construct cache for class bindings on first instantiation and
|
|
741
|
+
* returns the (possibly updated) shouldActivate flag.
|
|
742
|
+
*/
|
|
743
|
+
_refreshActivationCacheIfNeeded(binding, needsActivation) {
|
|
744
|
+
if (binding.kind === "class" && this._classHasPostConstruct.get(binding.target) === void 0) {
|
|
745
|
+
this._refreshClassPostConstructCache(binding.target);
|
|
746
|
+
this._activationNeedByBindingId.delete(binding.id);
|
|
747
|
+
return this._needsActivation(binding);
|
|
748
|
+
}
|
|
749
|
+
return needsActivation;
|
|
750
|
+
}
|
|
757
751
|
_requiresResolutionContext(binding) {
|
|
758
752
|
return binding.kind === "dynamic" || binding.kind === "dynamic-async";
|
|
759
753
|
}
|
|
760
|
-
_acquireSyncResolutionContext(resolutionPath,
|
|
761
|
-
const depth =
|
|
754
|
+
_acquireSyncResolutionContext(resolutionPath, resolutionStack, hint) {
|
|
755
|
+
const depth = resolutionStack.length;
|
|
762
756
|
const existing = this._syncResolutionContextPool[depth];
|
|
763
757
|
if (existing !== void 0) {
|
|
764
|
-
existing.reset(this, resolutionPath,
|
|
758
|
+
existing.reset(this, resolutionPath, resolutionStack, hint);
|
|
765
759
|
return existing;
|
|
766
760
|
}
|
|
767
|
-
const created = new DefaultResolutionContext(this, resolutionPath,
|
|
761
|
+
const created = new DefaultResolutionContext(this, resolutionPath, resolutionStack, hint);
|
|
768
762
|
this._syncResolutionContextPool[depth] = created;
|
|
769
763
|
return created;
|
|
770
764
|
}
|