speccore 6.89.0 → 6.90.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 (39) hide show
  1. package/dist/cli.js +15 -0
  2. package/dist/cli.js.map +1 -1
  3. package/dist/commands/code-index.d.ts +1 -0
  4. package/dist/commands/code-index.d.ts.map +1 -1
  5. package/dist/commands/code-index.js +10 -0
  6. package/dist/commands/code-index.js.map +1 -1
  7. package/dist/commands/knowledge.d.ts +12 -0
  8. package/dist/commands/knowledge.d.ts.map +1 -1
  9. package/dist/commands/knowledge.js +80 -0
  10. package/dist/commands/knowledge.js.map +1 -1
  11. package/dist/core/code-graph/builder.d.ts +6 -0
  12. package/dist/core/code-graph/builder.d.ts.map +1 -0
  13. package/dist/core/code-graph/builder.js +155 -0
  14. package/dist/core/code-graph/builder.js.map +1 -0
  15. package/dist/core/code-graph/index.d.ts +25 -0
  16. package/dist/core/code-graph/index.d.ts.map +1 -0
  17. package/dist/core/code-graph/index.js +125 -0
  18. package/dist/core/code-graph/index.js.map +1 -0
  19. package/dist/core/code-graph/parser.d.ts +10 -0
  20. package/dist/core/code-graph/parser.d.ts.map +1 -0
  21. package/dist/core/code-graph/parser.js +314 -0
  22. package/dist/core/code-graph/parser.js.map +1 -0
  23. package/dist/core/code-graph/query.d.ts +14 -0
  24. package/dist/core/code-graph/query.d.ts.map +1 -0
  25. package/dist/core/code-graph/query.js +112 -0
  26. package/dist/core/code-graph/query.js.map +1 -0
  27. package/dist/core/code-graph/reporter.d.ts +7 -0
  28. package/dist/core/code-graph/reporter.d.ts.map +1 -0
  29. package/dist/core/code-graph/reporter.js +97 -0
  30. package/dist/core/code-graph/reporter.js.map +1 -0
  31. package/dist/core/code-graph/types.d.ts +60 -0
  32. package/dist/core/code-graph/types.d.ts.map +1 -0
  33. package/dist/core/code-graph/types.js +7 -0
  34. package/dist/core/code-graph/types.js.map +1 -0
  35. package/dist/core/code-graph/visualizer.d.ts +9 -0
  36. package/dist/core/code-graph/visualizer.d.ts.map +1 -0
  37. package/dist/core/code-graph/visualizer.js +97 -0
  38. package/dist/core/code-graph/visualizer.js.map +1 -0
  39. package/package.json +1 -1
