camouf 0.1.0

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.
Files changed (167) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +346 -0
  3. package/dist/cli/commands/analyze.d.ts +8 -0
  4. package/dist/cli/commands/analyze.d.ts.map +1 -0
  5. package/dist/cli/commands/analyze.js +81 -0
  6. package/dist/cli/commands/analyze.js.map +1 -0
  7. package/dist/cli/commands/init.d.ts +9 -0
  8. package/dist/cli/commands/init.d.ts.map +1 -0
  9. package/dist/cli/commands/init.js +104 -0
  10. package/dist/cli/commands/init.js.map +1 -0
  11. package/dist/cli/commands/report.d.ts +8 -0
  12. package/dist/cli/commands/report.d.ts.map +1 -0
  13. package/dist/cli/commands/report.js +63 -0
  14. package/dist/cli/commands/report.js.map +1 -0
  15. package/dist/cli/commands/validate.d.ts +9 -0
  16. package/dist/cli/commands/validate.d.ts.map +1 -0
  17. package/dist/cli/commands/validate.js +87 -0
  18. package/dist/cli/commands/validate.js.map +1 -0
  19. package/dist/cli/commands/watch.d.ts +9 -0
  20. package/dist/cli/commands/watch.d.ts.map +1 -0
  21. package/dist/cli/commands/watch.js +93 -0
  22. package/dist/cli/commands/watch.js.map +1 -0
  23. package/dist/cli/index.d.ts +9 -0
  24. package/dist/cli/index.d.ts.map +1 -0
  25. package/dist/cli/index.js +48 -0
  26. package/dist/cli/index.js.map +1 -0
  27. package/dist/cli/version.d.ts +16 -0
  28. package/dist/cli/version.d.ts.map +1 -0
  29. package/dist/cli/version.js +16 -0
  30. package/dist/cli/version.js.map +1 -0
  31. package/dist/core/analyzer/architecture-visualizer.d.ts +25 -0
  32. package/dist/core/analyzer/architecture-visualizer.d.ts.map +1 -0
  33. package/dist/core/analyzer/architecture-visualizer.js +333 -0
  34. package/dist/core/analyzer/architecture-visualizer.js.map +1 -0
  35. package/dist/core/analyzer/dependency-analyzer.d.ts +49 -0
  36. package/dist/core/analyzer/dependency-analyzer.d.ts.map +1 -0
  37. package/dist/core/analyzer/dependency-analyzer.js +242 -0
  38. package/dist/core/analyzer/dependency-analyzer.js.map +1 -0
  39. package/dist/core/config/config-schema.d.ts +280 -0
  40. package/dist/core/config/config-schema.d.ts.map +1 -0
  41. package/dist/core/config/config-schema.js +199 -0
  42. package/dist/core/config/config-schema.js.map +1 -0
  43. package/dist/core/config/configuration-manager.d.ts +82 -0
  44. package/dist/core/config/configuration-manager.d.ts.map +1 -0
  45. package/dist/core/config/configuration-manager.js +306 -0
  46. package/dist/core/config/configuration-manager.js.map +1 -0
  47. package/dist/core/logger.d.ts +27 -0
  48. package/dist/core/logger.d.ts.map +1 -0
  49. package/dist/core/logger.js +86 -0
  50. package/dist/core/logger.js.map +1 -0
  51. package/dist/core/parsers/go-parser.d.ts +16 -0
  52. package/dist/core/parsers/go-parser.d.ts.map +1 -0
  53. package/dist/core/parsers/go-parser.js +117 -0
  54. package/dist/core/parsers/go-parser.js.map +1 -0
  55. package/dist/core/parsers/java-parser.d.ts +22 -0
  56. package/dist/core/parsers/java-parser.d.ts.map +1 -0
  57. package/dist/core/parsers/java-parser.js +114 -0
  58. package/dist/core/parsers/java-parser.js.map +1 -0
  59. package/dist/core/parsers/javascript-parser.d.ts +14 -0
  60. package/dist/core/parsers/javascript-parser.d.ts.map +1 -0
  61. package/dist/core/parsers/javascript-parser.js +19 -0
  62. package/dist/core/parsers/javascript-parser.js.map +1 -0
  63. package/dist/core/parsers/parser-registry.d.ts +45 -0
  64. package/dist/core/parsers/parser-registry.d.ts.map +1 -0
  65. package/dist/core/parsers/parser-registry.js +121 -0
  66. package/dist/core/parsers/parser-registry.js.map +1 -0
  67. package/dist/core/parsers/parser.interface.d.ts +49 -0
  68. package/dist/core/parsers/parser.interface.d.ts.map +1 -0
  69. package/dist/core/parsers/parser.interface.js +7 -0
  70. package/dist/core/parsers/parser.interface.js.map +1 -0
  71. package/dist/core/parsers/python-parser.d.ts +22 -0
  72. package/dist/core/parsers/python-parser.d.ts.map +1 -0
  73. package/dist/core/parsers/python-parser.js +136 -0
  74. package/dist/core/parsers/python-parser.js.map +1 -0
  75. package/dist/core/parsers/rust-parser.d.ts +16 -0
  76. package/dist/core/parsers/rust-parser.d.ts.map +1 -0
  77. package/dist/core/parsers/rust-parser.js +176 -0
  78. package/dist/core/parsers/rust-parser.js.map +1 -0
  79. package/dist/core/parsers/typescript-parser.d.ts +29 -0
  80. package/dist/core/parsers/typescript-parser.d.ts.map +1 -0
  81. package/dist/core/parsers/typescript-parser.js +251 -0
  82. package/dist/core/parsers/typescript-parser.js.map +1 -0
  83. package/dist/core/reporter/report-generator.d.ts +31 -0
  84. package/dist/core/reporter/report-generator.d.ts.map +1 -0
  85. package/dist/core/reporter/report-generator.js +417 -0
  86. package/dist/core/reporter/report-generator.js.map +1 -0
  87. package/dist/core/reporter/violation-reporter.d.ts +62 -0
  88. package/dist/core/reporter/violation-reporter.d.ts.map +1 -0
  89. package/dist/core/reporter/violation-reporter.js +265 -0
  90. package/dist/core/reporter/violation-reporter.js.map +1 -0
  91. package/dist/core/rules/builtin/api-versioning.rule.d.ts +28 -0
  92. package/dist/core/rules/builtin/api-versioning.rule.d.ts.map +1 -0
  93. package/dist/core/rules/builtin/api-versioning.rule.js +103 -0
  94. package/dist/core/rules/builtin/api-versioning.rule.js.map +1 -0
  95. package/dist/core/rules/builtin/circular-dependencies.rule.d.ts +26 -0
  96. package/dist/core/rules/builtin/circular-dependencies.rule.d.ts.map +1 -0
  97. package/dist/core/rules/builtin/circular-dependencies.rule.js +99 -0
  98. package/dist/core/rules/builtin/circular-dependencies.rule.js.map +1 -0
  99. package/dist/core/rules/builtin/data-flow-integrity.rule.d.ts +27 -0
  100. package/dist/core/rules/builtin/data-flow-integrity.rule.d.ts.map +1 -0
  101. package/dist/core/rules/builtin/data-flow-integrity.rule.js +111 -0
  102. package/dist/core/rules/builtin/data-flow-integrity.rule.js.map +1 -0
  103. package/dist/core/rules/builtin/ddd-boundaries.rule.d.ts +31 -0
  104. package/dist/core/rules/builtin/ddd-boundaries.rule.d.ts.map +1 -0
  105. package/dist/core/rules/builtin/ddd-boundaries.rule.js +141 -0
  106. package/dist/core/rules/builtin/ddd-boundaries.rule.js.map +1 -0
  107. package/dist/core/rules/builtin/distributed-transactions.rule.d.ts +27 -0
  108. package/dist/core/rules/builtin/distributed-transactions.rule.d.ts.map +1 -0
  109. package/dist/core/rules/builtin/distributed-transactions.rule.js +134 -0
  110. package/dist/core/rules/builtin/distributed-transactions.rule.js.map +1 -0
  111. package/dist/core/rules/builtin/index.d.ts +16 -0
  112. package/dist/core/rules/builtin/index.d.ts.map +1 -0
  113. package/dist/core/rules/builtin/index.js +16 -0
  114. package/dist/core/rules/builtin/index.js.map +1 -0
  115. package/dist/core/rules/builtin/layer-dependencies.rule.d.ts +30 -0
  116. package/dist/core/rules/builtin/layer-dependencies.rule.d.ts.map +1 -0
  117. package/dist/core/rules/builtin/layer-dependencies.rule.js +102 -0
  118. package/dist/core/rules/builtin/layer-dependencies.rule.js.map +1 -0
  119. package/dist/core/rules/builtin/performance-antipatterns.rule.d.ts +29 -0
  120. package/dist/core/rules/builtin/performance-antipatterns.rule.d.ts.map +1 -0
  121. package/dist/core/rules/builtin/performance-antipatterns.rule.js +148 -0
  122. package/dist/core/rules/builtin/performance-antipatterns.rule.js.map +1 -0
  123. package/dist/core/rules/builtin/resilience-patterns.rule.d.ts +29 -0
  124. package/dist/core/rules/builtin/resilience-patterns.rule.d.ts.map +1 -0
  125. package/dist/core/rules/builtin/resilience-patterns.rule.js +123 -0
  126. package/dist/core/rules/builtin/resilience-patterns.rule.js.map +1 -0
  127. package/dist/core/rules/builtin/security-context.rule.d.ts +32 -0
  128. package/dist/core/rules/builtin/security-context.rule.d.ts.map +1 -0
  129. package/dist/core/rules/builtin/security-context.rule.js +145 -0
  130. package/dist/core/rules/builtin/security-context.rule.js.map +1 -0
  131. package/dist/core/rules/builtin/type-safety.rule.d.ts +32 -0
  132. package/dist/core/rules/builtin/type-safety.rule.d.ts.map +1 -0
  133. package/dist/core/rules/builtin/type-safety.rule.js +175 -0
  134. package/dist/core/rules/builtin/type-safety.rule.js.map +1 -0
  135. package/dist/core/rules/rule-engine.d.ts +72 -0
  136. package/dist/core/rules/rule-engine.d.ts.map +1 -0
  137. package/dist/core/rules/rule-engine.js +225 -0
  138. package/dist/core/rules/rule-engine.js.map +1 -0
  139. package/dist/core/rules/rule.interface.d.ts +169 -0
  140. package/dist/core/rules/rule.interface.d.ts.map +1 -0
  141. package/dist/core/rules/rule.interface.js +38 -0
  142. package/dist/core/rules/rule.interface.js.map +1 -0
  143. package/dist/core/scanner/project-detector.d.ts +51 -0
  144. package/dist/core/scanner/project-detector.d.ts.map +1 -0
  145. package/dist/core/scanner/project-detector.js +310 -0
  146. package/dist/core/scanner/project-detector.js.map +1 -0
  147. package/dist/core/scanner/project-scanner.d.ts +101 -0
  148. package/dist/core/scanner/project-scanner.d.ts.map +1 -0
  149. package/dist/core/scanner/project-scanner.js +321 -0
  150. package/dist/core/scanner/project-scanner.js.map +1 -0
  151. package/dist/core/watcher/file-watcher.d.ts +48 -0
  152. package/dist/core/watcher/file-watcher.d.ts.map +1 -0
  153. package/dist/core/watcher/file-watcher.js +124 -0
  154. package/dist/core/watcher/file-watcher.js.map +1 -0
  155. package/dist/types/config.types.d.ts +163 -0
  156. package/dist/types/config.types.d.ts.map +1 -0
  157. package/dist/types/config.types.js +36 -0
  158. package/dist/types/config.types.js.map +1 -0
  159. package/dist/types/core.types.d.ts +247 -0
  160. package/dist/types/core.types.d.ts.map +1 -0
  161. package/dist/types/core.types.js +7 -0
  162. package/dist/types/core.types.js.map +1 -0
  163. package/dist/types/index.d.ts +7 -0
  164. package/dist/types/index.d.ts.map +1 -0
  165. package/dist/types/index.js +7 -0
  166. package/dist/types/index.js.map +1 -0
  167. package/package.json +90 -0
