UNPKG

@samiyev/guardian

Version:

Research-backed code quality guardian for AI-assisted development. Detects hardcodes, secrets, circular deps, framework leaks, entity exposure, and 9 architecture violations. Enforces Clean Architecture/DDD principles. Works with GitHub Copilot, Cursor, W

86 lines 2.75 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.DependencyGraph = void 0; const BaseEntity_1 = require("./BaseEntity"); /** * Represents dependency graph of the analyzed project */ class DependencyGraph extends BaseEntity_1.BaseEntity { nodes; constructor(id) { super(id); this.nodes = new Map(); } addFile(file) { const fileId = file.path.relative; if (!this.nodes.has(fileId)) { this.nodes.set(fileId, { file, dependencies: [], dependents: [], }); } this.touch(); } addDependency(from, to) { const fromNode = this.nodes.get(from); const toNode = this.nodes.get(to); if (fromNode && toNode) { if (!fromNode.dependencies.includes(to)) { fromNode.dependencies.push(to); } if (!toNode.dependents.includes(from)) { toNode.dependents.push(from); } this.touch(); } } getNode(filePath) { return this.nodes.get(filePath); } getAllNodes() { return Array.from(this.nodes.values()); } findCycles() { const cycles = []; const visited = new Set(); const recursionStack = new Set(); const dfs = (nodeId, path) => { visited.add(nodeId); recursionStack.add(nodeId); path.push(nodeId); const node = this.nodes.get(nodeId); if (node) { for (const dep of node.dependencies) { if (!visited.has(dep)) { dfs(dep, [...path]); } else if (recursionStack.has(dep)) { const cycleStart = path.indexOf(dep); cycles.push(path.slice(cycleStart)); } } } recursionStack.delete(nodeId); }; for (const nodeId of this.nodes.keys()) { if (!visited.has(nodeId)) { dfs(nodeId, []); } } return cycles; } getMetrics() { const nodes = Array.from(this.nodes.values()); const totalFiles = nodes.length; const totalDependencies = nodes.reduce((sum, node) => sum + node.dependencies.length, 0); return { totalFiles, totalDependencies, avgDependencies: totalFiles > 0 ? totalDependencies / totalFiles : 0, maxDependencies: Math.max(...nodes.map((node) => node.dependencies.length), 0), }; } } exports.DependencyGraph = DependencyGraph; //# sourceMappingURL=DependencyGraph.js.map