From 99b6e4e954cf0318fc0d7446ef8bd086a4afdf1c Mon Sep 17 00:00:00 2001 From: Aditya kumar singh <143548997+Adityakk9031@users.noreply.github.com> Date: Sat, 15 Aug 2026 17:45:24 +0530 Subject: [PATCH 1/2] fix(codetype): support multiline and side-effect import detection --- src/code_type_detector.rs | 30 ++++++++++++++++++++++++++++-- 1 file changed, 28 insertions(+), 2 deletions(-) diff --git a/src/code_type_detector.rs b/src/code_type_detector.rs index 29b42bf..461aa6e 100644 --- a/src/code_type_detector.rs +++ b/src/code_type_detector.rs @@ -257,11 +257,12 @@ impl CodeTypeDetector { fn extract_imports(&self, content: &str, _language: &str) -> Vec { let mut imports = Vec::new(); - // Extract require() calls + // Extract require() calls and ES import statements (including multiline and side-effect imports) let require_patterns = vec![ regex::Regex::new(r#"require\(\s*['"]([^'"]+)['"]\s*\)"#).unwrap(), - regex::Regex::new(r#"import\s+.*from\s+['"]([^'"]+)['"]"#).unwrap(), + regex::Regex::new(r#"(?s)import\s+.*?from\s+['"]([^'"]+)['"]"#).unwrap(), regex::Regex::new(r#"import\s*\(\s*['"]([^'"]+)['"]\s*\)"#).unwrap(), + regex::Regex::new(r#"import\s+['"]([^'"]+)['"]"#).unwrap(), ]; for pattern in require_patterns { @@ -513,4 +514,29 @@ mod tests { assert_eq!(detector.detect_from_ast(&tree, source), CodeType::Backend); } + + #[test] + fn detect_code_type_handles_multiline_imports() { + let detector = CodeTypeDetector::new(); + let code = r#" + import { + Injectable, + NestMiddleware, + } from '@nestjs/common'; + + @Injectable() + export class AuthMiddleware {} + "#; + assert_eq!(detector.detect_code_type("auth.ts", code, "typescript"), CodeType::Backend); + } + + #[test] + fn detect_code_type_handles_side_effect_imports() { + let detector = CodeTypeDetector::new(); + let code = r#" + import 'express'; + export const app = {}; + "#; + assert_eq!(detector.detect_code_type("server.ts", code, "typescript"), CodeType::Backend); + } } From 1ecc00c3dccc630c8f2f746550beef352ef44858 Mon Sep 17 00:00:00 2001 From: Aditya kumar singh <143548997+Adityakk9031@users.noreply.github.com> Date: Thu, 27 Aug 2026 17:00:42 +0530 Subject: [PATCH 2/2] fix(codetype): constrain import regex and isolate import extraction to js/ts --- src/code_type_detector.rs | 30 +++++++++++++++++++++++++++--- 1 file changed, 27 insertions(+), 3 deletions(-) diff --git a/src/code_type_detector.rs b/src/code_type_detector.rs index 461aa6e..8f1c792 100644 --- a/src/code_type_detector.rs +++ b/src/code_type_detector.rs @@ -254,13 +254,20 @@ impl CodeTypeDetector { } } - fn extract_imports(&self, content: &str, _language: &str) -> Vec { + fn extract_imports(&self, content: &str, language: &str) -> Vec { + let lang = language.to_lowercase(); + if !matches!(lang.as_str(), "javascript" | "typescript" | "tsx" | "jsx" | "js" | "ts") { + return Vec::new(); + } + let mut imports = Vec::new(); - // Extract require() calls and ES import statements (including multiline and side-effect imports) + // Extract require() calls and ES import statements (including multiline and side-effect imports). + // The import ... from pattern is constrained to not match across statement boundaries (semicolons). let require_patterns = vec![ regex::Regex::new(r#"require\(\s*['"]([^'"]+)['"]\s*\)"#).unwrap(), - regex::Regex::new(r#"(?s)import\s+.*?from\s+['"]([^'"]+)['"]"#).unwrap(), + regex::Regex::new(r#"(?s)import\s+(?:\{[^};]*\}|[^;]+?)\s+from\s*['"]([^'"]+)['"]"#) + .unwrap(), regex::Regex::new(r#"import\s*\(\s*['"]([^'"]+)['"]\s*\)"#).unwrap(), regex::Regex::new(r#"import\s+['"]([^'"]+)['"]"#).unwrap(), ]; @@ -539,4 +546,21 @@ mod tests { "#; assert_eq!(detector.detect_code_type("server.ts", code, "typescript"), CodeType::Backend); } + + #[test] + fn import_regex_does_not_capture_across_statement_boundaries() { + let detector = CodeTypeDetector::new(); + // Semicolon ends the import statement; subsequent `from` in unrelated code must not form a match with `import` + let code = "import foo;\nlet x = calculate(from, 'react');\n"; + let imports = detector.extract_imports(code, "javascript"); + assert!(!imports.contains(&"react".to_string())); + } + + #[test] + fn non_js_imports_do_not_override_backend_default() { + let detector = CodeTypeDetector::new(); + // A Go file importing rxgo should not match JS frontend react signature + let code = "package main\n\nimport \"github.com/reactivex/rxgo\"\n"; + assert_eq!(detector.detect_code_type("main.go", code, "go"), CodeType::Backend); + } }