@@ -0,0 +1,333 @@
1
+ /**
2
+ * Architecture Visualizer
3
+ *
4
+ * Generates visual representations of the architecture.
5
+ */
6
+ import * as fs from 'fs/promises';
7
+ import * as path from 'path';
8
+ export class ArchitectureVisualizer {
9
+ config;
10
+ constructor(config) {
11
+ this.config = config;
12
+ }
13
+ async generate(analysis, options) {
14
+ await fs.mkdir(options.outputPath, { recursive: true });
15
+ switch (options.format) {
16
+ case 'html':
17
+ await this.generateHtmlVisualization(analysis, options.outputPath);
18
+ break;
19
+ case 'dot':
20
+ await this.generateDotVisualization(analysis, options.outputPath);
21
+ break;
22
+ case 'json':
23
+ await this.generateJsonVisualization(analysis, options.outputPath);
24
+ break;
25
+ }
26
+ }
27
+ async generateHtmlVisualization(analysis, outputPath) {
28
+ // Generate interactive HTML visualization using D3.js
29
+ const html = `
30
+ <!DOCTYPE html>
31
+ <html lang="en">
32
+ <head>
33
+ <meta charset="UTF-8">
34
+ <meta name="viewport" content="width=device-width, initial-scale=1.0">
35
+ <title>Architecture Visualization - ${this.config.name || 'Project'}</title>
36
+ <script src="https://d3js.org/d3.v7.min.js"></script>
37
+ <style>
38
+ * { margin: 0; padding: 0; box-sizing: border-box; }
39
+ body {
40
+ font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, sans-serif;
41
+ background: #1a1a2e;
42
+ color: #eee;
43
+ overflow: hidden;
44
+ }
45
+ #container {
46
+ display: flex;
47
+ height: 100vh;
48
+ }
49
+ #sidebar {
50
+ width: 300px;
51
+ background: #16213e;
52
+ padding: 1rem;
53
+ overflow-y: auto;
54
+ }
55
+ #graph {
56
+ flex: 1;
57
+ position: relative;
58
+ }
59
+ h1 { font-size: 1.2rem; margin-bottom: 1rem; }
60
+ h2 { font-size: 1rem; margin: 1rem 0 0.5rem; color: #e94560; }
61
+ .stat { margin: 0.5rem 0; }
62
+ .stat-label { color: #aaa; font-size: 0.85rem; }
63
+ .stat-value { font-size: 1.5rem; font-weight: bold; color: #e94560; }
64
+ .list { list-style: none; }
65
+ .list li {
66
+ padding: 0.5rem;
67
+ margin: 0.25rem 0;
68
+ background: #0f3460;
69
+ border-radius: 4px;
70
+ font-size: 0.85rem;
71
+ white-space: nowrap;
72
+ overflow: hidden;
73
+ text-overflow: ellipsis;
74
+ }
75
+ .node circle {
76
+ stroke: #fff;
77
+ stroke-width: 1.5px;
78
+ }
79
+ .link {
80
+ stroke: #999;
81
+ stroke-opacity: 0.6;
82
+ }
83
+ .link.violation {
84
+ stroke: #e94560;
85
+ stroke-width: 2px;
86
+ }
87
+ .node text {
88
+ font-size: 10px;
89
+ fill: #eee;
90
+ }
91
+ .tooltip {
92
+ position: absolute;
93
+ background: #16213e;
94
+ padding: 0.5rem 1rem;
95
+ border-radius: 4px;
96
+ font-size: 0.85rem;
97
+ pointer-events: none;
98
+ opacity: 0;
99
+ transition: opacity 0.2s;
100
+ }
101
+ </style>
102
+ </head>
103
+ <body>
104
+ <div id="container">
105
+ <div id="sidebar">
106
+ <h1>🏗️ ${this.config.name || 'Project'}</h1>
107
+
108
+ <h2>📊 Summary</h2>
109
+ <div class="stat">
110
+ <div class="stat-label">Files</div>
111
+ <div class="stat-value">${analysis.summary.totalFiles}</div>
112
+ </div>
113
+ <div class="stat">
114
+ <div class="stat-label">Dependencies</div>
115
+ <div class="stat-value">${analysis.summary.totalDependencies}</div>
116
+ </div>
117
+ <div class="stat">
118
+ <div class="stat-label">Circular Deps</div>
119
+ <div class="stat-value">${analysis.summary.circularDependencies}</div>
120
+ </div>
121
+ <div class="stat">
122
+ <div class="stat-label">Avg Coupling</div>
123
+ <div class="stat-value">${analysis.summary.averageCoupling.toFixed(1)}</div>
124
+ </div>
125
+
126
+ <h2>🔥 Hotspots</h2>
127
+ <ul class="list">
128
+ ${analysis.hotspots.slice(0, 10).map(h => `<li title="${h.file}">${this.getFileName(h.file)} (${h.dependents})</li>`).join('')}
129
+ </ul>
130
+
131
+ <h2>💡 Suggestions</h2>
132
+ <ul class="list">
133
+ ${analysis.suggestions.map(s => `<li title="${s}">${s}</li>`).join('')}
134
+ </ul>
135
+ </div>
136
+
137
+ <div id="graph">
138
+ <div class="tooltip" id="tooltip"></div>
139
+ </div>
140
+ </div>
141
+
142
+ <script>
143
+ const data = ${JSON.stringify(this.prepareGraphData(analysis))};
144
+
145
+ const container = document.getElementById('graph');
146
+ const width = container.clientWidth;
147
+ const height = container.clientHeight;
148
+
149
+ const svg = d3.select('#graph')
150
+ .append('svg')
151
+ .attr('width', width)
152
+ .attr('height', height);
153
+
154
+ const g = svg.append('g');
155
+
156
+ // Zoom behavior
157
+ const zoom = d3.zoom()
158
+ .scaleExtent([0.1, 4])
159
+ .on('zoom', (event) => g.attr('transform', event.transform));
160
+
161
+ svg.call(zoom);
162
+
163
+ // Force simulation
164
+ const simulation = d3.forceSimulation(data.nodes)
165
+ .force('link', d3.forceLink(data.links).id(d => d.id).distance(100))
166
+ .force('charge', d3.forceManyBody().strength(-300))
167
+ .force('center', d3.forceCenter(width / 2, height / 2))
168
+ .force('collision', d3.forceCollide().radius(30));
169
+
170
+ // Links
171
+ const link = g.append('g')
172
+ .selectAll('line')
173
+ .data(data.links)
174
+ .join('line')
175
+ .attr('class', d => d.violation ? 'link violation' : 'link');
176
+
177
+ // Nodes
178
+ const node = g.append('g')
179
+ .selectAll('.node')
180
+ .data(data.nodes)
181
+ .join('g')
182
+ .attr('class', 'node')
183
+ .call(d3.drag()
184
+ .on('start', dragstarted)
185
+ .on('drag', dragged)
186
+ .on('end', dragended));
187
+
188
+ node.append('circle')
189
+ .attr('r', d => Math.min(5 + d.size * 2, 20))
190
+ .attr('fill', d => d.color);
191
+
192
+ node.append('text')
193
+ .attr('dx', 12)
194
+ .attr('dy', 4)
195
+ .text(d => d.label);
196
+
197
+ // Tooltip
198
+ const tooltip = d3.select('#tooltip');
199
+
200
+ node.on('mouseover', (event, d) => {
201
+ tooltip
202
+ .style('opacity', 1)
203
+ .html(\`<strong>\${d.label}</strong><br/>Deps: \${d.deps}<br/>Dependents: \${d.dependents}\`)
204
+ .style('left', (event.pageX + 10) + 'px')
205
+ .style('top', (event.pageY - 10) + 'px');
206
+ })
207
+ .on('mouseout', () => {
208
+ tooltip.style('opacity', 0);
209
+ });
210
+
211
+ simulation.on('tick', () => {
212
+ link
213
+ .attr('x1', d => d.source.x)
214
+ .attr('y1', d => d.source.y)
215
+ .attr('x2', d => d.target.x)
216
+ .attr('y2', d => d.target.y);
217
+
218
+ node.attr('transform', d => \`translate(\${d.x},\${d.y})\`);
219
+ });
220
+
221
+ function dragstarted(event) {
222
+ if (!event.active) simulation.alphaTarget(0.3).restart();
223
+ event.subject.fx = event.subject.x;
224
+ event.subject.fy = event.subject.y;
225
+ }
226
+
227
+ function dragged(event) {
228
+ event.subject.fx = event.x;
229
+ event.subject.fy = event.y;
230
+ }
231
+
232
+ function dragended(event) {
233
+ if (!event.active) simulation.alphaTarget(0);
234
+ event.subject.fx = null;
235
+ event.subject.fy = null;
236
+ }
237
+ </script>
238
+ </body>
239
+ </html>
240
+ `.trim();
241
+ await fs.writeFile(path.join(outputPath, 'visualization.html'), html);
242
+ }
243
+ async generateDotVisualization(analysis, outputPath) {
244
+ // Generate GraphViz DOT format
245
+ let dot = `digraph Architecture {\n`;
246
+ dot += ` rankdir=LR;\n`;
247
+ dot += ` node [shape=box, style=filled, fillcolor=lightblue];\n`;
248
+ dot += ` edge [color=gray];\n\n`;
249
+ // Add layer subgraphs
250
+ const layerFiles = new Map();
251
+ for (const hotspot of analysis.hotspots) {
252
+ const layer = this.getLayerForFile(hotspot.file);
253
+ if (layer) {
254
+ const files = layerFiles.get(layer) || [];
255
+ files.push(hotspot.file);
256
+ layerFiles.set(layer, files);
257
+ }
258
+ }
259
+ for (const [layer, files] of layerFiles) {
260
+ dot += ` subgraph cluster_${layer} {\n`;
261
+ dot += ` label="${layer}";\n`;
262
+ dot += ` style=filled;\n`;
263
+ dot += ` color=lightgrey;\n`;
264
+ for (const file of files) {
265
+ const safeName = this.sanitizeNodeName(file);
266
+ dot += ` "${safeName}" [label="${this.getFileName(file)}"];\n`;
267
+ }
268
+ dot += ` }\n\n`;
269
+ }
270
+ // Add edges for circular dependencies
271
+ for (const cycle of analysis.circularDependencies) {
272
+ for (let i = 0; i < cycle.cycle.length; i++) {
273
+ const from = this.sanitizeNodeName(cycle.cycle[i]);
274
+ const to = this.sanitizeNodeName(cycle.cycle[(i + 1) % cycle.cycle.length]);
275
+ dot += ` "${from}" -> "${to}" [color=red, style=bold];\n`;
276
+ }
277
+ }
278
+ dot += `}\n`;
279
+ await fs.writeFile(path.join(outputPath, 'architecture.dot'), dot);
280
+ }
281
+ async generateJsonVisualization(analysis, outputPath) {
282
+ const graphData = this.prepareGraphData(analysis);
283
+ await fs.writeFile(path.join(outputPath, 'graph-data.json'), JSON.stringify(graphData, null, 2));
284
+ }
285
+ prepareGraphData(analysis) {
286
+ const layerColors = {
287
+ presentation: '#4ecca3',
288
+ application: '#45aaf2',
289
+ domain: '#f7b731',
290
+ infrastructure: '#fc5c65',
291
+ shared: '#a55eea',
292
+ };
293
+ const nodes = analysis.hotspots.map(h => ({
294
+ id: h.file,
295
+ label: this.getFileName(h.file),
296
+ color: layerColors[this.getLayerForFile(h.file) || 'shared'] || '#999',
297
+ size: h.dependents,
298
+ deps: h.dependencies,
299
+ dependents: h.dependents,
300
+ }));
301
+ const links = [];
302
+ // Add circular dependency links
303
+ for (const cycle of analysis.circularDependencies) {
304
+ for (let i = 0; i < cycle.cycle.length; i++) {
305
+ links.push({
306
+ source: cycle.cycle[i],
307
+ target: cycle.cycle[(i + 1) % cycle.cycle.length],
308
+ violation: true,
309
+ });
310
+ }
311
+ }
312
+ return { nodes, links };
313
+ }
314
+ getFileName(filePath) {
315
+ return path.basename(filePath);
316
+ }
317
+ getLayerForFile(filePath) {
318
+ const normalizedPath = filePath.replace(/\\/g, '/').toLowerCase();
319
+ for (const layer of this.config.layers) {
320
+ for (const dir of layer.directories) {
321
+ const normalizedDir = dir.replace(/\\/g, '/').toLowerCase();
322
+ if (normalizedPath.startsWith(normalizedDir + '/') || normalizedPath === normalizedDir) {
323
+ return layer.name;
324
+ }
325
+ }
326
+ }
327
+ return undefined;
328
+ }
329
+ sanitizeNodeName(name) {
330
+ return name.replace(/[^a-zA-Z0-9]/g, '_');
331
+ }
332
+ }
333
+ //# sourceMappingURL=architecture-visualizer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"architecture-visualizer.js","sourceRoot":"","sources":["../../../src/core/analyzer/architecture-visualizer.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,49 @@
1
+ /**
2
+ * Dependency Analyzer
3
+ *
4
+ * Analyzes the dependency graph for insights and metrics.
5
+ */
6
+ import { CamoufConfig } from '../../types/config.types.js';
7
+ import { AnalysisResult } from '../../types/core.types.js';
8
+ import { DependencyGraph } from '../scanner/project-scanner.js';
9
+ interface AnalyzeOptions {
10
+ maxDepth?: number;
11
+ focus?: string;
12
+ includeMetrics?: boolean;
13
+ analyzeCoupling?: boolean;
14
+ }
15
+ export declare class DependencyAnalyzer {
16
+ private config;
17
+ constructor(config: CamoufConfig);
18
+ analyze(graph: DependencyGraph, options?: AnalyzeOptions): Promise<AnalysisResult>;
19
+ /**
20
+ * Find all circular dependencies using DFS
21
+ */
22
+ private findCircularDependencies;
23
+ /**
24
+ * Find layer violations
25
+ */
26
+ private findLayerViolations;
27
+ /**
28
+ * Calculate coupling metrics
29
+ */
30
+ private calculateCouplingMetrics;
31
+ /**
32
+ * Find hotspot files (high coupling)
33
+ */
34
+ private findHotspots;
35
+ /**
36
+ * Calculate detailed file metrics
37
+ */
38
+ private calculateFileMetrics;
39
+ /**
40
+ * Generate improvement suggestions
41
+ */
42
+ private generateSuggestions;
43
+ /**
44
+ * Get layer for a file path
45
+ */
46
+ private getLayerForFile;
47
+ }
48
+ export {};
49
+ //# sourceMappingURL=dependency-analyzer.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dependency-analyzer.d.ts","sourceRoot":"","sources":["../../../src/core/analyzer/dependency-analyzer.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAC3D,OAAO,EAAE,cAAc,EAA6E,MAAM,2BAA2B,CAAC;AACtI,OAAO,EAAE,eAAe,EAAE,MAAM,+BAA+B,CAAC;AAGhE,UAAU,cAAc;IACtB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,eAAe,CAAC,EAAE,OAAO,CAAC;CAC3B;AAED,qBAAa,kBAAkB;IAC7B,OAAO,CAAC,MAAM,CAAe;gBAEjB,MAAM,EAAE,YAAY;IAI1B,OAAO,CAAC,KAAK,EAAE,eAAe,EAAE,OAAO,GAAE,cAAmB,GAAG,OAAO,CAAC,cAAc,CAAC;IAuD5F;;OAEG;IACH,OAAO,CAAC,wBAAwB;IAqDhC;;OAEG;IACH,OAAO,CAAC,mBAAmB;IAyC3B;;OAEG;IACH,OAAO,CAAC,wBAAwB;IAsBhC;;OAEG;IACH,OAAO,CAAC,YAAY;IAyBpB;;OAEG;YACW,oBAAoB;IAmBlC;;OAEG;IACH,OAAO,CAAC,mBAAmB;IA+D3B;;OAEG;IACH,OAAO,CAAC,eAAe;CAWxB"}
@@ -0,0 +1,242 @@
1
+ /**
2
+ * Dependency Analyzer
3
+ *
4
+ * Analyzes the dependency graph for insights and metrics.
5
+ */
6
+ import { Logger } from '../logger.js';
7
+ export class DependencyAnalyzer {
8
+ config;
9
+ constructor(config) {
10
+ this.config = config;
11
+ }
12
+ async analyze(graph, options = {}) {
13
+ Logger.debug('Starting dependency analysis...');
14
+ const nodes = graph.nodes();
15
+ const edges = graph.edges();
16
+ // Calculate basic metrics
17
+ const totalFiles = nodes.length;
18
+ const totalDependencies = edges.length;
19
+ // Find circular dependencies
20
+ const circularDependencies = this.findCircularDependencies(graph);
21
+ // Find layer violations
22
+ const layerViolations = this.findLayerViolations(graph);
23
+ // Calculate coupling metrics
24
+ const couplingMetrics = this.calculateCouplingMetrics(graph);
25
+ // Find hotspots (files with most dependencies/dependents)
26
+ const hotspots = this.findHotspots(graph);
27
+ // Generate file metrics if requested
28
+ const fileMetrics = options.includeMetrics
29
+ ? await this.calculateFileMetrics(graph)
30
+ : undefined;
31
+ // Generate suggestions
32
+ const suggestions = this.generateSuggestions({
33
+ totalFiles,
34
+ circularDependencies,
35
+ layerViolations,
36
+ hotspots,
37
+ couplingMetrics,
38
+ });
39
+ const summary = {
40
+ totalFiles,
41
+ totalDependencies,
42
+ circularDependencies: circularDependencies.length,
43
+ averageCoupling: couplingMetrics.average,
44
+ maxCoupling: couplingMetrics.max,
45
+ layerViolations: layerViolations.length,
46
+ };
47
+ return {
48
+ summary,
49
+ hotspots,
50
+ circularDependencies,
51
+ layerViolations,
52
+ suggestions,
53
+ fileMetrics,
54
+ };
55
+ }
56
+ /**
57
+ * Find all circular dependencies using DFS
58
+ */
59
+ findCircularDependencies(graph) {
60
+ const cycles = [];
61
+ const visited = new Set();
62
+ const recursionStack = new Set();
63
+ const path = [];
64
+ const dfs = (node) => {
65
+ visited.add(node);
66
+ recursionStack.add(node);
67
+ path.push(node);
68
+ const outEdges = graph.outEdges(node) || [];
69
+ for (const edge of outEdges) {
70
+ const neighbor = edge.w;
71
+ if (!visited.has(neighbor)) {
72
+ dfs(neighbor);
73
+ }
74
+ else if (recursionStack.has(neighbor)) {
75
+ // Found a cycle
76
+ const cycleStart = path.indexOf(neighbor);
77
+ if (cycleStart !== -1) {
78
+ const cycle = path.slice(cycleStart);
79
+ // Only add if not a duplicate
80
+ const cycleKey = [...cycle].sort().join(',');
81
+ const exists = cycles.some(c => [...c.cycle].sort().join(',') === cycleKey);
82
+ if (!exists && cycle.length > 1) {
83
+ cycles.push({
84
+ cycle,
85
+ files: cycle,
86
+ });
87
+ }
88
+ }
89
+ }
90
+ }
91
+ path.pop();
92
+ recursionStack.delete(node);
93
+ };
94
+ for (const node of graph.nodes()) {
95
+ if (!visited.has(node)) {
96
+ dfs(node);
97
+ }
98
+ }
99
+ return cycles;
100
+ }
101
+ /**
102
+ * Find layer violations
103
+ */
104
+ findLayerViolations(graph) {
105
+ const violations = [];
106
+ // Build layer map
107
+ const layerMap = new Map();
108
+ const allowedDeps = new Map();
109
+ for (const layer of this.config.layers) {
110
+ for (const dir of layer.directories) {
111
+ const normalizedDir = dir.replace(/\\/g, '/').toLowerCase();
112
+ layerMap.set(normalizedDir, layer.name);
113
+ }
114
+ allowedDeps.set(layer.name, new Set(layer.allowedDependencies));
115
+ }
116
+ // Check each edge
117
+ for (const edge of graph.edges()) {
118
+ const sourceNode = graph.node(edge.v);
119
+ const targetNode = graph.node(edge.w);
120
+ if (!sourceNode || !targetNode)
121
+ continue;
122
+ const sourceLayer = this.getLayerForFile(sourceNode.data.relativePath, layerMap);
123
+ const targetLayer = this.getLayerForFile(targetNode.data.relativePath, layerMap);
124
+ if (!sourceLayer || !targetLayer || sourceLayer === targetLayer)
125
+ continue;
126
+ const allowed = allowedDeps.get(sourceLayer);
127
+ if (!allowed?.has(targetLayer) && !allowed?.has('*')) {
128
+ violations.push({
129
+ sourceLayer,
130
+ targetLayer,
131
+ file: sourceNode.data.relativePath,
132
+ dependency: targetNode.data.relativePath,
133
+ });
134
+ }
135
+ }
136
+ return violations;
137
+ }
138
+ /**
139
+ * Calculate coupling metrics
140
+ */
141
+ calculateCouplingMetrics(graph) {
142
+ const couplings = [];
143
+ for (const node of graph.nodes()) {
144
+ const inDegree = (graph.inEdges(node) || []).length;
145
+ const outDegree = (graph.outEdges(node) || []).length;
146
+ const coupling = inDegree + outDegree;
147
+ couplings.push(coupling);
148
+ }
149
+ if (couplings.length === 0) {
150
+ return { average: 0, max: 0, min: 0 };
151
+ }
152
+ const sum = couplings.reduce((a, b) => a + b, 0);
153
+ const average = sum / couplings.length;
154
+ const max = Math.max(...couplings);
155
+ const min = Math.min(...couplings);
156
+ return { average, max, min };
157
+ }
158
+ /**
159
+ * Find hotspot files (high coupling)
160
+ */
161
+ findHotspots(graph) {
162
+ const hotspots = [];
163
+ for (const node of graph.nodes()) {
164
+ const inEdges = graph.inEdges(node) || [];
165
+ const outEdges = graph.outEdges(node) || [];
166
+ const dependents = inEdges.length;
167
+ const dependencies = outEdges.length;
168
+ const coupling = dependents + dependencies;
169
+ hotspots.push({
170
+ file: node,
171
+ dependents,
172
+ dependencies,
173
+ coupling,
174
+ });
175
+ }
176
+ // Sort by number of dependents (most depended upon)
177
+ hotspots.sort((a, b) => b.dependents - a.dependents);
178
+ return hotspots.slice(0, 20);
179
+ }
180
+ /**
181
+ * Calculate detailed file metrics
182
+ */
183
+ async calculateFileMetrics(graph) {
184
+ const metrics = [];
185
+ for (const node of graph.nodes()) {
186
+ const nodeData = graph.node(node);
187
+ const inEdges = graph.inEdges(node) || [];
188
+ const outEdges = graph.outEdges(node) || [];
189
+ metrics.push({
190
+ file: node,
191
+ linesOfCode: 0, // Would need to read file to calculate
192
+ dependencies: outEdges.length,
193
+ dependents: inEdges.length,
194
+ });
195
+ }
196
+ return metrics;
197
+ }
198
+ /**
199
+ * Generate improvement suggestions
200
+ */
201
+ generateSuggestions(data) {
202
+ const suggestions = [];
203
+ // Circular dependencies suggestions
204
+ if (data.circularDependencies.length > 0) {
205
+ suggestions.push(`Found ${data.circularDependencies.length} circular dependency chains. Consider:`, ` - Extracting shared code to a common module`, ` - Using dependency injection`, ` - Applying the mediator pattern for complex interactions`);
206
+ }
207
+ // Layer violation suggestions
208
+ if (data.layerViolations.length > 0) {
209
+ suggestions.push(`Found ${data.layerViolations.length} layer violations. Consider:`, ` - Moving shared code to the 'shared' layer`, ` - Using interfaces for cross-layer communication`, ` - Restructuring to follow the defined architecture`);
210
+ }
211
+ // High coupling suggestions
212
+ if (data.couplingMetrics.max > 20) {
213
+ const highCouplingFiles = data.hotspots.filter(h => h.coupling > 15);
214
+ if (highCouplingFiles.length > 0) {
215
+ suggestions.push(`${highCouplingFiles.length} files have high coupling (>15 connections). Consider:`, ` - Breaking large files into smaller, focused modules`, ` - Applying the single responsibility principle`, ` - Creating facade modules to reduce direct dependencies`);
216
+ }
217
+ }
218
+ // Hotspot suggestions
219
+ const superHotspots = data.hotspots.filter(h => h.dependents > 10);
220
+ if (superHotspots.length > 0) {
221
+ suggestions.push(`${superHotspots.length} files are depended upon by >10 other files:`, ...superHotspots.slice(0, 3).map(h => ` - ${h.file} (${h.dependents} dependents)`), ` These might be good candidates for optimization or splitting.`);
222
+ }
223
+ // General suggestions if no issues
224
+ if (suggestions.length === 0) {
225
+ suggestions.push(`✨ Great job! No major architectural issues detected.`, `Continue monitoring as your codebase grows.`);
226
+ }
227
+ return suggestions;
228
+ }
229
+ /**
230
+ * Get layer for a file path
231
+ */
232
+ getLayerForFile(filePath, layerMap) {
233
+ const normalizedPath = filePath.replace(/\\/g, '/').toLowerCase();
234
+ for (const [dir, layer] of layerMap) {
235
+ if (normalizedPath.startsWith(dir + '/') || normalizedPath === dir) {
236
+ return layer;
237
+ }
238
+ }
239
+ return undefined;
240
+ }
241
+ }
242
+ //# sourceMappingURL=dependency-analyzer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dependency-analyzer.js","sourceRoot":"","sources":["../../../src/core/analyzer/dependency-analyzer.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAKH,OAAO,EAAE,MAAM,EAAE,MAAM,cAAc,CAAC;AAStC,MAAM,OAAO,kBAAkB;IACrB,MAAM,CAAe;IAE7B,YAAY,MAAoB;QAC9B,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;IACvB,CAAC;IAED,KAAK,CAAC,OAAO,CAAC,KAAsB,EAAE,UAA0B,EAAE;QAChE,MAAM,CAAC,KAAK,CAAC,iCAAiC,CAAC,CAAC;QAEhD,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,EAAE,CAAC;QAC5B,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,EAAE,CAAC;QAE5B,0BAA0B;QAC1B,MAAM,UAAU,GAAG,KAAK,CAAC,MAAM,CAAC;QAChC,MAAM,iBAAiB,GAAG,KAAK,CAAC,MAAM,CAAC;QAEvC,6BAA6B;QAC7B,MAAM,oBAAoB,GAAG,IAAI,CAAC,wBAAwB,CAAC,KAAK,CAAC,CAAC;QAElE,wBAAwB;QACxB,MAAM,eAAe,GAAG,IAAI,CAAC,mBAAmB,CAAC,KAAK,CAAC,CAAC;QAExD,6BAA6B;QAC7B,MAAM,eAAe,GAAG,IAAI,CAAC,wBAAwB,CAAC,KAAK,CAAC,CAAC;QAE7D,0DAA0D;QAC1D,MAAM,QAAQ,GAAG,IAAI,CAAC,YAAY,CAAC,KAAK,CAAC,CAAC;QAE1C,qCAAqC;QACrC,MAAM,WAAW,GAAG,OAAO,CAAC,cAAc;YACxC,CAAC,CAAC,MAAM,IAAI,CAAC,oBAAoB,CAAC,KAAK,CAAC;YACxC,CAAC,CAAC,SAAS,CAAC;QAEd,uBAAuB;QACvB,MAAM,WAAW,GAAG,IAAI,CAAC,mBAAmB,CAAC;YAC3C,UAAU;YACV,oBAAoB;YACpB,eAAe;YACf,QAAQ;YACR,eAAe;SAChB,CAAC,CAAC;QAEH,MAAM,OAAO,GAAoB;YAC/B,UAAU;YACV,iBAAiB;YACjB,oBAAoB,EAAE,oBAAoB,CAAC,MAAM;YACjD,eAAe,EAAE,eAAe,CAAC,OAAO;YACxC,WAAW,EAAE,eAAe,CAAC,GAAG;YAChC,eAAe,EAAE,eAAe,CAAC,MAAM;SACxC,CAAC;QAEF,OAAO;YACL,OAAO;YACP,QAAQ;YACR,oBAAoB;YACpB,eAAe;YACf,WAAW;YACX,WAAW;SACZ,CAAC;IACJ,CAAC;IAED;;OAEG;IACK,wBAAwB,CAAC,KAAsB;QACrD,MAAM,MAAM,GAAyB,EAAE,CAAC;QACxC,MAAM,OAAO,GAAG,IAAI,GAAG,EAAU,CAAC;QAClC,MAAM,cAAc,GAAG,IAAI,GAAG,EAAU,CAAC;QACzC,MAAM,IAAI,GAAa,EAAE,CAAC;QAE1B,MAAM,GAAG,GAAG,CAAC,IAAY,EAAQ,EAAE;YACjC,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;YAClB,cAAc,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;YACzB,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YAEhB,MAAM,QAAQ,GAAG,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC;YAE5C,KAAK,MAAM,IAAI,IAAI,QAAQ,EAAE,CAAC;gBAC5B,MAAM,QAAQ,GAAG,IAAI,CAAC,CAAC,CAAC;gBAExB,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE,CAAC;oBAC3B,GAAG,CAAC,QAAQ,CAAC,CAAC;gBAChB,CAAC;qBAAM,IAAI,cAAc,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE,CAAC;oBACxC,gBAAgB;oBAChB,MAAM,UAAU,GAAG,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;oBAC1C,IAAI,UAAU,KAAK,CAAC,CAAC,EAAE,CAAC;wBACtB,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC;wBAErC,8BAA8B;wBAC9B,MAAM,QAAQ,GAAG,CAAC,GAAG,KAAK,CAAC,CAAC,IAAI,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;wBAC7C,MAAM,MAAM,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAC7B,CAAC,GAAG,CAAC,CAAC,KAAK,CAAC,CAAC,IAAI,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,KAAK,QAAQ,CAC3C,CAAC;wBAEF,IAAI,CAAC,MAAM,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;4BAChC,MAAM,CAAC,IAAI,CAAC;gCACV,KAAK;gCACL,KAAK,EAAE,KAAK;6BACb,CAAC,CAAC;wBACL,CAAC;oBACH,CAAC;gBACH,CAAC;YACH,CAAC;YAED,IAAI,CAAC,GAAG,EAAE,CAAC;YACX,cAAc,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;QAC9B,CAAC,CAAC;QAEF,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,KAAK,EAAE,EAAE,CAAC;YACjC,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC;gBACvB,GAAG,CAAC,IAAI,CAAC,CAAC;YACZ,CAAC;QACH,CAAC;QAED,OAAO,MAAM,CAAC;IAChB,CAAC;IAED;;OAEG;IACK,mBAAmB,CAAC,KAAsB;QAChD,MAAM,UAAU,GAAqB,EAAE,CAAC;QAExC,kBAAkB;QAClB,MAAM,QAAQ,GAAG,IAAI,GAAG,EAAkB,CAAC;QAC3C,MAAM,WAAW,GAAG,IAAI,GAAG,EAAuB,CAAC;QAEnD,KAAK,MAAM,KAAK,IAAI,IAAI,CAAC,MAAM,CAAC,MAAM,EAAE,CAAC;YACvC,KAAK,MAAM,GAAG,IAAI,KAAK,CAAC,WAAW,EAAE,CAAC;gBACpC,MAAM,aAAa,GAAG,GAAG,CAAC,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC,WAAW,EAAE,CAAC;gBAC5D,QAAQ,CAAC,GAAG,CAAC,aAAa,EAAE,KAAK,CAAC,IAAI,CAAC,CAAC;YAC1C,CAAC;YACD,WAAW,CAAC,GAAG,CAAC,KAAK,CAAC,IAAI,EAAE,IAAI,GAAG,CAAC,KAAK,CAAC,mBAAmB,CAAC,CAAC,CAAC;QAClE,CAAC;QAED,kBAAkB;QAClB,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,KAAK,EAAE,EAAE,CAAC;YACjC,MAAM,UAAU,GAAG,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YACtC,MAAM,UAAU,GAAG,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;YAEtC,IAAI,CAAC,UAAU,IAAI,CAAC,UAAU;gBAAE,SAAS;YAEzC,MAAM,WAAW,GAAG,IAAI,CAAC,eAAe,CAAC,UAAU,CAAC,IAAI,CAAC,YAAY,EAAE,QAAQ,CAAC,CAAC;YACjF,MAAM,WAAW,GAAG,IAAI,CAAC,eAAe,CAAC,UAAU,CAAC,IAAI,CAAC,YAAY,EAAE,QAAQ,CAAC,CAAC;YAEjF,IAAI,CAAC,WAAW,IAAI,CAAC,WAAW,IAAI,WAAW,KAAK,WAAW;gBAAE,SAAS;YAE1E,MAAM,OAAO,GAAG,WAAW,CAAC,GAAG,CAAC,WAAW,CAAC,CAAC;YAC7C,IAAI,CAAC,OAAO,EAAE,GAAG,CAAC,WAAW,CAAC,IAAI,CAAC,OAAO,EAAE,GAAG,CAAC,GAAG,CAAC,EAAE,CAAC;gBACrD,UAAU,CAAC,IAAI,CAAC;oBACd,WAAW;oBACX,WAAW;oBACX,IAAI,EAAE,UAAU,CAAC,IAAI,CAAC,YAAY;oBAClC,UAAU,EAAE,UAAU,CAAC,IAAI,CAAC,YAAY;iBACzC,CAAC,CAAC;YACL,CAAC;QACH,CAAC;QAED,OAAO,UAAU,CAAC;IACpB,CAAC;IAED;;OAEG;IACK,wBAAwB,CAAC,KAAsB;QACrD,MAAM,SAAS,GAAa,EAAE,CAAC;QAE/B,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,KAAK,EAAE,EAAE,CAAC;YACjC,MAAM,QAAQ,GAAG,CAAC,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC,CAAC,MAAM,CAAC;YACpD,MAAM,SAAS,GAAG,CAAC,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC,CAAC,MAAM,CAAC;YACtD,MAAM,QAAQ,GAAG,QAAQ,GAAG,SAAS,CAAC;YACtC,SAAS,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QAC3B,CAAC;QAED,IAAI,SAAS,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC3B,OAAO,EAAE,OAAO,EAAE,CAAC,EAAE,GAAG,EAAE,CAAC,EAAE,GAAG,EAAE,CAAC,EAAE,CAAC;QACxC,CAAC;QAED,MAAM,GAAG,GAAG,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,CAAC;QACjD,MAAM,OAAO,GAAG,GAAG,GAAG,SAAS,CAAC,MAAM,CAAC;QACvC,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC,GAAG,SAAS,CAAC,CAAC;QACnC,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC,GAAG,SAAS,CAAC,CAAC;QAEnC,OAAO,EAAE,OAAO,EAAE,GAAG,EAAE,GAAG,EAAE,CAAC;IAC/B,CAAC;IAED;;OAEG;IACK,YAAY,CAAC,KAAsB;QACzC,MAAM,QAAQ,GAAc,EAAE,CAAC;QAE/B,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,KAAK,EAAE,EAAE,CAAC;YACjC,MAAM,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC;YAC1C,MAAM,QAAQ,GAAG,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC;YAE5C,MAAM,UAAU,GAAG,OAAO,CAAC,MAAM,CAAC;YAClC,MAAM,YAAY,GAAG,QAAQ,CAAC,MAAM,CAAC;YACrC,MAAM,QAAQ,GAAG,UAAU,GAAG,YAAY,CAAC;YAE3C,QAAQ,CAAC,IAAI,CAAC;gBACZ,IAAI,EAAE,IAAI;gBACV,UAAU;gBACV,YAAY;gBACZ,QAAQ;aACT,CAAC,CAAC;QACL,CAAC;QAED,oDAAoD;QACpD,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,GAAG,CAAC,CAAC,UAAU,CAAC,CAAC;QAErD,OAAO,QAAQ,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;IAC/B,CAAC;IAED;;OAEG;IACK,KAAK,CAAC,oBAAoB,CAAC,KAAsB;QACvD,MAAM,OAAO,GAAkB,EAAE,CAAC;QAElC,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,KAAK,EAAE,EAAE,CAAC;YACjC,MAAM,QAAQ,GAAG,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YAClC,MAAM,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC;YAC1C,MAAM,QAAQ,GAAG,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,EAAE,CAAC;YAE5C,OAAO,CAAC,IAAI,CAAC;gBACX,IAAI,EAAE,IAAI;gBACV,WAAW,EAAE,CAAC,EAAE,uCAAuC;gBACvD,YAAY,EAAE,QAAQ,CAAC,MAAM;gBAC7B,UAAU,EAAE,OAAO,CAAC,MAAM;aAC3B,CAAC,CAAC;QACL,CAAC;QAED,OAAO,OAAO,CAAC;IACjB,CAAC;IAED;;OAEG;IACK,mBAAmB,CAAC,IAM3B;QACC,MAAM,WAAW,GAAa,EAAE,CAAC;QAEjC,oCAAoC;QACpC,IAAI,IAAI,CAAC,oBAAoB,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACzC,WAAW,CAAC,IAAI,CACd,SAAS,IAAI,CAAC,oBAAoB,CAAC,MAAM,wCAAwC,EACjF,+CAA+C,EAC/C,gCAAgC,EAChC,4DAA4D,CAC7D,CAAC;QACJ,CAAC;QAED,8BAA8B;QAC9B,IAAI,IAAI,CAAC,eAAe,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACpC,WAAW,CAAC,IAAI,CACd,SAAS,IAAI,CAAC,eAAe,CAAC,MAAM,8BAA8B,EAClE,8CAA8C,EAC9C,oDAAoD,EACpD,sDAAsD,CACvD,CAAC;QACJ,CAAC;QAED,4BAA4B;QAC5B,IAAI,IAAI,CAAC,eAAe,CAAC,GAAG,GAAG,EAAE,EAAE,CAAC;YAClC,MAAM,iBAAiB,GAAG,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,QAAQ,GAAG,EAAE,CAAC,CAAC;YACrE,IAAI,iBAAiB,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;gBACjC,WAAW,CAAC,IAAI,CACd,GAAG,iBAAiB,CAAC,MAAM,wDAAwD,EACnF,wDAAwD,EACxD,kDAAkD,EAClD,2DAA2D,CAC5D,CAAC;YACJ,CAAC;QACH,CAAC;QAED,sBAAsB;QACtB,MAAM,aAAa,GAAG,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,GAAG,EAAE,CAAC,CAAC;QACnE,IAAI,aAAa,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YAC7B,WAAW,CAAC,IAAI,CACd,GAAG,aAAa,CAAC,MAAM,8CAA8C,EACrE,GAAG,aAAa,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,OAAO,CAAC,CAAC,IAAI,KAAK,CAAC,CAAC,UAAU,cAAc,CAAC,EACnF,iEAAiE,CAClE,CAAC;QACJ,CAAC;QAED,mCAAmC;QACnC,IAAI,WAAW,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC7B,WAAW,CAAC,IAAI,CACd,sDAAsD,EACtD,6CAA6C,CAC9C,CAAC;QACJ,CAAC;QAED,OAAO,WAAW,CAAC;IACrB,CAAC;IAED;;OAEG;IACK,eAAe,CAAC,QAAgB,EAAE,QAA6B;QACrE,MAAM,cAAc,GAAG,QAAQ,CAAC,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC,WAAW,EAAE,CAAC;QAElE,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,QAAQ,EAAE,CAAC;YACpC,IAAI,cAAc,CAAC,UAAU,CAAC,GAAG,GAAG,GAAG,CAAC,IAAI,cAAc,KAAK,GAAG,EAAE,CAAC;gBACnE,OAAO,KAAK,CAAC;YACf,CAAC;QACH,CAAC;QAED,OAAO,SAAS,CAAC;IACnB,CAAC;CACF"}