code-graph-llm 1.4.1 → 1.5.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.
package/index.js CHANGED
@@ -11,22 +11,25 @@ const __dirname = path.dirname(__filename);
11
11
 
12
12
  const IGNORE_FILE = '.gitignore';
13
13
  const DEFAULT_MAP_FILE = 'llm-code-graph.md';
14
-
15
14
  const SYMBOL_REGEXES = [
16
15
  // Types, Classes, Interfaces (Universal) with Inheritance support
17
- // Captures: class Name extends Parent, interface Name implements Base
18
- /\b(?:class|interface|type|struct|enum|protocol|extension|trait|module|namespace|object)\s+([a-zA-Z_]\w*)(?:\s+(?:extends|implements|:)\s+([a-zA-Z_]\w*(?:\s*,\s*[a-zA-Z_]\w*)*))?/g,
19
-
16
+ /\b(?:class|interface|type|struct|enum|protocol|extension|trait|module|namespace|object)\s+([a-zA-Z_]\w*)(?:[^\n\S]*(?:extends|implements|:|(?:\())[^\n\S]*([a-zA-Z_]\w*(?:[^\n\S]*,\s*[a-zA-Z_]\w*)*)\)?)?/g,
17
+
20
18
  // Explicit Function Keywords
21
19
  /\b(?:function|def|fn|func|fun|method|procedure|sub|routine)\s+([a-zA-Z_]\w*)/g,
22
-
23
- // Method/Var Declarations (C-style, Java, C#, TS, Dart)
24
- /\b(?:void|async|public|private|protected|static|virtual|override|readonly|int|float|double|char|bool|string|val|var|let|final)\s+([a-zA-Z_]\w*)(?=\s*(?:\([^)]*\)|[a-zA-Z_]\w*)\s*(?:\{|=>|;|=))/g,
25
-
20
+
21
+ // Method/Var Declarations (Java, Spring Boot, C-style)
22
+ // Captures: public String askAi(String question), void realFunction()
23
+ /\b(?:void|async|public|private|protected|static|final|native|synchronized|abstract|transient|volatile)\s+(?:[\w<>[\]]+\s+)?([a-zA-Z_]\w*)(?=\s*\([^)]*\)\s*(?:\{|=>|;|=))/g,
24
+
25
+ // Spring/Java/Dart Annotations (Captures the annotation name as a prefix)
26
+ /(@[a-zA-Z_]\w*(?:\([^)]*\))?)\s*(?:(?:public|private|protected|static|final|abstract|class|interface|enum|void|[\w<>[\]]+)\s+)+([a-zA-Z_]\w*)/g,
27
+
26
28
  // Exported symbols
27
29
  /\bexport\s+(?:default\s+)?(?:const|let|var|function|class|type|interface|enum|async|val)\s+([a-zA-Z_]\w*)/g
28
30
  ];
29
31
 
