@inversifyjs/core
Version:
InversifyJs core package
133 lines • 8.94 kB
JavaScript
import { InversifyCoreError } from '../../error/models/InversifyCoreError.js';
import { InversifyCoreErrorKind } from '../../error/models/InversifyCoreErrorKind.js';
import { ClassElementMetadataKind } from '../../metadata/models/ClassElementMetadataKind.js';
import { ResolvedValueElementMetadataKind } from '../../metadata/models/ResolvedValueElementMetadataKind.js';
import { getServiceFromMaybeLazyServiceIdentifier } from '../calculations/getServiceFromMaybeLazyServiceIdentifier.js';
import { isInstanceBindingNode } from '../calculations/isInstanceBindingNode.js';
import { tryBuildGetPlanOptionsFromManagedClassElementMetadata } from '../calculations/tryBuildGetPlanOptionsFromManagedClassElementMetadata.js';
import { tryBuildGetPlanOptionsFromResolvedValueElementMetadata } from '../calculations/tryBuildGetPlanOptionsFromResolvedValueElementMetadata.js';
import { LazyPlanServiceNode } from '../models/LazyPlanServiceNode.js';
import { cacheNonRootPlanServiceNode } from './cacheNonRootPlanServiceNode.js';
const MAX_PLAN_DEPTH = 500;
class LazyManagedClassMetadataPlanServiceNode extends LazyPlanServiceNode {
#params;
#buildLazyPlanServiceNodeNodeFromClassElementMetadata;
#bindingConstraintsList;
#elementMetadata;
constructor(params, buildLazyPlanServiceNodeNodeFromClassElementMetadata, bindingConstraintsList, elementMetadata, serviceNode) {
super(serviceNode, getServiceFromMaybeLazyServiceIdentifier(elementMetadata.value));
this.#buildLazyPlanServiceNodeNodeFromClassElementMetadata =
buildLazyPlanServiceNodeNodeFromClassElementMetadata;
this.#params = params;
this.#bindingConstraintsList = bindingConstraintsList;
this.#elementMetadata = elementMetadata;
}
_buildPlanServiceNode() {
return this.#buildLazyPlanServiceNodeNodeFromClassElementMetadata(this.#params, this.#bindingConstraintsList, this.#elementMetadata);
}
}
class LazyResolvedValueMetadataPlanServiceNode extends LazyPlanServiceNode {
#params;
#buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata;
#bindingConstraintsList;
#resolvedValueElementMetadata;
constructor(params, buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata, bindingConstraintsList, resolvedValueElementMetadata, serviceNode) {
super(serviceNode, getServiceFromMaybeLazyServiceIdentifier(resolvedValueElementMetadata.value));
this.#params = params;
this.#buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata =
buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata;
this.#bindingConstraintsList = bindingConstraintsList;
this.#resolvedValueElementMetadata = resolvedValueElementMetadata;
}
_buildPlanServiceNode() {
return this.#buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata(this.#params, this.#bindingConstraintsList, this.#resolvedValueElementMetadata);
}
}
export function currySubplan(buildLazyPlanServiceNodeNodeFromClassElementMetadata, buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata, buildPlanServiceNodeFromClassElementMetadata, buildPlanServiceNodeFromResolvedValueElementMetadata) {
const subplanInstanceBindingNode = currySubplanInstanceBindingNode(buildLazyPlanServiceNodeNodeFromClassElementMetadata, buildPlanServiceNodeFromClassElementMetadata);
const subplanResolvedValueBindingNode = currySubplanResolvedValueBindingNode(buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata, buildPlanServiceNodeFromResolvedValueElementMetadata);
return (params, bindingConstraintsList) => {
if (isInstanceBindingNode(params.node)) {
return subplanInstanceBindingNode(params, params.node, bindingConstraintsList);
}
else {
return subplanResolvedValueBindingNode(params, params.node, bindingConstraintsList);
}
};
}
function currySubplanInstanceBindingNode(buildLazyPlanServiceNodeNodeFromClassElementMetadata, buildPlanServiceNodeFromClassElementMetadata) {
const handlePlanServiceNodeBuildFromClassElementMetadata = curryHandlePlanServiceNodeBuildFromClassElementMetadata(buildLazyPlanServiceNodeNodeFromClassElementMetadata, buildPlanServiceNodeFromClassElementMetadata);
return (params, node, bindingConstraintsList) => {
const classMetadata = node.classMetadata;
for (const [index, elementMetadata,] of classMetadata.constructorArguments.entries()) {
node.constructorParams[index] =
handlePlanServiceNodeBuildFromClassElementMetadata(params, bindingConstraintsList, elementMetadata);
}
for (const [propertyKey, elementMetadata] of classMetadata.properties) {
const planServiceNode = handlePlanServiceNodeBuildFromClassElementMetadata(params, bindingConstraintsList, elementMetadata);
if (planServiceNode !== undefined) {
node.propertyParams.set(propertyKey, planServiceNode);
}
}
return params.node;
};
}
function currySubplanResolvedValueBindingNode(buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata, buildPlanServiceNodeFromResolvedValueElementMetadata) {
const handlePlanServiceNodeBuildFromResolvedValueElementMetadata = curryHandlePlanServiceNodeBuildFromResolvedValueElementMetadata(buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata, buildPlanServiceNodeFromResolvedValueElementMetadata);
return (params, node, bindingConstraintsList) => {
const resolvedValueMetadata = node.binding.metadata;
for (const [index, elementMetadata,] of resolvedValueMetadata.arguments.entries()) {
node.params[index] =
handlePlanServiceNodeBuildFromResolvedValueElementMetadata(params, bindingConstraintsList, elementMetadata);
}
return params.node;
};
}
function curryHandlePlanServiceNodeBuildFromClassElementMetadata(buildLazyPlanServiceNodeNodeFromClassElementMetadata, buildPlanServiceNodeFromClassElementMetadata) {
return (params, bindingConstraintsList, elementMetadata) => {
if (elementMetadata.kind === ClassElementMetadataKind.unmanaged) {
return undefined;
}
if (bindingConstraintsList.length > MAX_PLAN_DEPTH) {
throw new InversifyCoreError(InversifyCoreErrorKind.planningMaxDepthExceeded, 'Maximum plan depth exceeded. This is likely caused by a circular dependency.');
}
const getPlanOptions = tryBuildGetPlanOptionsFromManagedClassElementMetadata(elementMetadata);
if (getPlanOptions !== undefined) {
const planResult = params.operations.getPlan(getPlanOptions);
if (planResult !== undefined && planResult.tree.root.isContextFree) {
return planResult.tree.root;
}
}
const serviceNode = buildPlanServiceNodeFromClassElementMetadata(params, bindingConstraintsList, elementMetadata);
const lazyPlanServiceNode = new LazyManagedClassMetadataPlanServiceNode(params, buildLazyPlanServiceNodeNodeFromClassElementMetadata, bindingConstraintsList, elementMetadata, serviceNode);
cacheNonRootPlanServiceNode(getPlanOptions, params.operations, lazyPlanServiceNode, {
bindingConstraintsList,
chainedBindings: elementMetadata.kind === ClassElementMetadataKind.multipleInjection &&
elementMetadata.chained,
optionalBindings: elementMetadata.optional,
});
return lazyPlanServiceNode;
};
}
function curryHandlePlanServiceNodeBuildFromResolvedValueElementMetadata(buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata, buildPlanServiceNodeFromResolvedValueElementMetadata) {
return (params, bindingConstraintsList, elementMetadata) => {
const getPlanOptions = tryBuildGetPlanOptionsFromResolvedValueElementMetadata(elementMetadata);
if (getPlanOptions !== undefined) {
const planResult = params.operations.getPlan(getPlanOptions);
if (planResult !== undefined && planResult.tree.root.isContextFree) {
return planResult.tree.root;
}
}
const serviceNode = buildPlanServiceNodeFromResolvedValueElementMetadata(params, bindingConstraintsList, elementMetadata);
const lazyPlanServiceNode = new LazyResolvedValueMetadataPlanServiceNode(params, buildLazyPlanServiceNodeNodeFromResolvedValueElementMetadata, bindingConstraintsList, elementMetadata, serviceNode);
cacheNonRootPlanServiceNode(getPlanOptions, params.operations, lazyPlanServiceNode, {
bindingConstraintsList,
chainedBindings: elementMetadata.kind ===
ResolvedValueElementMetadataKind.multipleInjection &&
elementMetadata.chained,
optionalBindings: elementMetadata.optional,
});
return lazyPlanServiceNode;
};
}
//# sourceMappingURL=currySubplan.js.map