Merge #4900
4900: Self variant enum res fix r=BGluth a=BGluth Fixes #4789. This is my first PR for this project, so it's probably worth giving it an extra close look. A few things that I wasn't sure about: - Is `resolve_path` really the best place to perform this check? It seemed like a natural place, but perhaps there's a better place? - When handling the new variant `PathResolution::VariantDef`, I couldn't see an obvious variant of `TypeNs` to return in `in_type_ns` for Unions and Structs. Co-authored-by: BGluth <gluthb@gmail.com>
This commit is contained in:
commit
87615166af
@ -216,13 +216,43 @@ pub(crate) fn resolve_path(
|
||||
if let Some(assoc) = self.infer.as_ref()?.assoc_resolutions_for_expr(expr_id) {
|
||||
return Some(PathResolution::AssocItem(assoc.into()));
|
||||
}
|
||||
if let Some(VariantId::EnumVariantId(variant)) =
|
||||
self.infer.as_ref()?.variant_resolution_for_expr(expr_id)
|
||||
{
|
||||
return Some(PathResolution::Def(ModuleDef::EnumVariant(variant.into())));
|
||||
}
|
||||
}
|
||||
|
||||
if let Some(path_pat) = path.syntax().parent().and_then(ast::PathPat::cast) {
|
||||
let pat_id = self.pat_id(&path_pat.into())?;
|
||||
if let Some(assoc) = self.infer.as_ref()?.assoc_resolutions_for_pat(pat_id) {
|
||||
return Some(PathResolution::AssocItem(assoc.into()));
|
||||
}
|
||||
if let Some(VariantId::EnumVariantId(variant)) =
|
||||
self.infer.as_ref()?.variant_resolution_for_pat(pat_id)
|
||||
{
|
||||
return Some(PathResolution::Def(ModuleDef::EnumVariant(variant.into())));
|
||||
}
|
||||
}
|
||||
|
||||
if let Some(rec_lit) = path.syntax().parent().and_then(ast::RecordLit::cast) {
|
||||
let expr_id = self.expr_id(db, &rec_lit.into())?;
|
||||
if let Some(VariantId::EnumVariantId(variant)) =
|
||||
self.infer.as_ref()?.variant_resolution_for_expr(expr_id)
|
||||
{
|
||||
return Some(PathResolution::Def(ModuleDef::EnumVariant(variant.into())));
|
||||
}
|
||||
}
|
||||
|
||||
if let Some(rec_pat) = path.syntax().parent().and_then(ast::RecordPat::cast) {
|
||||
let pat_id = self.pat_id(&rec_pat.into())?;
|
||||
if let Some(VariantId::EnumVariantId(variant)) =
|
||||
self.infer.as_ref()?.variant_resolution_for_pat(pat_id)
|
||||
{
|
||||
return Some(PathResolution::Def(ModuleDef::EnumVariant(variant.into())));
|
||||
}
|
||||
}
|
||||
|
||||
// This must be a normal source file rather than macro file.
|
||||
let hir_path =
|
||||
crate::Path::from_src(path.clone(), &Hygiene::new(db.upcast(), self.file_id))?;
|
||||
|
@ -908,4 +908,84 @@ fn baz(foo: Foo) {
|
||||
"x: i32|x",
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn goto_def_for_enum_variant_self_pattern_const() {
|
||||
check_goto(
|
||||
"
|
||||
//- /lib.rs
|
||||
enum Foo {
|
||||
Bar,
|
||||
}
|
||||
impl Foo {
|
||||
fn baz(self) {
|
||||
match self {
|
||||
Self::Bar<|> => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
",
|
||||
"Bar ENUM_VARIANT FileId(1) 15..18 15..18",
|
||||
"Bar|Bar",
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn goto_def_for_enum_variant_self_pattern_record() {
|
||||
check_goto(
|
||||
"
|
||||
//- /lib.rs
|
||||
enum Foo {
|
||||
Bar { val: i32 },
|
||||
}
|
||||
impl Foo {
|
||||
fn baz(self) -> i32 {
|
||||
match self {
|
||||
Self::Bar<|> { val } => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
",
|
||||
"Bar ENUM_VARIANT FileId(1) 15..31 15..18",
|
||||
"Bar { val: i32 }|Bar",
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn goto_def_for_enum_variant_self_expr_const() {
|
||||
check_goto(
|
||||
"
|
||||
//- /lib.rs
|
||||
enum Foo {
|
||||
Bar,
|
||||
}
|
||||
impl Foo {
|
||||
fn baz(self) {
|
||||
Self::Bar<|>;
|
||||
}
|
||||
}
|
||||
",
|
||||
"Bar ENUM_VARIANT FileId(1) 15..18 15..18",
|
||||
"Bar|Bar",
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn goto_def_for_enum_variant_self_expr_record() {
|
||||
check_goto(
|
||||
"
|
||||
//- /lib.rs
|
||||
enum Foo {
|
||||
Bar { val: i32 },
|
||||
}
|
||||
impl Foo {
|
||||
fn baz(self) {
|
||||
Self::Bar<|> {val: 4};
|
||||
}
|
||||
}
|
||||
",
|
||||
"Bar ENUM_VARIANT FileId(1) 15..31 15..18",
|
||||
"Bar { val: i32 }|Bar",
|
||||
);
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user