@@ -0,0 +1,97 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.generateGraphReport = generateGraphReport;
4
+ function generateGraphReport(graph) {
5
+ const m = graph.metadata;
6
+ const lines = [];
7
+ lines.push(`# ${m.projectName} — Code Knowledge Graph Report`);
8
+ lines.push('');
9
+ lines.push(`> Generated at: ${m.generatedAt}`);
10
+ lines.push(`> Scanned: ${m.scannedFiles} files | ${m.totalNodes} nodes | ${m.totalEdges} edges`);
11
+ lines.push(`> Confidence: ${m.extractedEdges} EXTRACTED | ${m.inferredEdges} INFERRED`);
12
+ lines.push('');
13
+ // 1. God Nodes
14
+ lines.push('## 🔥 God Nodes (Most Connected)');
15
+ lines.push('');
16
+ const godNodeDetails = graph.godNodes
17
+ .map(id => graph.nodes.find(n => n.id === id))
18
+ .filter(Boolean);
19
+ for (const n of godNodeDetails.slice(0, 15)) {
20
+ lines.push(`- **${n.name}** (${n.type}) — degree: ${n.degree}, file: \`${n.filePath}\``);
21
+ }
22
+ lines.push('');
23
+ // 2. Communities
24
+ lines.push('## 🏘️ Communities (Auto-detected Subsystems)');
25
+ lines.push('');
26
+ for (const comm of graph.communities.slice(0, 10)) {
27
+ lines.push(`### Community ${comm.id}: ${comm.label}`);
28
+ lines.push(`- Nodes: ${comm.nodes.length} | Density: ${(comm.density * 100).toFixed(1)}%`);
29
+ const sampleNodes = comm.nodes
30
+ .map(id => graph.nodes.find(n => n.id === id))
31
+ .filter(Boolean)
32
+ .slice(0, 8);
33
+ lines.push(`- Key members: ${sampleNodes.map(n => n.name).join(', ')}${comm.nodes.length > 8 ? '...' : ''}`);
34
+ lines.push('');
35
+ }
36
+ // 3. Cross-community Bridges
37
+ lines.push('## 🔗 Cross-Community Bridges');
38
+ lines.push('');
39
+ const bridgeEdges = graph.edges.filter(e => {
40
+ const s = graph.nodes.find(n => n.id === e.source);
41
+ const t = graph.nodes.find(n => n.id === e.target);
42
+ return s && t && s.community !== undefined && t.community !== undefined && s.community !== t.community;
43
+ }).slice(0, 15);
44
+ if (bridgeEdges.length === 0) {
45
+ lines.push('No significant cross-community bridges detected.');
46
+ }
47
+ else {
48
+ for (const e of bridgeEdges) {
49
+ const s = graph.nodes.find(n => n.id === e.source);
50
+ const t = graph.nodes.find(n => n.id === e.target);
51
+ lines.push(`- \`${s?.name}\` [${e.type}] → \`${t?.name}\` (${e.confidence})`);
52
+ }
53
+ }
54
+ lines.push('');
55
+ // 4. Suggested Questions
56
+ lines.push('## ❓ Suggested Questions');
57
+ lines.push('');
58
+ const topComm = graph.communities[0];
59
+ if (topComm) {
60
+ lines.push(`- "How does \`${topComm.label}\` subsystem interact with other modules?"`);
61
+ }
62
+ if (graph.godNodes[0]) {
63
+ const topGod = graph.nodes.find(n => n.id === graph.godNodes[0]);
64
+ lines.push(`- "What depends on \`${topGod?.name}\` and why is it a god node?"`);
65
+ }
66
+ const deepestDir = findDeepestDir(graph.nodes);
67
+ if (deepestDir) {
68
+ lines.push(`- "Explain the architecture of \`${deepestDir}\`"`);
69
+ }
70
+ lines.push(`- "Find the shortest path from entry point to database layer"`);
71
+ lines.push('');
72
+ // 5. Query Examples
73
+ lines.push('## 🛠️ Query Examples');
74
+ lines.push('');
75
+ lines.push('```bash');
76
+ lines.push('# Explain a concept');
77
+ lines.push(`speccore knowledge explain "${godNodeDetails[0]?.name || 'main'}"`);
78
+ lines.push('');
79
+ lines.push('# Trace path between two concepts');
80
+ lines.push(`speccore knowledge path "${godNodeDetails[0]?.name || 'A'}" "${godNodeDetails[1]?.name || 'B'}"`);
81
+ lines.push('');
82
+ lines.push('# Natural language query');
83
+ lines.push('speccore knowledge query "How is authentication handled?"');
84
+ lines.push('```');
85
+ lines.push('');
86
+ return lines.join('\n');
87
+ }
88
+ function findDeepestDir(nodes) {
89
+ const dirs = new Set(nodes.map(n => n.filePath.split('/').slice(0, -1).join('/')));
90
+ let deepest = '';
91
+ for (const d of dirs) {
92
+ if (d.split('/').length > deepest.split('/').length)
93
+ deepest = d;
94
+ }
95
+ return deepest || null;
96
+ }
97
+ //# sourceMappingURL=reporter.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reporter.js","sourceRoot":"","sources":["../../../src/core/code-graph/reporter.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,60 @@
1
+ /**
2
+ * Code Knowledge Graph — 类型定义
3
+ * v6.90.0: 本地 AST 解析构建代码知识图谱
4
+ */
5
+ export type NodeType = 'function' | 'class' | 'interface' | 'type' | 'variable' | 'module' | 'method' | 'property' | 'enum';
6
+ export type EdgeType = 'calls' | 'imports' | 'exports' | 'extends' | 'implements' | 'references' | 'contains' | 'typed_by';
7
+ export type Confidence = 'EXTRACTED' | 'INFERRED';
8
+ export interface CodeNode {
9
+ id: string;
10
+ name: string;
11
+ type: NodeType;
12
+ filePath: string;
13
+ line: number;
14
+ column: number;
15
+ community?: number;
16
+ degree?: number;
17
+ /** 代码片段(前200字符) */
18
+ snippet?: string;
19
+ }
20
+ export interface CodeEdge {
21
+ source: string;
22
+ target: string;
23
+ type: EdgeType;
24
+ confidence: Confidence;
25
+ /** 关系发生的文件 */
26
+ filePath?: string;
27
+ /** 行号 */
28
+ line?: number;
29
+ }
30
+ export interface CodeCommunity {
31
+ id: number;
32
+ /** 社区标签(通常是目录名或高频概念) */
33
+ label: string;
34
+ nodes: string[];
35
+ /** 内部边数 / 总边数 */
36
+ density: number;
37
+ }
38
+ export interface CodeGraph {
39
+ nodes: CodeNode[];
40
+ edges: CodeEdge[];
41
+ communities: CodeCommunity[];
42
+ /** 高度数节点(连接数前10%) */
43
+ godNodes: string[];
44
+ metadata: {
45
+ projectName: string;
46
+ projectRoot: string;
47
+ scannedFiles: number;
48
+ totalNodes: number;
49
+ totalEdges: number;
50
+ extractedEdges: number;
51
+ inferredEdges: number;
52
+ generatedAt: string;
53
+ };
54
+ }
55
+ export interface GraphQueryResult {
56
+ nodes: CodeNode[];
57
+ edges: CodeEdge[];
58
+ path?: string[];
59
+ }
60
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/core/code-graph/types.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,MAAM,MAAM,QAAQ,GAChB,UAAU,GACV,OAAO,GACP,WAAW,GACX,MAAM,GACN,UAAU,GACV,QAAQ,GACR,QAAQ,GACR,UAAU,GACV,MAAM,CAAC;AAEX,MAAM,MAAM,QAAQ,GAChB,OAAO,GACP,SAAS,GACT,SAAS,GACT,SAAS,GACT,YAAY,GACZ,YAAY,GACZ,UAAU,GACV,UAAU,CAAC;AAEf,MAAM,MAAM,UAAU,GAAG,WAAW,GAAG,UAAU,CAAC;AAElD,MAAM,WAAW,QAAQ;IACvB,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,QAAQ,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,EAAE,MAAM,CAAC;IACf,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,mBAAmB;IACnB,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED,MAAM,WAAW,QAAQ;IACvB,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,IAAI,EAAE,QAAQ,CAAC;IACf,UAAU,EAAE,UAAU,CAAC;IACvB,cAAc;IACd,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,SAAS;IACT,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,aAAa;IAC5B,EAAE,EAAE,MAAM,CAAC;IACX,wBAAwB;IACxB,KAAK,EAAE,MAAM,CAAC;IACd,KAAK,EAAE,MAAM,EAAE,CAAC;IAChB,iBAAiB;IACjB,OAAO,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,SAAS;IACxB,KAAK,EAAE,QAAQ,EAAE,CAAC;IAClB,KAAK,EAAE,QAAQ,EAAE,CAAC;IAClB,WAAW,EAAE,aAAa,EAAE,CAAC;IAC7B,qBAAqB;IACrB,QAAQ,EAAE,MAAM,EAAE,CAAC;IACnB,QAAQ,EAAE;QACR,WAAW,EAAE,MAAM,CAAC;QACpB,WAAW,EAAE,MAAM,CAAC;QACpB,YAAY,EAAE,MAAM,CAAC;QACrB,UAAU,EAAE,MAAM,CAAC;QACnB,UAAU,EAAE,MAAM,CAAC;QACnB,cAAc,EAAE,MAAM,CAAC;QACvB,aAAa,EAAE,MAAM,CAAC;QACtB,WAAW,EAAE,MAAM,CAAC;KACrB,CAAC;CACH;AAED,MAAM,WAAW,gBAAgB;IAC/B,KAAK,EAAE,QAAQ,EAAE,CAAC;IAClB,KAAK,EAAE,QAAQ,EAAE,CAAC;IAClB,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;CACjB"}
@@ -0,0 +1,7 @@
1
+ "use strict";
2
+ /**
3
+ * Code Knowledge Graph — 类型定义
4
+ * v6.90.0: 本地 AST 解析构建代码知识图谱
5
+ */
6
+ Object.defineProperty(exports, "__esModule", { value: true });
7
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../../../src/core/code-graph/types.ts"],"names":[],"mappings":";AAAA;;;GAGG"}
@@ -0,0 +1,9 @@
1
+ /**
2
+ * Code Knowledge Graph — graph.html 可视化生成器
3
+ * v6.90.0
4
+ *
5
+ * 使用 vis-network CDN,与现有 knowledge-visualizer 风格一致
6
+ */
7
+ import type { CodeGraph } from './types';
8
+ export declare function buildCodeGraphHtml(graph: CodeGraph): string;
9
+ //# sourceMappingURL=visualizer.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"visualizer.d.ts","sourceRoot":"","sources":["../../../src/core/code-graph/visualizer.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,SAAS,CAAC;AAEzC,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,SAAS,GAAG,MAAM,CAiG3D"}
@@ -0,0 +1,97 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.buildCodeGraphHtml = buildCodeGraphHtml;
4
+ function buildCodeGraphHtml(graph) {
5
+ const palette = [
6
+ '#0ea5e9', '#14b8a6', '#f97316', '#8b5cf6',
7
+ '#ec4899', '#22c55e', '#eab308', '#6366f1',
8
+ '#06b6d4', '#f43f5e',
9
+ ];
10
+ const nodes = graph.nodes.map(n => ({
11
+ id: n.id,
12
+ label: n.name,
13
+ group: n.community ?? -1,
14
+ title: `<b>${n.name}</b><br>type: ${n.type}<br>file: ${n.filePath}<br>line: ${n.line}<br>degree: ${n.degree}`,
15
+ value: n.degree || 1,
16
+ color: n.community !== undefined ? palette[n.community % palette.length] : '#94a3b8',
17
+ }));
18
+ const edges = graph.edges.map((e, i) => ({
19
+ from: e.source,
20
+ to: e.target,
21
+ label: e.type,
22
+ title: `${e.type} (${e.confidence})`,
23
+ dashes: e.confidence === 'INFERRED',
24
+ color: e.confidence === 'EXTRACTED' ? { color: '#0ea5e9', opacity: 0.6 } : { color: '#94a3b8', opacity: 0.4 },
25
+ arrows: { to: { enabled: true, scaleFactor: 0.5 } },
26
+ }));
27
+ const godNodeSet = new Set(graph.godNodes);
28
+ for (const n of nodes) {
29
+ if (godNodeSet.has(n.id)) {
30
+ n.value = (n.value || 1) * 2;
31
+ n.font = { size: 16, bold: true };
32
+ }
33
+ }
34
+ const meta = graph.metadata;
35
+ return `<!DOCTYPE html>
36
+ <html lang="zh-CN">
37
+ <head>
38
+ <meta charset="UTF-8">
39
+ <meta name="viewport" content="width=device-width,initial-scale=1.0">
40
+ <title>${meta.projectName} — Code Graph</title>
41
+ <script src="https://unpkg.com/vis-network/standalone/umd/vis-network.min.js"></script>
42
+ <style>
43
+ body{margin:0;font-family:'Segoe UI',system-ui,sans-serif;background:#0b1929;color:#bae6fd;overflow:hidden}
44
+ #graph{position:fixed;inset:0}
45
+ .panel{position:fixed;top:12px;left:12px;background:rgba(13,31,56,.95);border:1px solid rgba(14,165,233,.2);border-radius:10px;padding:14px;max-width:280px;z-index:10;font-size:12px}
46
+ .panel h2{margin:0 0 8px;font-size:14px;color:#0ea5e9}
47
+ .panel .stat{display:flex;justify-content:space-between;padding:3px 0;border-bottom:1px solid rgba(255,255,255,.05)}
48
+ .panel .stat span{color:#5b7fa5}
49
+ .panel .legend{margin-top:10px}
50
+ .panel .legend-item{display:flex;align-items:center;gap:6px;margin:4px 0}
51
+ .panel .dot{width:10px;height:10px;border-radius:50%}
52
+ .panel .line{width:20px;height:2px}
53
+ .search{position:fixed;top:12px;right:12px;z-index:10;display:flex;gap:6px}
54
+ .search input{background:rgba(13,31,56,.95);border:1px solid rgba(14,165,233,.2);border-radius:6px;padding:6px 10px;color:#bae6fd;font-size:12px;outline:none;width:180px}
55
+ .search input::placeholder{color:#5b7fa5}
56
+ .search button{background:#0ea5e9;border:none;border-radius:6px;padding:6px 12px;color:#fff;font-size:12px;cursor:pointer}
57
+ </style>
58
+ </head>
59
+ <body>
60
+ <div id="graph"></div>
61
+ <div class="panel">
62
+ <h2>${meta.projectName}</h2>
63
+ <div class="stat">Files <span>${meta.scannedFiles}</span></div>
64
+ <div class="stat">Nodes <span>${meta.totalNodes}</span></div>
65
+ <div class="stat">Edges <span>${meta.totalEdges}</span></div>
66
+ <div class="stat">Communities <span>${graph.communities.length}</span></div>
67
+ <div class="stat">EXTRACTED <span>${meta.extractedEdges}</span></div>
68
+ <div class="stat">INFERRED <span>${meta.inferredEdges}</span></div>
69
+ <div class="legend">
70
+ <div class="legend-item"><span class="dot" style="background:#0ea5e9"></span> EXTRACTED edge</div>
71
+ <div class="legend-item"><span class="line" style="background:#94a3b8;border-top:2px dashed #94a3b8"></span> INFERRED edge</div>
72
+ <div class="legend-item"><span class="dot" style="background:#f97316"></span> God node</div>
73
+ </div>
74
+ </div>
75
+ <div class="search">
76
+ <input type="text" id="searchInput" placeholder="Search node...">
77
+ <button onclick="searchNode()">Find</button>
78
+ </div>
79
+ <script>
80
+ const nodes=new vis.DataSet(${JSON.stringify(nodes)});
81
+ const edges=new vis.DataSet(${JSON.stringify(edges)});
82
+ const container=document.getElementById('graph');
83
+ const data={nodes,edges};
84
+ const options={
85
+ nodes:{shape:'dot',font:{color:'#bae6fd',size:12},borderWidth:1,borderWidthSelected:2},
86
+ edges:{width:1,smooth:{type:'continuous'}},
87
+ physics:{stabilization:false,barnesHut:{gravitationalConstant:-3000,springConstant:0.04,springLength:95}},
88
+ interaction:{hover:true,tooltipDelay:200,hideEdgesOnDrag:true}
89
+ };
90
+ const network=new vis.Network(container,data,options);
91
+ function searchNode(){const v=document.getElementById('searchInput').value.toLowerCase();const found=nodes.get({filter:n=>n.label.toLowerCase().includes(v)})[0];if(found){network.focus(found.id,{scale:1.2,animation:true});network.selectNodes([found.id]);}}
92
+ document.getElementById('searchInput').addEventListener('keydown',e=>{if(e.key==='Enter')searchNode();});
93
+ </script>
94
+ </body>
95
+ </html>`;
96
+ }
97
+ //# sourceMappingURL=visualizer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"visualizer.js","sourceRoot":"","sources":["../../../src/core/code-graph/visualizer.ts"],"names":[],"mappings":";;AAQA,gDAiGC;AAjGD,SAAgB,kBAAkB,CAAC,KAAgB;IACjD,MAAM,OAAO,GAAG;QACd,SAAS,EAAE,SAAS,EAAE,SAAS,EAAE,SAAS;QAC1C,SAAS,EAAE,SAAS,EAAE,SAAS,EAAE,SAAS;QAC1C,SAAS,EAAE,SAAS;KACrB,CAAC;IAEF,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;QAClC,EAAE,EAAE,CAAC,CAAC,EAAE;QACR,KAAK,EAAE,CAAC,CAAC,IAAI;QACb,KAAK,EAAE,CAAC,CAAC,SAAS,IAAI,CAAC,CAAC;QACxB,KAAK,EAAE,MAAM,CAAC,CAAC,IAAI,iBAAiB,CAAC,CAAC,IAAI,aAAa,CAAC,CAAC,QAAQ,aAAa,CAAC,CAAC,IAAI,eAAe,CAAC,CAAC,MAAM,EAAE;QAC7G,KAAK,EAAE,CAAC,CAAC,MAAM,IAAI,CAAC;QACpB,KAAK,EAAE,CAAC,CAAC,SAAS,KAAK,SAAS,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,SAAS,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,SAAS;KACrF,CAAC,CAAC,CAAC;IAEJ,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC;QACvC,IAAI,EAAE,CAAC,CAAC,MAAM;QACd,EAAE,EAAE,CAAC,CAAC,MAAM;QACZ,KAAK,EAAE,CAAC,CAAC,IAAI;QACb,KAAK,EAAE,GAAG,CAAC,CAAC,IAAI,KAAK,CAAC,CAAC,UAAU,GAAG;QACpC,MAAM,EAAE,CAAC,CAAC,UAAU,KAAK,UAAU;QACnC,KAAK,EAAE,CAAC,CAAC,UAAU,KAAK,WAAW,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,SAAS,EAAE,OAAO,EAAE,GAAG,EAAE,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,SAAS,EAAE,OAAO,EAAE,GAAG,EAAE;QAC7G,MAAM,EAAE,EAAE,EAAE,EAAE,EAAE,OAAO,EAAE,IAAI,EAAE,WAAW,EAAE,GAAG,EAAE,EAAE;KACpD,CAAC,CAAC,CAAC;IAEJ,MAAM,UAAU,GAAG,IAAI,GAAG,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC;IAC3C,KAAK,MAAM,CAAC,IAAI,KAAK,EAAE,CAAC;QACtB,IAAI,UAAU,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC;YACzB,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC,KAAK,IAAI,CAAC,CAAC,GAAG,CAAC,CAAC;YAC5B,CAAS,CAAC,IAAI,GAAG,EAAE,IAAI,EAAE,EAAE,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC;QAC7C,CAAC;IACH,CAAC;IAED,MAAM,IAAI,GAAG,KAAK,CAAC,QAAQ,CAAC;IAE5B,OAAO;;;;;SAKA,IAAI,CAAC,WAAW;;;;;;;;;;;;;;;;;;;;;;MAsBnB,IAAI,CAAC,WAAW;gCACU,IAAI,CAAC,YAAY;gCACjB,IAAI,CAAC,UAAU;gCACf,IAAI,CAAC,UAAU;sCACT,KAAK,CAAC,WAAW,CAAC,MAAM;oCAC1B,IAAI,CAAC,cAAc;mCACpB,IAAI,CAAC,aAAa;;;;;;;;;;;;8BAYvB,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC;8BACrB,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC;;;;;;;;;;;;;;QAc3C,CAAC;AACT,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "speccore",
3
- "version": "6.89.0",
3
+ "version": "6.90.0",
4
4
  "description": "SpecCore - Code by Spec, Not by Vibe.",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",