Use span_label instead of note

This puts the error message closer to the link, making it easier to see
what went wrong.
This commit is contained in:
Joshua Nelson 2020-09-11 13:42:56 -04:00
parent c213c68500
commit 57250eff55
3 changed files with 65 additions and 78 deletions

View file

@ -1516,16 +1516,15 @@ fn resolution_failure(
collector.cx.tcx.item_name(res.def_id()).to_string() collector.cx.tcx.item_name(res.def_id()).to_string()
) )
}; };
let assoc_item_not_allowed = |res: Res, diag: &mut DiagnosticBuilder<'_>| { let assoc_item_not_allowed = |res: Res| {
let def_id = res.def_id(); let def_id = res.def_id();
let name = collector.cx.tcx.item_name(def_id); let name = collector.cx.tcx.item_name(def_id);
let note = format!( format!(
"`{}` is {} {}, not a module or type, and cannot have associated items", "`{}` is {} {}, not a module or type, and cannot have associated items",
name, name,
res.article(), res.article(),
res.descr() res.descr()
); )
diag.note(&note);
}; };
// ignore duplicates // ignore duplicates
let mut variants_seen = SmallVec::<[_; 3]>::new(); let mut variants_seen = SmallVec::<[_; 3]>::new();
@ -1559,12 +1558,18 @@ fn resolution_failure(
continue; continue;
} }
variants_seen.push(variant); variants_seen.push(variant);
match failure { let note = match failure {
ResolutionFailure::NotInScope { name, .. } => { ResolutionFailure::NotInScope { name, .. } => {
if in_scope { if in_scope {
continue; continue;
} }
diag.note(&format!("no item named `{}` is in scope", name)); // NOTE: uses an explicit `continue` so the `note:` will come before the `help:`
let note = format!("no item named `{}` is in scope", name);
if let Some(span) = sp {
diag.span_label(span, &note);
} else {
diag.note(&note);
}
// If the link has `::` in the path, assume it's meant to be an intra-doc link // If the link has `::` in the path, assume it's meant to be an intra-doc link
if !path_str.contains("::") { if !path_str.contains("::") {
// Otherwise, the `[]` might be unrelated. // Otherwise, the `[]` might be unrelated.
@ -1572,16 +1577,10 @@ fn resolution_failure(
// don't show this for autolinks (`<>`), `()` style links, or reference links // don't show this for autolinks (`<>`), `()` style links, or reference links
diag.help(r#"to escape `[` and `]` characters, add '\' before them like `\[` or `\]`"#); diag.help(r#"to escape `[` and `]` characters, add '\' before them like `\[` or `\]`"#);
} }
continue;
} }
ResolutionFailure::Dummy => continue, ResolutionFailure::Dummy => continue,
ResolutionFailure::WrongNamespace(res, expected_ns) => { ResolutionFailure::WrongNamespace(res, expected_ns) => {
let note = format!(
"this link resolves to {}, which is not in the {} namespace",
item(res),
expected_ns.descr()
);
diag.note(&note);
if let Res::Def(kind, _) = res { if let Res::Def(kind, _) = res {
let disambiguator = Disambiguator::Kind(kind); let disambiguator = Disambiguator::Kind(kind);
suggest_disambiguator( suggest_disambiguator(
@ -1593,24 +1592,26 @@ fn resolution_failure(
&link_range, &link_range,
) )
} }
format!(
"this link resolves to {}, which is not in the {} namespace",
item(res),
expected_ns.descr()
)
} }
ResolutionFailure::NoParentItem => { ResolutionFailure::NoParentItem => {
diag.level = rustc_errors::Level::Bug; diag.level = rustc_errors::Level::Bug;
diag.note("all intra doc links should have a parent item"); "all intra doc links should have a parent item".to_owned()
} }
ResolutionFailure::NoPrimitiveImpl(res, _) => { ResolutionFailure::NoPrimitiveImpl(res, _) => format!(
let note = format!(
"this link partially resolves to {}, which does not have any associated items", "this link partially resolves to {}, which does not have any associated items",
item(res), item(res),
); ),
diag.note(&note);
}
ResolutionFailure::NoPrimitiveAssocItem { prim_name, assoc_item, .. } => { ResolutionFailure::NoPrimitiveAssocItem { prim_name, assoc_item, .. } => {
let note = format!( format!(
"the builtin type `{}` does not have an associated item named `{}`", "the builtin type `{}` does not have an associated item named `{}`",
prim_name, assoc_item prim_name, assoc_item
); )
diag.note(&note);
} }
ResolutionFailure::NoAssocItem(res, assoc_item) => { ResolutionFailure::NoAssocItem(res, assoc_item) => {
use DefKind::*; use DefKind::*;
@ -1645,34 +1646,43 @@ fn resolution_failure(
| Use | Use
| LifetimeParam | LifetimeParam
| Ctor(_, _) | Ctor(_, _)
| AnonConst => return assoc_item_not_allowed(res, diag), | AnonConst => {
let note = assoc_item_not_allowed(res);
if let Some(span) = sp {
diag.span_label(span, &note);
} else {
diag.note(&note);
}
return;
}
Trait | TyAlias | ForeignTy | OpaqueTy | TraitAlias | TyParam Trait | TyAlias | ForeignTy | OpaqueTy | TraitAlias | TyParam
| Static => "associated item", | Static => "associated item",
Impl | GlobalAsm => unreachable!("not a path"), Impl | GlobalAsm => unreachable!("not a path"),
} }
}; };
let note = format!( format!(
"the {} `{}` has no {} named `{}`", "the {} `{}` has no {} named `{}`",
res.descr(), res.descr(),
name, name,
path_description, path_description,
assoc_item assoc_item
); )
diag.note(&note);
} }
ResolutionFailure::CannotHaveAssociatedItems(res, _) => { ResolutionFailure::CannotHaveAssociatedItems(res, _) => {
assoc_item_not_allowed(res, diag) assoc_item_not_allowed(res)
} }
ResolutionFailure::NotAVariant(res, variant) => { ResolutionFailure::NotAVariant(res, variant) => format!(
let note = format!(
"this link partially resolves to {}, but there is no variant named {}", "this link partially resolves to {}, but there is no variant named {}",
item(res), item(res),
variant variant
); ),
};
if let Some(span) = sp {
diag.span_label(span, &note);
} else {
diag.note(&note); diag.note(&note);
} }
} }
}
}, },
); );
} }

