Skip to content

Commit

Permalink
Auto merge of rust-lang#9567 - rust-lang:doc-link-with-code, r=Alexendoo
Browse files Browse the repository at this point in the history
avoid doc-link-with-quotes in code blocks

This fixes rust-lang#8961 by moving the lint into the docs code, thus being able to re-use the pulldown-cmark parser and simplifying the code.

---

changelog: none
  • Loading branch information
bors committed Oct 1, 2022
2 parents 8030ee9 + 3757a0e commit 8da2429
Show file tree
Hide file tree
Showing 7 changed files with 67 additions and 82 deletions.
70 changes: 56 additions & 14 deletions clippy_lints/src/doc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -198,6 +198,29 @@ declare_clippy_lint! {
"presence of `fn main() {` in code examples"
}

declare_clippy_lint! {
/// ### What it does
/// Detects the syntax `['foo']` in documentation comments (notice quotes instead of backticks)
/// outside of code blocks
/// ### Why is this bad?
/// It is likely a typo when defining an intra-doc link
///
/// ### Example
/// ```rust
/// /// See also: ['foo']
/// fn bar() {}
/// ```
/// Use instead:
/// ```rust
/// /// See also: [`foo`]
/// fn bar() {}
/// ```
#[clippy::version = "1.63.0"]
pub DOC_LINK_WITH_QUOTES,
pedantic,
"possible typo for an intra-doc link"
}

#[expect(clippy::module_name_repetitions)]
#[derive(Clone)]
pub struct DocMarkdown {
Expand All @@ -214,9 +237,14 @@ impl DocMarkdown {
}
}

impl_lint_pass!(DocMarkdown =>
[DOC_MARKDOWN, MISSING_SAFETY_DOC, MISSING_ERRORS_DOC, MISSING_PANICS_DOC, NEEDLESS_DOCTEST_MAIN]
);
impl_lint_pass!(DocMarkdown => [
DOC_LINK_WITH_QUOTES,
DOC_MARKDOWN,
MISSING_SAFETY_DOC,
MISSING_ERRORS_DOC,
MISSING_PANICS_DOC,
NEEDLESS_DOCTEST_MAIN
]);

impl<'tcx> LateLintPass<'tcx> for DocMarkdown {
fn check_crate(&mut self, cx: &LateContext<'tcx>) {
Expand Down Expand Up @@ -432,7 +460,7 @@ pub fn strip_doc_comment_decoration(doc: &str, comment_kind: CommentKind, span:
(no_stars, sizes)
}

#[derive(Copy, Clone)]
#[derive(Copy, Clone, Default)]
struct DocHeaders {
safety: bool,
errors: bool,
Expand Down Expand Up @@ -476,11 +504,7 @@ fn check_attrs<'a>(cx: &LateContext<'_>, valid_idents: &FxHashSet<String>, attrs
}

if doc.is_empty() {
return DocHeaders {
safety: false,
errors: false,
panics: false,
};
return DocHeaders::default();
}

let mut cb = fake_broken_link_callback;
Expand Down Expand Up @@ -521,11 +545,7 @@ fn check_doc<'a, Events: Iterator<Item = (pulldown_cmark::Event<'a>, Range<usize
use pulldown_cmark::Tag::{CodeBlock, Heading, Item, Link, Paragraph};
use pulldown_cmark::{CodeBlockKind, CowStr};

let mut headers = DocHeaders {
safety: false,
errors: false,
panics: false,
};
let mut headers = DocHeaders::default();
let mut in_code = false;
let mut in_link = None;
let mut in_heading = false;
Expand Down Expand Up @@ -612,6 +632,7 @@ fn check_doc<'a, Events: Iterator<Item = (pulldown_cmark::Event<'a>, Range<usize
check_code(cx, &text, edition, span);
}
} else {
check_link_quotes(cx, in_link.is_some(), trimmed_text, span, &range, begin, text.len());
// Adjust for the beginning of the current `Event`
let span = span.with_lo(span.lo() + BytePos::from_usize(range.start - begin));
text_to_check.push((text, span));
Expand All @@ -622,6 +643,27 @@ fn check_doc<'a, Events: Iterator<Item = (pulldown_cmark::Event<'a>, Range<usize
headers
}

fn check_link_quotes(
cx: &LateContext<'_>,
in_link: bool,
trimmed_text: &str,
span: Span,
range: &Range<usize>,
begin: usize,
text_len: usize,
) {
if in_link && trimmed_text.starts_with('\'') && trimmed_text.ends_with('\'') {
// fix the span to only point at the text within the link
let lo = span.lo() + BytePos::from_usize(range.start - begin);
span_lint(
cx,
DOC_LINK_WITH_QUOTES,
span.with_lo(lo).with_hi(lo + BytePos::from_usize(text_len)),
"possible intra-doc link using quotes instead of backticks",
);
}
}

