Skip to main content

react_auditor/rules/quality/
no_commented_code.rs

1use oxc_ast::ast::Program;
2use oxc_semantic::Semantic;
3
4use crate::rules::{Rule, RuleFinding, RuleMeta, Severity};
5
6pub struct NoCommentedCode;
7
8const RULE_META: RuleMeta = RuleMeta {
9    id: "no-commented-code",
10    default_severity: Severity::Warning,
11    category: "quality",
12    description: "Remove dead commented-out code",
13};
14
15const CODE_KEYWORDS: &[&str] = &[
16    "function ",
17    "const ",
18    "let ",
19    "var ",
20    "if ",
21    "else ",
22    "for ",
23    "while ",
24    "return ",
25    "import ",
26    "export ",
27    "class ",
28    "new ",
29    "try ",
30    "catch ",
31    "=>",
32    "console.",
33    "document.",
34    "require(",
35];
36
37impl Rule for NoCommentedCode {
38    fn meta(&self) -> &RuleMeta {
39        &RULE_META
40    }
41
42    fn run(&self, _program: &Program, _semantic: &Semantic, source_text: &str) -> Vec<RuleFinding> {
43        let mut findings = Vec::new();
44        let lines: Vec<&str> = source_text.lines().collect();
45
46        let mut i = 0;
47        while i < lines.len() {
48            let trimmed = lines[i].trim();
49            if let Some(body) = trimmed.strip_prefix("//") {
50                let comment_body = body.trim();
51                if looks_like_code(comment_body) {
52                    findings.push(RuleFinding {
53                        line: i + 1,
54                        column: 1,
55                        message: format!("Commented-out code: {comment_body}"),
56                    });
57                }
58            } else if trimmed.starts_with("/*") {
59                // Collect multi-line comment
60                let mut comment_lines = vec![];
61                let start_line = i;
62                while i < lines.len() {
63                    comment_lines.push(lines[i]);
64                    if lines[i].contains("*/") {
65                        break;
66                    }
67                    i += 1;
68                }
69                let full_comment = comment_lines.join("\n");
70                let body = full_comment.trim_start_matches("/*").trim_end_matches("*/");
71
72                let mut line_count = 0;
73                for comment_line in body.lines() {
74                    let cl = comment_line.trim().trim_start_matches('*').trim();
75                    if looks_like_code(cl) {
76                        line_count += 1;
77                    }
78                }
79
80                if line_count >= 2 && comment_lines.len() >= 3 {
81                    findings.push(RuleFinding {
82                        line: start_line + 1,
83                        column: 1,
84                        message: "Multi-line commented-out code detected".to_string(),
85                    });
86                }
87            }
88            i += 1;
89        }
90
91        findings
92    }
93}
94
95fn looks_like_code(text: &str) -> bool {
96    let t = text.trim();
97    if t.is_empty() || t.len() < 3 {
98        return false;
99    }
100    CODE_KEYWORDS.iter().any(|kw| t.contains(kw))
101}