Skip to content

Commit f5b164c

Browse files
committed
Fix the root of the problem
1 parent 517f068 commit f5b164c

File tree

3 files changed

+37
-6
lines changed

3 files changed

+37
-6
lines changed

clippy_lints/src/doc.rs

Lines changed: 30 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -454,6 +454,18 @@ fn lint_for_missing_headers(
454454
#[expect(clippy::cast_possible_truncation)]
455455
#[must_use]
456456
pub fn strip_doc_comment_decoration(doc: &str, comment_kind: CommentKind, span: Span) -> (String, Vec<(usize, Span)>) {
457+
fn get_line_indentation(line: &Vec<char>) -> u32 {
458+
let mut indent = 0;
459+
for c in line {
460+
if *c == ' ' {
461+
indent += 1;
462+
} else if *c == '\n' {
463+
indent += 4;
464+
}; // Standard "Tab" space
465+
}
466+
indent
467+
}
468+
457469
// one-line comments lose their prefix
458470
if comment_kind == CommentKind::Line {
459471
let mut doc = doc.to_owned();
@@ -465,15 +477,32 @@ pub fn strip_doc_comment_decoration(doc: &str, comment_kind: CommentKind, span:
465477

466478
let mut sizes = vec![];
467479
let mut contains_initial_stars = false;
480+
let mut least_indented = 10; // (Hoping the document has less indentation than 10)
468481
for line in doc.lines() {
469482
let offset = line.as_ptr() as usize - doc.as_ptr() as usize;
470483
debug_assert_eq!(offset as u32 as usize, offset);
484+
if !line.is_empty() {
485+
// Empty lines don't have indentation
486+
let line_indent = get_line_indentation(&line.chars().collect::<Vec<char>>());
487+
if line_indent < least_indented {
488+
least_indented = line_indent;
489+
};
490+
};
471491
contains_initial_stars |= line.trim_start().starts_with('*');
472492
// +1 adds the newline, +3 skips the opening delimiter
473493
sizes.push((line.len() + 1, span.with_lo(span.lo() + BytePos(3 + offset as u32))));
474494
}
475495
if !contains_initial_stars {
476-
return (doc.to_string(), sizes);
496+
let mut new_doc = Vec::new();
497+
for line in doc.lines() {
498+
if line.len() >= least_indented as usize {
499+
new_doc.push(&line[least_indented.saturating_sub(1) as usize..]); // Sometimes users start the comment the same line the doc comment is defined.
500+
// /** Example of this behaviour
501+
// (Some description)
502+
// */
503+
};
504+
}
505+
return (new_doc.join("\n"), sizes);
477506
}
478507
// remove the initial '*'s if any
479508
let mut no_stars = String::with_capacity(doc.len());
@@ -646,9 +675,7 @@ fn check_doc<'a, Events: Iterator<Item = (pulldown_cmark::Event<'a>, Range<usize
646675
headers.safety |= in_heading && trimmed_text == "Implementation safety";
647676
headers.safety |= in_heading && trimmed_text == "Implementation Safety";
648677
headers.errors |= in_heading && trimmed_text == "Errors";
649-
headers.errors |= trimmed_text.contains("# Errors\n"); // For /** Doc comments */
650678
headers.panics |= in_heading && trimmed_text == "Panics";
651-
headers.panics |= trimmed_text.contains("# Panics\n");
652679
if in_code {
653680
if is_rust {
654681
let edition = edition.unwrap_or_else(|| cx.tcx.sess.edition());

tests/ui/doc_errors.rs

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,10 @@ impl Struct1 {
6464
}
6565

6666
/**
67+
Before text
68+
```
69+
Indentation block
70+
```
6771
# Errors
6872
Hi
6973
*/
@@ -73,7 +77,7 @@ impl Struct1 {
7377

7478
/**
7579
This is not sufficiently documented.
76-
*/
80+
*/
7781
pub fn pub_method_missing_block_errors_header() -> Result<(), ()> {
7882
unimplemented!();
7983
}

tests/ui/doc_errors.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -37,13 +37,13 @@ LL | pub async fn async_pub_method_missing_errors_header() -> Result<(), ()>
3737
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
3838

3939
error: docs for function returning `Result` missing `# Errors` section
40-
--> $DIR/doc_errors.rs:77:5
40+
--> $DIR/doc_errors.rs:81:5
4141
|
4242
LL | pub fn pub_method_missing_block_errors_header() -> Result<(), ()> {
4343
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
4444

4545
error: docs for function returning `Result` missing `# Errors` section
46-
--> $DIR/doc_errors.rs:100:5
46+
--> $DIR/doc_errors.rs:104:5
4747
|
4848
LL | fn trait_method_missing_errors_header() -> Result<(), ()>;
4949
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

0 commit comments

Comments
 (0)