fn get_current_span(spans: &[(usize, Span)], idx: usize) -> (usize, Span) {
let index = match spans.binary_search_by(|c| c.0.cmp(&idx)) {
Ok(o) => o,
Expand Down
60 changes: 0 additions & 60 deletions clippy_lints/src/doc_link_with_quotes.rs

This file was deleted.

2 changes: 1 addition & 1 deletion clippy_lints/src/lib.register_lints.rs
Original file line number Diff line number Diff line change
Expand Up @@ -118,12 +118,12 @@ store.register_lints(&[
disallowed_names::DISALLOWED_NAMES,
disallowed_script_idents::DISALLOWED_SCRIPT_IDENTS,
disallowed_types::DISALLOWED_TYPES,
doc::DOC_LINK_WITH_QUOTES,
doc::DOC_MARKDOWN,
doc::MISSING_ERRORS_DOC,
doc::MISSING_PANICS_DOC,
doc::MISSING_SAFETY_DOC,
doc::NEEDLESS_DOCTEST_MAIN,
doc_link_with_quotes::DOC_LINK_WITH_QUOTES,
double_parens::DOUBLE_PARENS,
drop_forget_ref::DROP_COPY,
drop_forget_ref::DROP_NON_DROP,
Expand Down
2 changes: 1 addition & 1 deletion clippy_lints/src/lib.register_pedantic.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,10 +20,10 @@ store.register_group(true, "clippy::pedantic", Some("clippy_pedantic"), vec![
LintId::of(dereference::REF_BINDING_TO_REFERENCE),
LintId::of(derive::EXPL_IMPL_CLONE_ON_COPY),
LintId::of(derive::UNSAFE_DERIVE_DESERIALIZE),
LintId::of(doc::DOC_LINK_WITH_QUOTES),
LintId::of(doc::DOC_MARKDOWN),
LintId::of(doc::MISSING_ERRORS_DOC),
LintId::of(doc::MISSING_PANICS_DOC),
LintId::of(doc_link_with_quotes::DOC_LINK_WITH_QUOTES),
LintId::of(empty_enum::EMPTY_ENUM),
LintId::of(enum_variants::MODULE_NAME_REPETITIONS),
LintId::of(eta_reduction::REDUNDANT_CLOSURE_FOR_METHOD_CALLS),
Expand Down
2 changes: 0 additions & 2 deletions clippy_lints/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -204,7 +204,6 @@ mod disallowed_names;
mod disallowed_script_idents;
mod disallowed_types;
mod doc;
mod doc_link_with_quotes;
mod double_parens;
mod drop_forget_ref;
mod duplicate_mod;
Expand Down Expand Up @@ -864,7 +863,6 @@ pub fn register_plugins(store: &mut rustc_lint::LintStore, sess: &Session, conf:
store.register_early_pass(|| Box::new(single_char_lifetime_names::SingleCharLifetimeNames));
store.register_late_pass(move |_| Box::new(manual_bits::ManualBits::new(msrv)));
store.register_late_pass(|_| Box::new(default_union_representation::DefaultUnionRepresentation));
store.register_early_pass(|| Box::new(doc_link_with_quotes::DocLinkWithQuotes));
store.register_late_pass(|_| Box::<only_used_in_recursion::OnlyUsedInRecursion>::default());
let allow_dbg_in_tests = conf.allow_dbg_in_tests;
store.register_late_pass(move |_| Box::new(dbg_macro::DbgMacro::new(allow_dbg_in_tests)));
Expand Down
7 changes: 6 additions & 1 deletion tests/ui/doc_link_with_quotes.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,14 @@ fn main() {
foo()
}

/// Calls ['bar']
/// Calls ['bar'] uselessly
pub fn foo() {
bar()
}

/// # Examples
/// This demonstrates issue \#8961
/// ```
/// let _ = vec!['w', 'a', 't'];
/// ```
pub fn bar() {}
6 changes: 3 additions & 3 deletions tests/ui/doc_link_with_quotes.stderr
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
error: possible intra-doc link using quotes instead of backticks
--> $DIR/doc_link_with_quotes.rs:7:1
--> $DIR/doc_link_with_quotes.rs:7:12
|
LL | /// Calls ['bar']
| ^^^^^^^^^^^^^^^^^
LL | /// Calls ['bar'] uselessly
| ^^^^^
|
= note: `-D clippy::doc-link-with-quotes` implied by `-D warnings`

Expand Down

0 comments on commit 8da2429

Please sign in to comment.