diff options
Diffstat (limited to 'crates/completion/src/completions/snippet.rs')
-rw-r--r-- | crates/completion/src/completions/snippet.rs | 114 |
1 files changed, 114 insertions, 0 deletions
diff --git a/crates/completion/src/completions/snippet.rs b/crates/completion/src/completions/snippet.rs new file mode 100644 index 000000000..6f0c00078 --- /dev/null +++ b/crates/completion/src/completions/snippet.rs | |||
@@ -0,0 +1,114 @@ | |||
1 | //! This file provides snippet completions, like `pd` => `eprintln!(...)`. | ||
2 | |||
3 | use crate::{ | ||
4 | config::SnippetCap, item::Builder, CompletionContext, CompletionItem, CompletionItemKind, | ||
5 | CompletionKind, Completions, | ||
6 | }; | ||
7 | |||
8 | fn snippet(ctx: &CompletionContext, cap: SnippetCap, label: &str, snippet: &str) -> Builder { | ||
9 | CompletionItem::new(CompletionKind::Snippet, ctx.source_range(), label) | ||
10 | .insert_snippet(cap, snippet) | ||
11 | .kind(CompletionItemKind::Snippet) | ||
12 | } | ||
13 | |||
14 | pub(crate) fn complete_expr_snippet(acc: &mut Completions, ctx: &CompletionContext) { | ||
15 | if !(ctx.is_trivial_path && ctx.function_syntax.is_some()) { | ||
16 | return; | ||
17 | } | ||
18 | let cap = match ctx.config.snippet_cap { | ||
19 | Some(it) => it, | ||
20 | None => return, | ||
21 | }; | ||
22 | |||
23 | snippet(ctx, cap, "pd", "eprintln!(\"$0 = {:?}\", $0);").add_to(acc); | ||
24 | snippet(ctx, cap, "ppd", "eprintln!(\"$0 = {:#?}\", $0);").add_to(acc); | ||
25 | } | ||
26 | |||
27 | pub(crate) fn complete_item_snippet(acc: &mut Completions, ctx: &CompletionContext) { | ||
28 | if !ctx.is_new_item { | ||
29 | return; | ||
30 | } | ||
31 | let cap = match ctx.config.snippet_cap { | ||
32 | Some(it) => it, | ||
33 | None => return, | ||
34 | }; | ||
35 | |||
36 | snippet( | ||
37 | ctx, | ||
38 | cap, | ||
39 | "tmod (Test module)", | ||
40 | "\ | ||
41 | #[cfg(test)] | ||
42 | mod tests { | ||
43 | use super::*; | ||
44 | |||
45 | #[test] | ||
46 | fn ${1:test_name}() { | ||
47 | $0 | ||
48 | } | ||
49 | }", | ||
50 | ) | ||
51 | .lookup_by("tmod") | ||
52 | .add_to(acc); | ||
53 | |||
54 | snippet( | ||
55 | ctx, | ||
56 | cap, | ||
57 | "tfn (Test function)", | ||
58 | "\ | ||
59 | #[test] | ||
60 | fn ${1:feature}() { | ||
61 | $0 | ||
62 | }", | ||
63 | ) | ||
64 | .lookup_by("tfn") | ||
65 | .add_to(acc); | ||
66 | |||
67 | snippet(ctx, cap, "macro_rules", "macro_rules! $1 {\n\t($2) => {\n\t\t$0\n\t};\n}").add_to(acc); | ||
68 | } | ||
69 | |||
70 | #[cfg(test)] | ||
71 | mod tests { | ||
72 | use expect_test::{expect, Expect}; | ||
73 | |||
74 | use crate::{test_utils::completion_list, CompletionKind}; | ||
75 | |||
76 | fn check(ra_fixture: &str, expect: Expect) { | ||
77 | let actual = completion_list(ra_fixture, CompletionKind::Snippet); | ||
78 | expect.assert_eq(&actual) | ||
79 | } | ||
80 | |||
81 | #[test] | ||
82 | fn completes_snippets_in_expressions() { | ||
83 | check( | ||
84 | r#"fn foo(x: i32) { <|> }"#, | ||
85 | expect![[r#" | ||
86 | sn pd | ||
87 | sn ppd | ||
88 | "#]], | ||
89 | ); | ||
90 | } | ||
91 | |||
92 | #[test] | ||
93 | fn should_not_complete_snippets_in_path() { | ||
94 | check(r#"fn foo(x: i32) { ::foo<|> }"#, expect![[""]]); | ||
95 | check(r#"fn foo(x: i32) { ::<|> }"#, expect![[""]]); | ||
96 | } | ||
97 | |||
98 | #[test] | ||
99 | fn completes_snippets_in_items() { | ||
100 | check( | ||
101 | r#" | ||
102 | #[cfg(test)] | ||
103 | mod tests { | ||
104 | <|> | ||
105 | } | ||
106 | "#, | ||
107 | expect![[r#" | ||
108 | sn macro_rules | ||
109 | sn tfn (Test function) | ||
110 | sn tmod (Test module) | ||
111 | "#]], | ||
112 | ) | ||
113 | } | ||
114 | } | ||