32
+
30
33
  const EDGE_REGEXES = [
31
34
  // Imports/Includes (JS, TS, Python, Go, Rust, C++, Java, Dart)
32
35
  /\b(?:import|from|include|require|using)\s*(?:[\(\s])\s*['"]?([@\w\.\/\-]+)['"]?/g,
@@ -59,19 +62,30 @@ export function extractSymbolsAndInheritance(content) {
59
62
  const symbols = [];
60
63
  const inheritance = [];
61
64
 
62
- // Create a version of content without comments to find symbols accurately
63
- const noComments = content.replace(/\/\*[\s\S]*?\*\/|\/\/.*/g, '');
65
+ // Create a version of content without comments AND strings to find symbols accurately
66
+ const cleanContent = content
67
+ .replace(/\/\*[\s\S]*?\*\/|\/\/.*/g, '')
68
+ .replace(/['"`](?:\\.|[^'"`])*['"`]/g, '');
64
69
 
65
70
  for (const regex of SYMBOL_REGEXES) {
66
71
  let match;
67
72
  regex.lastIndex = 0;
68
- while ((match = regex.exec(noComments)) !== null) {
73
+ while ((match = regex.exec(cleanContent)) !== null) {
69
74
  if (match[1]) {
70
- const symbolName = match[1];
71
- if (['if', 'for', 'while', 'switch', 'return', 'await', 'yield', 'const', 'new', 'let', 'var'].includes(symbolName)) continue;
75
+ // Handle the Annotation regex separately (it has 2 groups)
76
+ let symbolName = match[1];
77
+ let annotation = '';
78
+
79
+ if (symbolName.startsWith('@')) {
80
+ annotation = symbolName;
81
+ symbolName = match[2] || '';
82
+ if (!symbolName) continue;
83
+ }
84
+
85
+ if (['if', 'for', 'while', 'switch', 'return', 'await', 'yield', 'const', 'new', 'let', 'var', 'class', 'void', 'public', 'private', 'protected'].includes(symbolName)) continue;
72
86
 
73
- // Capture inheritance if present (match[2])
74
- if (match[2]) {
87
+ // Capture inheritance if present (match[2] only for non-annotation regex)
88
+ if (!annotation && match[2]) {
75
89
  const parents = match[2].split(',').map(p => p.trim());
76
90
  parents.forEach(parent => {
77
91
  inheritance.push({ child: symbolName, parent });
@@ -94,6 +108,7 @@ export function extractSymbolsAndInheritance(content) {
94
108
  if (clean) comment = clean + (comment ? ' ' + comment : '');
95
109
  if (comment.length > 100) break;
96
110
  } else if (line === '' && comment === '') continue;
111
+ else if (line.startsWith('@')) continue; // Skip annotations in comment search
97
112
  else break;
98
113
  }
99
114
 
@@ -106,7 +121,8 @@ export function extractSymbolsAndInheritance(content) {
106
121
  }
107
122
  }
108
123
 
109
- symbols.push(context ? `${symbolName} [${context}]` : symbolName);
124
+ const displaySymbol = annotation ? `${annotation} ${symbolName}` : symbolName;
125
+ symbols.push(context ? `${displaySymbol} [${context}]` : displaySymbol);
110
126
  }
111
127
  }
112
128
  }
@@ -125,7 +141,8 @@ export function extractEdges(content) {
125
141
  while ((match = regex.exec(noComments)) !== null) {
126
142
  if (match[1]) {
127
143
  const dep = match[1];
128
- if (dep.length > 1 && !['style', 'react', 'vue', 'flutter'].includes(dep.toLowerCase())) {
144
+ // Filter out obvious noise, common library names, or keywords
145
+ if (dep.length > 1 && !['style', 'react', 'vue', 'flutter', 'new', 'const', 'let', 'var', 'dependencies', 'from', 'import'].includes(dep.toLowerCase())) {
129
146
  dependencies.add(dep);
130
147
  }
131
148
  }
package/llm-code-graph.md CHANGED
@@ -1,20 +1,14 @@
1
1
  # CODE_GRAPH_MAP
2
2
  > LLM_ONLY: DO NOT EDIT. COMPACT PROJECT MAP.
3
3
 
4
- - index.js | desc: Contains 7 symbols.
5
- - syms: [SUPPORTED_EXTENSIONS [= [], extractSymbolsAndInheritance [(content)], generate [(cwd = process.cwd()], getIgnores [(cwd, additionalLines = [])], installHook [(cwd = process.cwd()], walk [(dir, ig)], watch [(cwd = process.cwd()]]
6
- - test/index.test.js | desc: Contains 8 symbols.
7
- - syms: [AdminUser [extends BaseUser], IRepository [implements IBase], MyWidget [: StatelessWidget], ignored [by subdir/.gitignore], included [.js'), 'function included()], noDocFunc [(arg1: string, arg2: number)], realFunction [()], testFunc [This is a test function]]
4
+ - index.js | desc: Contains 5 symbols.
5
+ - syms: [SUPPORTED_EXTENSIONS [= [], extractSymbolsAndInheritance [(content)], generate [(cwd = process.cwd()], getIgnores [(cwd, additionalLines = [])], walk [(dir, ig)]]
6
+ - test/index.test.js
8
7
 
9
8
  ## GRAPH EDGES
10
- [AdminUser] -> [inherits] -> [BaseUser]
11
- [IRepository] -> [inherits] -> [IBase]
12
- [MyWidget] -> [inherits] -> [StatelessWidget]
13
9
  [index.js] -> [imports] -> [chokidar]
14
- [index.js] -> [imports] -> [dependencies]
15
10
  [index.js] -> [imports] -> [fs]
16
11
  [index.js] -> [imports] -> [ignore]
17
- [index.js] -> [imports] -> [new]
18
12
  [index.js] -> [imports] -> [path]
19
13
  [index.js] -> [imports] -> [url]
20
14
  [test/index.test.js] -> [imports] -> [../index.js]
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "code-graph-llm",
3
- "version": "1.4.1",
3
+ "version": "1.5.0",
4
4
  "description": "Compact, language-agnostic codebase mapper for LLM token efficiency.",
5
5
  "main": "index.js",
6
6
  "bin": {
@@ -18,7 +18,7 @@
18
18
  "license": "MIT",
19
19
  "repository": {
20
20
  "type": "git",
21
- "url": "https://github.com/youruser/code-graph.git"
21
+ "url": "https://github.com/jabhijeet/code-graph.git"
22
22
  },
23
23
  "dependencies": {
24
24
  "chokidar": "^3.6.0",
@@ -67,6 +67,20 @@ test('extractEdges - Imports and includes', () => {
67
67
  assert.ok(edges.includes('header.h'));
68
68
  });
69
69
 
70
+ test('extractSymbols - Java/Spring Annotations', () => {
71
+ const code = `
72
+ @RestController
73
+ public class MyController {
74
+ @GetMapping("/test")
75
+ public String hello() { return "hi"; }
76
+ }
77
+ `;
78
+ const { symbols } = extractSymbolsAndInheritance(code);
79
+ assert.ok(symbols.some(s => s.includes('@RestController MyController')));
80
+ // Note: Strings are stripped during extraction to avoid false positives
81
+ assert.ok(symbols.some(s => s.includes('@GetMapping() hello')));
82
+ });
83
+
70
84
  test('getIgnores - Default Patterns', () => {
71
85
  const ig = getIgnores(process.cwd());
72
86
  assert.strictEqual(ig.ignores('.git/'), true);