Unnamed repository; edit this file 'description' to name the repository.
Diffstat (limited to 'crates/ide-completion/src/completions/keyword.rs')
-rw-r--r--crates/ide-completion/src/completions/keyword.rs115
1 files changed, 24 insertions, 91 deletions
diff --git a/crates/ide-completion/src/completions/keyword.rs b/crates/ide-completion/src/completions/keyword.rs
index 281e6e9783..e870ecc229 100644
--- a/crates/ide-completion/src/completions/keyword.rs
+++ b/crates/ide-completion/src/completions/keyword.rs
@@ -2,106 +2,39 @@
//! - `self`, `super` and `crate`, as these are considered part of path completions.
//! - `await`, as this is a postfix completion we handle this in the postfix completions.
-use syntax::T;
+use syntax::ast::Item;
-use crate::{
- context::{NameRefContext, PathKind},
- CompletionContext, CompletionItem, CompletionItemKind, Completions,
-};
+use crate::{context::NameRefContext, CompletionContext, Completions};
pub(crate) fn complete_expr_keyword(acc: &mut Completions, ctx: &CompletionContext) {
- if matches!(ctx.nameref_ctx(), Some(NameRefContext { record_expr: Some(_), .. })) {
- cov_mark::hit!(no_keyword_completion_in_record_lit);
- return;
- }
- if ctx.is_non_trivial_path() {
- cov_mark::hit!(no_keyword_completion_in_non_trivial_path);
- return;
- }
- if ctx.pattern_ctx.is_some() {
- return;
- }
-
- let mut add_keyword = |kw, snippet| add_keyword(acc, ctx, kw, snippet);
-
- let expects_assoc_item = ctx.expects_assoc_item();
- let has_block_expr_parent = ctx.has_block_expr_parent();
- let expects_item = ctx.expects_item();
-
- if let Some(PathKind::Vis { .. }) = ctx.path_kind() {
- return;
- }
- if ctx.has_unfinished_impl_or_trait_prev_sibling() {
- add_keyword("where", "where");
- if ctx.has_impl_prev_sibling() {
- add_keyword("for", "for");
- }
- return;
- }
- if ctx.previous_token_is(T![unsafe]) {
- if expects_item || expects_assoc_item || has_block_expr_parent {
- add_keyword("fn", "fn $1($2) {\n $0\n}")
+ let item = match ctx.nameref_ctx() {
+ Some(NameRefContext { keyword: Some(item), record_expr: None, .. })
+ if !ctx.is_non_trivial_path() =>
+ {
+ item
}
+ _ => return,
+ };
- if expects_item || has_block_expr_parent {
- add_keyword("trait", "trait $1 {\n $0\n}");
- add_keyword("impl", "impl $1 {\n $0\n}");
- }
-
- return;
- }
-
- if ctx.qualifier_ctx.vis_node.is_none()
- && (expects_item || ctx.expects_non_trait_assoc_item() || ctx.expect_field())
- {
- add_keyword("pub(crate)", "pub(crate)");
- add_keyword("pub(super)", "pub(super)");
- add_keyword("pub", "pub");
- }
-
- if expects_item || expects_assoc_item || has_block_expr_parent {
- add_keyword("unsafe", "unsafe");
- add_keyword("fn", "fn $1($2) {\n $0\n}");
- add_keyword("const", "const $0");
- add_keyword("type", "type $0");
- }
-
- if expects_item || has_block_expr_parent {
- if ctx.qualifier_ctx.vis_node.is_none() {
- add_keyword("impl", "impl $1 {\n $0\n}");
- add_keyword("extern", "extern $0");
- }
- add_keyword("use", "use $0");
- add_keyword("trait", "trait $1 {\n $0\n}");
- add_keyword("static", "static $0");
- add_keyword("mod", "mod $0");
- }
-
- if expects_item || has_block_expr_parent {
- add_keyword("enum", "enum $1 {\n $0\n}");
- add_keyword("struct", "struct $0");
- add_keyword("union", "union $1 {\n $0\n}");
- }
-}
-
-pub(super) fn add_keyword(acc: &mut Completions, ctx: &CompletionContext, kw: &str, snippet: &str) {
- let mut item = CompletionItem::new(CompletionItemKind::Keyword, ctx.source_range(), kw);
+ let mut add_keyword = |kw, snippet| acc.add_keyword_snippet(ctx, kw, snippet);
- match ctx.config.snippet_cap {
- Some(cap) => {
- if snippet.ends_with('}') && ctx.incomplete_let {
- // complete block expression snippets with a trailing semicolon, if inside an incomplete let
- cov_mark::hit!(let_semi);
- item.insert_snippet(cap, format!("{};", snippet));
- } else {
- item.insert_snippet(cap, snippet);
+ match item {
+ Item::Impl(it) => {
+ if it.for_token().is_none() && it.trait_().is_none() && it.self_ty().is_some() {
+ add_keyword("for", "for");
}
+ add_keyword("where", "where");
}
- None => {
- item.insert_text(if snippet.contains('$') { kw } else { snippet });
+ Item::Enum(_)
+ | Item::Fn(_)
+ | Item::Struct(_)
+ | Item::Trait(_)
+ | Item::TypeAlias(_)
+ | Item::Union(_) => {
+ add_keyword("where", "where");
}
- };
- item.add_to(acc);
+ _ => (),
+ }
}
#[cfg(test)]