rulewright 0.1.2

Executable engineering standards for Rust workspaces
Documentation
use crate::{Example, FileCtx, Fix, Violation, infra::parse, violation};

#[rustfmt::skip]
const EXAMPLES: &[Example] = &[
    Example {
        label: "no space after //",
        code: "//comment",
        pass: false,
    },
    Example {
        label: "space after //",
        code: "// comment",
        pass: true,
    },
    Example {
        label: "doc comment",
        code: "/// doc comment",
        pass: true,
    },
    Example {
        label: "inner doc comment",
        code: "//! inner doc",
        pass: true,
    },
    Example {
        label: "hash prefix",
        code: "//# header",
        pass: true,
    },
    Example {
        label: "bare double slash",
        code: "//",
        pass: true,
    },
    Example {
        label: "not a comment",
        code: "let x = 1;",
        pass: true,
    },
];

crate::line_rule!(
    comment_space,
    "Require a space after `//` in comments (`//bad` -> `// good`).",
    "Missing space after // makes comments harder to read and looks like accidentally commented-out code.",
    Low,
    fix_comment_space,
);

fn check_comment_space(ctx: &FileCtx<'_>) -> Vec<Violation> {
    let mut out = Vec::new();

    for (i, line) in ctx.lines.iter().enumerate() {
        let lineno = i + 1;
        let trimmed = line.trim();

        if !parse::is_comment(trimmed) {
            continue;
        }

        let Some(ch) = parse::char_after_slashes(trimmed) else {
            continue;
        };

        if matches!(ch, ' ' | '/' | '!' | '#' | '[') {
            continue;
        }

        out.push(violation(
            ctx.rel,
            lineno,
            "missing space after `//` in comment",
        ));
    }

    out
}

fn fix_comment_space(ctx: &FileCtx<'_>, v: &Violation) -> Option<Fix> {
    let line = ctx.line(v.line)?;

    Some(Fix::replace_line(v.line, line.replacen("//", "// ", 1)))
}

crate::rulewright_test!(check_comment_space, {
    crate::example_tests!(EXAMPLES, check_comment_space);
    crate::fix_tests!(EXAMPLES, line, check_comment_space, fix_comment_space);
});