mirror of
https://github.com/rust-lang/rust.git
synced 2025-05-14 02:49:40 +00:00
Rollup merge of #84818 - ABouttefeux:enum-suggest, r=jackh726
suggestion for unit enum variant when matched with a patern resolve #84700 add suggestion for code like ```rust enum FarmAnimal { Worm, Cow, Bull, Chicken { num_eggs: usize }, Dog (String), } fn what_does_the_animal_say(animal: &FarmAnimal) { let noise = match animal { FarmAnimal::Cow(_) => "moo".to_string(), _ => todo!() }; println!("{:?} says: {:?}", animal, noise); } ``` ``` error[E0532]: expected tuple struct or tuple variant, found unit variant `FarmAnimal::Cow` --> $DIR/issue-84700.rs:15:9 | LL | Cow, | --- `FarmAnimal::Cow` defined here ... LL | FarmAnimal::Cow(_) => "moo".to_string(), | ^^^^^^^^^^^^^^^^^^ help: use this syntax instead: `FarmAnimal::Cow` ```
This commit is contained in:
commit
b0c7e64de0
@ -819,6 +819,19 @@ impl<'a: 'ast, 'ast> LateResolutionVisitor<'a, '_, 'ast> {
|
||||
_ => false,
|
||||
};
|
||||
|
||||
let find_span = |source: &PathSource<'_>, err: &mut DiagnosticBuilder<'_>| {
|
||||
match source {
|
||||
PathSource::Expr(Some(Expr { span, kind: ExprKind::Call(_, _), .. }))
|
||||
| PathSource::TupleStruct(span, _) => {
|
||||
// We want the main underline to cover the suggested code as well for
|
||||
// cleaner output.
|
||||
err.set_span(*span);
|
||||
*span
|
||||
}
|
||||
_ => span,
|
||||
}
|
||||
};
|
||||
|
||||
let mut bad_struct_syntax_suggestion = |def_id: DefId| {
|
||||
let (followed_by_brace, closing_brace) = self.followed_by_brace(span);
|
||||
|
||||
@ -862,18 +875,7 @@ impl<'a: 'ast, 'ast> LateResolutionVisitor<'a, '_, 'ast> {
|
||||
}
|
||||
}
|
||||
PathSource::Expr(_) | PathSource::TupleStruct(..) | PathSource::Pat => {
|
||||
let span = match &source {
|
||||
PathSource::Expr(Some(Expr {
|
||||
span, kind: ExprKind::Call(_, _), ..
|
||||
}))
|
||||
| PathSource::TupleStruct(span, _) => {
|
||||
// We want the main underline to cover the suggested code as well for
|
||||
// cleaner output.
|
||||
err.set_span(*span);
|
||||
*span
|
||||
}
|
||||
_ => span,
|
||||
};
|
||||
let span = find_span(&source, err);
|
||||
if let Some(span) = self.def_span(def_id) {
|
||||
err.span_label(span, &format!("`{}` defined here", path_str));
|
||||
}
|
||||
@ -1047,6 +1049,23 @@ impl<'a: 'ast, 'ast> LateResolutionVisitor<'a, '_, 'ast> {
|
||||
) if ns == ValueNS => {
|
||||
bad_struct_syntax_suggestion(def_id);
|
||||
}
|
||||
(Res::Def(DefKind::Ctor(_, CtorKind::Const), def_id), _) if ns == ValueNS => {
|
||||
match source {
|
||||
PathSource::Expr(_) | PathSource::TupleStruct(..) | PathSource::Pat => {
|
||||
let span = find_span(&source, err);
|
||||
if let Some(span) = self.def_span(def_id) {
|
||||
err.span_label(span, &format!("`{}` defined here", path_str));
|
||||
}
|
||||
err.span_suggestion(
|
||||
span,
|
||||
&format!("use this syntax instead"),
|
||||
format!("{path_str}"),
|
||||
Applicability::MaybeIncorrect,
|
||||
);
|
||||
}
|
||||
_ => return false,
|
||||
}
|
||||
}
|
||||
(Res::Def(DefKind::Ctor(_, CtorKind::Fn), def_id), _) if ns == ValueNS => {
|
||||
if let Some(span) = self.def_span(def_id) {
|
||||
err.span_label(span, &format!("`{}` defined here", path_str));
|
||||
|
@ -1,84 +1,154 @@
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit struct `Empty2`
|
||||
--> $DIR/empty-struct-unit-pat.rs:21:9
|
||||
|
|
||||
LL | struct Empty2;
|
||||
| -------------- `Empty2` defined here
|
||||
...
|
||||
LL | Empty2() => ()
|
||||
| ^^^^^^ help: a tuple struct with a similar name exists: `XEmpty6`
|
||||
| ^^^^^^^^
|
||||
|
|
||||
::: $DIR/auxiliary/empty-struct.rs:3:1
|
||||
|
|
||||
LL | pub struct XEmpty6();
|
||||
| --------------------- similarly named tuple struct `XEmpty6` defined here
|
||||
|
|
||||
help: use this syntax instead
|
||||
|
|
||||
LL | Empty2 => ()
|
||||
| ^^^^^^
|
||||
help: a tuple struct with a similar name exists
|
||||
|
|
||||
LL | XEmpty6() => ()
|
||||
| ^^^^^^^
|
||||
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit struct `XEmpty2`
|
||||
--> $DIR/empty-struct-unit-pat.rs:24:9
|
||||
|
|
||||
LL | XEmpty2() => ()
|
||||
| ^^^^^^^ help: a tuple struct with a similar name exists: `XEmpty6`
|
||||
| ^^^^^^^^^
|
||||
|
|
||||
::: $DIR/auxiliary/empty-struct.rs:3:1
|
||||
::: $DIR/auxiliary/empty-struct.rs:2:1
|
||||
|
|
||||
LL | pub struct XEmpty2;
|
||||
| ------------------- `XEmpty2` defined here
|
||||
LL | pub struct XEmpty6();
|
||||
| --------------------- similarly named tuple struct `XEmpty6` defined here
|
||||
|
|
||||
help: use this syntax instead
|
||||
|
|
||||
LL | XEmpty2 => ()
|
||||
| ^^^^^^^
|
||||
help: a tuple struct with a similar name exists
|
||||
|
|
||||
LL | XEmpty6() => ()
|
||||
| ^^^^^^^
|
||||
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit struct `Empty2`
|
||||
--> $DIR/empty-struct-unit-pat.rs:28:9
|
||||
|
|
||||
LL | struct Empty2;
|
||||
| -------------- `Empty2` defined here
|
||||
...
|
||||
LL | Empty2(..) => ()
|
||||
| ^^^^^^ help: a tuple struct with a similar name exists: `XEmpty6`
|
||||
| ^^^^^^^^^^
|
||||
|
|
||||
::: $DIR/auxiliary/empty-struct.rs:3:1
|
||||
|
|
||||
LL | pub struct XEmpty6();
|
||||
| --------------------- similarly named tuple struct `XEmpty6` defined here
|
||||
|
|
||||
help: use this syntax instead
|
||||
|
|
||||
LL | Empty2 => ()
|
||||
| ^^^^^^
|
||||
help: a tuple struct with a similar name exists
|
||||
|
|
||||
LL | XEmpty6(..) => ()
|
||||
| ^^^^^^^
|
||||
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit struct `XEmpty2`
|
||||
--> $DIR/empty-struct-unit-pat.rs:32:9
|
||||
|
|
||||
LL | XEmpty2(..) => ()
|
||||
| ^^^^^^^ help: a tuple struct with a similar name exists: `XEmpty6`
|
||||
| ^^^^^^^^^^^
|
||||
|
|
||||
::: $DIR/auxiliary/empty-struct.rs:3:1
|
||||
::: $DIR/auxiliary/empty-struct.rs:2:1
|
||||
|
|
||||
LL | pub struct XEmpty2;
|
||||
| ------------------- `XEmpty2` defined here
|
||||
LL | pub struct XEmpty6();
|
||||
| --------------------- similarly named tuple struct `XEmpty6` defined here
|
||||
|
|
||||
help: use this syntax instead
|
||||
|
|
||||
LL | XEmpty2 => ()
|
||||
| ^^^^^^^
|
||||
help: a tuple struct with a similar name exists
|
||||
|
|
||||
LL | XEmpty6(..) => ()
|
||||
| ^^^^^^^
|
||||
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit variant `E::Empty4`
|
||||
--> $DIR/empty-struct-unit-pat.rs:37:9
|
||||
|
|
||||
LL | Empty4
|
||||
| ------ `E::Empty4` defined here
|
||||
...
|
||||
LL | E::Empty4() => ()
|
||||
| ^^^^^^^^^ not a tuple struct or tuple variant
|
||||
| ^^^^^^^^^^^ help: use this syntax instead: `E::Empty4`
|
||||
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit variant `XE::XEmpty4`
|
||||
--> $DIR/empty-struct-unit-pat.rs:41:9
|
||||
|
|
||||
LL | XE::XEmpty4() => (),
|
||||
| ^^^^-------
|
||||
| |
|
||||
| help: a tuple variant with a similar name exists: `XEmpty5`
|
||||
| ^^^^^^^^^^^^^
|
||||
|
|
||||
::: $DIR/auxiliary/empty-struct.rs:8:5
|
||||
::: $DIR/auxiliary/empty-struct.rs:7:5
|
||||
|
|
||||
LL | XEmpty4,
|
||||
| ------- `XE::XEmpty4` defined here
|
||||
LL | XEmpty5(),
|
||||
| --------- similarly named tuple variant `XEmpty5` defined here
|
||||
|
|
||||
help: use this syntax instead
|
||||
|
|
||||
LL | XE::XEmpty4 => (),
|
||||
| ^^^^^^^^^^^
|
||||
help: a tuple variant with a similar name exists
|
||||
|
|
||||
LL | XE::XEmpty5() => (),
|
||||
| ^^^^^^^
|
||||
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit variant `E::Empty4`
|
||||
--> $DIR/empty-struct-unit-pat.rs:46:9
|
||||
|
|
||||
LL | Empty4
|
||||
| ------ `E::Empty4` defined here
|
||||
...
|
||||
LL | E::Empty4(..) => ()
|
||||
| ^^^^^^^^^ not a tuple struct or tuple variant
|
||||
| ^^^^^^^^^^^^^ help: use this syntax instead: `E::Empty4`
|
||||
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit variant `XE::XEmpty4`
|
||||
--> $DIR/empty-struct-unit-pat.rs:50:9
|
||||
|
|
||||
LL | XE::XEmpty4(..) => (),
|
||||
| ^^^^-------
|
||||
| |
|
||||
| help: a tuple variant with a similar name exists: `XEmpty5`
|
||||
| ^^^^^^^^^^^^^^^
|
||||
|
|
||||
::: $DIR/auxiliary/empty-struct.rs:8:5
|
||||
::: $DIR/auxiliary/empty-struct.rs:7:5
|
||||
|
|
||||
LL | XEmpty4,
|
||||
| ------- `XE::XEmpty4` defined here
|
||||
LL | XEmpty5(),
|
||||
| --------- similarly named tuple variant `XEmpty5` defined here
|
||||
|
|
||||
help: use this syntax instead
|
||||
|
|
||||
LL | XE::XEmpty4 => (),
|
||||
| ^^^^^^^^^^^
|
||||
help: a tuple variant with a similar name exists
|
||||
|
|
||||
LL | XE::XEmpty5(..) => (),
|
||||
| ^^^^^^^
|
||||
|
||||
error: aborting due to 8 previous errors
|
||||
|
||||
|
@ -21,8 +21,11 @@ LL | Foo::Baz => {}
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit struct `S`
|
||||
--> $DIR/issue-32004.rs:16:9
|
||||
|
|
||||
LL | struct S;
|
||||
| --------- `S` defined here
|
||||
...
|
||||
LL | S(()) => {}
|
||||
| ^ not a tuple struct or tuple variant
|
||||
| ^^^^^ help: use this syntax instead: `S`
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
|
||||
|
@ -1,14 +1,20 @@
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit variant `E::A`
|
||||
--> $DIR/issue-pr29383.rs:9:14
|
||||
|
|
||||
LL | A,
|
||||
| - `E::A` defined here
|
||||
...
|
||||
LL | Some(E::A(..)) => {}
|
||||
| ^^^^ not a tuple struct or tuple variant
|
||||
| ^^^^^^^^ help: use this syntax instead: `E::A`
|
||||
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit variant `E::B`
|
||||
--> $DIR/issue-pr29383.rs:11:14
|
||||
|
|
||||
LL | B,
|
||||
| - `E::B` defined here
|
||||
...
|
||||
LL | Some(E::B(..)) => {}
|
||||
| ^^^^ not a tuple struct or tuple variant
|
||||
| ^^^^^^^^ help: use this syntax instead: `E::B`
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
|
||||
|
@ -1,8 +1,11 @@
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit variant `Color::NoColor`
|
||||
--> $DIR/match-pattern-field-mismatch-2.rs:12:11
|
||||
|
|
||||
LL | NoColor,
|
||||
| ------- `Color::NoColor` defined here
|
||||
...
|
||||
LL | Color::NoColor(_) => { }
|
||||
| ^^^^^^^^^^^^^^ not a tuple struct or tuple variant
|
||||
| ^^^^^^^^^^^^^^^^^ help: use this syntax instead: `Color::NoColor`
|
||||
|
||||
error: aborting due to previous error
|
||||
|
||||
|
@ -9,11 +9,21 @@ error[E0532]: expected tuple struct or tuple variant, found unit variant `A::D`
|
||||
|
|
||||
LL | B(isize, isize),
|
||||
| --------------- similarly named tuple variant `B` defined here
|
||||
LL | C(isize, isize, isize),
|
||||
LL | D
|
||||
| - `A::D` defined here
|
||||
...
|
||||
LL | A::D(_) => (),
|
||||
| ^^^-
|
||||
| |
|
||||
| help: a tuple variant with a similar name exists: `B`
|
||||
| ^^^^^^^
|
||||
|
|
||||
help: use this syntax instead
|
||||
|
|
||||
LL | A::D => (),
|
||||
| ^^^^
|
||||
help: a tuple variant with a similar name exists
|
||||
|
|
||||
LL | A::B(_) => (),
|
||||
| ^
|
||||
|
||||
error[E0023]: this pattern has 3 fields, but the corresponding tuple variant has 2 fields
|
||||
--> $DIR/pattern-error-continue.rs:17:9
|
||||
|
26
src/test/ui/suggestions/issue-84700.rs
Normal file
26
src/test/ui/suggestions/issue-84700.rs
Normal file
@ -0,0 +1,26 @@
|
||||
// test for suggestion on fieldless enum variant
|
||||
|
||||
#[derive(PartialEq, Debug)]
|
||||
enum FarmAnimal {
|
||||
Worm,
|
||||
Cow,
|
||||
Bull,
|
||||
Chicken { num_eggs: usize },
|
||||
Dog (String),
|
||||
}
|
||||
|
||||
fn what_does_the_animal_say(animal: &FarmAnimal) {
|
||||
|
||||
let noise = match animal {
|
||||
FarmAnimal::Cow(_) => "moo".to_string(),
|
||||
//~^ ERROR expected tuple struct or tuple variant, found unit variant `FarmAnimal::Cow`
|
||||
FarmAnimal::Chicken(_) => "cluck, cluck!".to_string(),
|
||||
//~^ ERROR expected tuple struct or tuple variant, found struct variant `FarmAnimal::Chicken`
|
||||
FarmAnimal::Dog{..} => "woof!".to_string(),
|
||||
_ => todo!()
|
||||
};
|
||||
|
||||
println!("{:?} says: {:?}", animal, noise);
|
||||
}
|
||||
|
||||
fn main() {}
|
21
src/test/ui/suggestions/issue-84700.stderr
Normal file
21
src/test/ui/suggestions/issue-84700.stderr
Normal file
@ -0,0 +1,21 @@
|
||||
error[E0532]: expected tuple struct or tuple variant, found unit variant `FarmAnimal::Cow`
|
||||
--> $DIR/issue-84700.rs:15:9
|
||||
|
|
||||
LL | Cow,
|
||||
| --- `FarmAnimal::Cow` defined here
|
||||
...
|
||||
LL | FarmAnimal::Cow(_) => "moo".to_string(),
|
||||
| ^^^^^^^^^^^^^^^^^^ help: use this syntax instead: `FarmAnimal::Cow`
|
||||
|
||||
error[E0532]: expected tuple struct or tuple variant, found struct variant `FarmAnimal::Chicken`
|
||||
--> $DIR/issue-84700.rs:17:9
|
||||
|
|
||||
LL | Chicken { num_eggs: usize },
|
||||
| --------------------------- `FarmAnimal::Chicken` defined here
|
||||
...
|
||||
LL | FarmAnimal::Chicken(_) => "cluck, cluck!".to_string(),
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^ help: use struct pattern syntax instead: `FarmAnimal::Chicken { num_eggs }`
|
||||
|
||||
error: aborting due to 2 previous errors
|
||||
|
||||
For more information about this error, try `rustc --explain E0532`.
|
Loading…
Reference in New Issue
Block a user