View file

@ -2,37 +2,33 @@ warning: unresolved link to `error`
--> $DIR/intra-links-warning-crlf.rs:7:6 --> $DIR/intra-links-warning-crlf.rs:7:6
| |
LL | /// [error] LL | /// [error]
| ^^^^^ | ^^^^^ no item named `error` is in scope
| |
= note: `#[warn(broken_intra_doc_links)]` on by default = note: `#[warn(broken_intra_doc_links)]` on by default
= note: no item named `error` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `error1` warning: unresolved link to `error1`
--> $DIR/intra-links-warning-crlf.rs:12:11 --> $DIR/intra-links-warning-crlf.rs:12:11
| |
LL | /// docs [error1] LL | /// docs [error1]
| ^^^^^^ | ^^^^^^ no item named `error1` is in scope
| |
= note: no item named `error1` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `error2` warning: unresolved link to `error2`
--> $DIR/intra-links-warning-crlf.rs:15:11 --> $DIR/intra-links-warning-crlf.rs:15:11
| |
LL | /// docs [error2] LL | /// docs [error2]
| ^^^^^^ | ^^^^^^ no item named `error2` is in scope
| |
= note: no item named `error2` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `error` warning: unresolved link to `error`
--> $DIR/intra-links-warning-crlf.rs:23:20 --> $DIR/intra-links-warning-crlf.rs:23:20
| |
LL | * It also has an [error]. LL | * It also has an [error].
| ^^^^^ | ^^^^^ no item named `error` is in scope
| |
= note: no item named `error` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: 4 warnings emitted warning: 4 warnings emitted

View file

