Skip to content

Commit 123d9f6

Browse files
authored
feat: Enhance TypeScript root detection with adaptive search depth and skip directories (#38)
1 parent 90d2c95 commit 123d9f6

1 file changed

Lines changed: 35 additions & 8 deletions

File tree

  • internal/extractors/tsextractor

internal/extractors/tsextractor/ts.go

Lines changed: 35 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -34,28 +34,55 @@ func (e *TSExtractor) Detect(repoPath string) (bool, error) {
3434
}
3535

3636
// findTSRoot returns the directory that is the TypeScript project root, along
37-
// with a boolean indicating whether one was found. It checks repoPath itself
38-
// first, then one level of subdirectories to handle monorepos where the
39-
// TypeScript code lives in a subfolder (e.g. a "client/" directory).
37+
// with a boolean indicating whether one was found. Search depth adapts to
38+
// repo structure: Java/Gradle projects nest UI code deep (src/main/resources/ui)
39+
// so we search up to 8 levels; plain repos need at most 2.
4040
func findTSRoot(repoPath string) (string, bool) {
4141
if hasTSMarkers(repoPath) {
4242
return repoPath, true
4343
}
44+
maxDepth := 2
45+
if isJavaStructured(repoPath) {
46+
maxDepth = 8
47+
}
48+
return searchTSRoot(repoPath, 0, maxDepth)
49+
}
50+
51+
func isJavaStructured(repoPath string) bool {
52+
for _, marker := range []string{"pom.xml", "build.gradle", "build.gradle.kts"} {
53+
if _, err := os.Stat(filepath.Join(repoPath, marker)); err == nil {
54+
return true
55+
}
56+
}
57+
return false
58+
}
59+
60+
var tsSkipDirs = map[string]bool{
61+
"node_modules": true, "dist": true, ".next": true,
62+
"build": true, "out": true, "target": true, "vendor": true,
63+
}
4464

45-
entries, err := os.ReadDir(repoPath)
65+
func searchTSRoot(dir string, depth, maxDepth int) (string, bool) {
66+
if depth >= maxDepth {
67+
return "", false
68+
}
69+
entries, err := os.ReadDir(dir)
4670
if err != nil {
47-
return repoPath, false
71+
return "", false
4872
}
4973
for _, entry := range entries {
50-
if !entry.IsDir() || strings.HasPrefix(entry.Name(), ".") {
74+
if !entry.IsDir() || strings.HasPrefix(entry.Name(), ".") || tsSkipDirs[entry.Name()] {
5175
continue
5276
}
53-
sub := filepath.Join(repoPath, entry.Name())
77+
sub := filepath.Join(dir, entry.Name())
5478
if hasTSMarkers(sub) {
5579
return sub, true
5680
}
81+
if found, ok := searchTSRoot(sub, depth+1, maxDepth); ok {
82+
return found, true
83+
}
5784
}
58-
return repoPath, false
85+
return "", false
5986
}
6087

6188
// hasTSMarkers returns true if the directory looks like a TypeScript project root.

0 commit comments

Comments
 (0)