Unnamed repository; edit this file 'description' to name the repository.
Merge #10899
10899: ide: hack to make self not unresolved reference in async trait wrapped impl's r=Veykril a=jhgg
fixes #10708
this is a bit hacky, but it "works".
i'm not sure how to even write a test for this though, but i've confirmed it works via manual testing...
Co-authored-by: Jake Heinz <[email protected]>
| -rw-r--r-- | crates/ide/src/syntax_highlighting/highlight.rs | 22 |
1 files changed, 20 insertions, 2 deletions
diff --git a/crates/ide/src/syntax_highlighting/highlight.rs b/crates/ide/src/syntax_highlighting/highlight.rs index d63b0c87a9..b8177b4ab6 100644 --- a/crates/ide/src/syntax_highlighting/highlight.rs +++ b/crates/ide/src/syntax_highlighting/highlight.rs @@ -281,8 +281,18 @@ fn highlight_name_ref( return if syntactic_name_ref_highlighting { highlight_name_ref_by_syntax(name_ref, sema, krate) } else { - HlTag::UnresolvedReference.into() - } + // FIXME: Workaround for https://github.com/rust-analyzer/rust-analyzer/issues/10708 + // + // Some popular proc macros (namely async_trait) will rewrite `self` in such a way that it no + // longer resolves via NameRefClass. If we can't be resolved, but we know we're a self token, + // within a function with a self param, pretend to still be `self`, rather than + // an unresolved reference. + if name_ref.self_token().is_some() && is_in_fn_with_self_param(&name_ref) { + SymbolKind::SelfParam.into() + } else { + HlTag::UnresolvedReference.into() + } + }; } }; let mut h = match name_class { @@ -751,3 +761,11 @@ fn is_child_of_impl(token: &SyntaxToken) -> bool { _ => false, } } + +fn is_in_fn_with_self_param<N: AstNode>(node: &N) -> bool { + node.syntax() + .ancestors() + .find_map(ast::Fn::cast) + .and_then(|s| s.param_list()?.self_param()) + .is_some() +} |