@ -2,76 +2,62 @@ warning: unresolved link to `Foo::baz`
--> $DIR/intra-links-warning.rs:3:23 --> $DIR/intra-links-warning.rs:3:23
| |
LL | //! Test with [Foo::baz], [Bar::foo], ... LL | //! Test with [Foo::baz], [Bar::foo], ...
| ^^^^^^^^ | ^^^^^^^^ the struct `Foo` has no field or associated item named `baz`
| |
= note: `#[warn(broken_intra_doc_links)]` on by default = note: `#[warn(broken_intra_doc_links)]` on by default
= note: the struct `Foo` has no field or associated item named `baz`
warning: unresolved link to `Bar::foo` warning: unresolved link to `Bar::foo`
--> $DIR/intra-links-warning.rs:3:35 --> $DIR/intra-links-warning.rs:3:35
| |
LL | //! Test with [Foo::baz], [Bar::foo], ... LL | //! Test with [Foo::baz], [Bar::foo], ...
| ^^^^^^^^ | ^^^^^^^^ no item named `Bar` is in scope
|
= note: no item named `Bar` is in scope
warning: unresolved link to `Uniooon::X` warning: unresolved link to `Uniooon::X`
--> $DIR/intra-links-warning.rs:6:13 --> $DIR/intra-links-warning.rs:6:13
| |
LL | //! , [Uniooon::X] and [Qux::Z]. LL | //! , [Uniooon::X] and [Qux::Z].
| ^^^^^^^^^^ | ^^^^^^^^^^ no item named `Uniooon` is in scope
|
= note: no item named `Uniooon` is in scope
warning: unresolved link to `Qux::Z` warning: unresolved link to `Qux::Z`
--> $DIR/intra-links-warning.rs:6:30 --> $DIR/intra-links-warning.rs:6:30
| |
LL | //! , [Uniooon::X] and [Qux::Z]. LL | //! , [Uniooon::X] and [Qux::Z].
| ^^^^^^ | ^^^^^^ no item named `Qux` is in scope
|
= note: no item named `Qux` is in scope
warning: unresolved link to `Uniooon::X` warning: unresolved link to `Uniooon::X`
--> $DIR/intra-links-warning.rs:10:14 --> $DIR/intra-links-warning.rs:10:14
| |
LL | //! , [Uniooon::X] and [Qux::Z]. LL | //! , [Uniooon::X] and [Qux::Z].
| ^^^^^^^^^^ | ^^^^^^^^^^ no item named `Uniooon` is in scope
|
= note: no item named `Uniooon` is in scope
warning: unresolved link to `Qux::Z` warning: unresolved link to `Qux::Z`
--> $DIR/intra-links-warning.rs:10:31 --> $DIR/intra-links-warning.rs:10:31
| |
LL | //! , [Uniooon::X] and [Qux::Z]. LL | //! , [Uniooon::X] and [Qux::Z].
| ^^^^^^ | ^^^^^^ no item named `Qux` is in scope
|
= note: no item named `Qux` is in scope
warning: unresolved link to `Qux:Y` warning: unresolved link to `Qux:Y`
--> $DIR/intra-links-warning.rs:14:13 --> $DIR/intra-links-warning.rs:14:13
| |
LL | /// [Qux:Y] LL | /// [Qux:Y]
| ^^^^^ | ^^^^^ no item named `Qux:Y` is in scope
| |
= note: no item named `Qux:Y` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `error` warning: unresolved link to `error`
--> $DIR/intra-links-warning.rs:58:30 --> $DIR/intra-links-warning.rs:58:30
| |
LL | * time to introduce a link [error]*/ LL | * time to introduce a link [error]*/
| ^^^^^ | ^^^^^ no item named `error` is in scope
| |
= note: no item named `error` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `error` warning: unresolved link to `error`
--> $DIR/intra-links-warning.rs:64:30 --> $DIR/intra-links-warning.rs:64:30
| |
LL | * time to introduce a link [error] LL | * time to introduce a link [error]
| ^^^^^ | ^^^^^ no item named `error` is in scope
| |
= note: no item named `error` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `error` warning: unresolved link to `error`
@ -119,45 +105,40 @@ warning: unresolved link to `error1`
--> $DIR/intra-links-warning.rs:80:11 --> $DIR/intra-links-warning.rs:80:11
| |
LL | /// docs [error1] LL | /// docs [error1]
| ^^^^^^ | ^^^^^^ no item named `error1` is in scope
| |
= note: no item named `error1` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `error2` warning: unresolved link to `error2`
--> $DIR/intra-links-warning.rs:82:11 --> $DIR/intra-links-warning.rs:82:11
| |
LL | /// docs [error2] LL | /// docs [error2]
| ^^^^^^ | ^^^^^^ no item named `error2` is in scope
| |
= note: no item named `error2` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `BarA` warning: unresolved link to `BarA`
--> $DIR/intra-links-warning.rs:21:10 --> $DIR/intra-links-warning.rs:21:10
| |
LL | /// bar [BarA] bar LL | /// bar [BarA] bar
| ^^^^ | ^^^^ no item named `BarA` is in scope
| |
= note: no item named `BarA` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `BarB` warning: unresolved link to `BarB`
--> $DIR/intra-links-warning.rs:27:9 --> $DIR/intra-links-warning.rs:27:9
| |
LL | * bar [BarB] bar LL | * bar [BarB] bar
| ^^^^ | ^^^^ no item named `BarB` is in scope
| |
= note: no item named `BarB` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `BarC` warning: unresolved link to `BarC`
--> $DIR/intra-links-warning.rs:34:6 --> $DIR/intra-links-warning.rs:34:6
| |
LL | bar [BarC] bar LL | bar [BarC] bar
| ^^^^ | ^^^^ no item named `BarC` is in scope
| |
= note: no item named `BarC` is in scope
= help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]` = help: to escape `[` and `]` characters, add '\' before them like `\[` or `\]`
warning: unresolved link to `BarD` warning: unresolved link to `BarD`