UNPKG

@notjustcoders/ioc-arise

Version:

Arise type-safe IoC containers from your code. Zero overhead, zero coupling.

73 lines 3.32 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.ModuleDependencyResolver = void 0; const topological_sorter_1 = require("../utils/topological-sorter"); class ModuleDependencyResolver { constructor(moduleGroupedClasses) { this.moduleGroupedClasses = moduleGroupedClasses; this.interfaceToModuleMap = this.buildInterfaceToModuleMap(); } resolve() { const moduleDependencies = this.buildModuleDependencyGraph(); const sortResult = this.topologicalSort(moduleDependencies); return { sortedModules: sortResult.sorted, cycles: sortResult.cycles, moduleDependencies }; } buildInterfaceToModuleMap() { const interfaceToModuleMap = new Map(); for (const [moduleName, classes] of this.moduleGroupedClasses) { for (const classInfo of classes) { // Map both interface names and class names to their modules if (classInfo.interfaceName) { interfaceToModuleMap.set(classInfo.interfaceName, moduleName); } // Also map class names to their modules for cross-module class dependencies interfaceToModuleMap.set(classInfo.name, moduleName); // For concrete classes that extend abstract classes, map the abstract class to this module if (classInfo.abstractClassName) { interfaceToModuleMap.set(classInfo.abstractClassName, moduleName); } } } return interfaceToModuleMap; } buildModuleDependencyGraph() { const moduleDependencies = new Map(); // Initialize all modules with empty dependency sets for (const moduleName of this.moduleGroupedClasses.keys()) { moduleDependencies.set(moduleName, new Set()); } // Analyze dependencies between modules for (const [moduleName, classes] of this.moduleGroupedClasses) { const moduleDeps = moduleDependencies.get(moduleName); for (const classInfo of classes) { for (const dependency of classInfo.dependencies) { // Check if this dependency is an interface or class from another module const dependencyModule = this.interfaceToModuleMap.get(dependency.name); if (dependencyModule && dependencyModule !== moduleName) { moduleDeps.add(dependencyModule); } } } } return moduleDependencies; } topologicalSort(moduleDependencies) { // Convert Map<string, Set<string>> to Map<string, string[]> for TopologicalSorter const graphMap = new Map(); for (const [module, deps] of moduleDependencies) { graphMap.set(module, Array.from(deps)); } return topological_sorter_1.TopologicalSorter.sort(graphMap, "desc"); } getModuleDependencies(moduleName) { const result = this.resolve(); const deps = result.moduleDependencies.get(moduleName); return deps ? Array.from(deps) : []; } } exports.ModuleDependencyResolver = ModuleDependencyResolver; //# sourceMappingURL=module-dependency-resolver.js.map