aboutsummaryrefslogtreecommitdiff
path: root/crates/ra_ide_api
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ra_ide_api')
-rw-r--r--crates/ra_ide_api/src/completion/complete_path.rs523
1 files changed, 366 insertions, 157 deletions
diff --git a/crates/ra_ide_api/src/completion/complete_path.rs b/crates/ra_ide_api/src/completion/complete_path.rs
index b42b7c458..a41cab359 100644
--- a/crates/ra_ide_api/src/completion/complete_path.rs
+++ b/crates/ra_ide_api/src/completion/complete_path.rs
@@ -74,10 +74,11 @@ pub(super) fn complete_path(acc: &mut Completions, ctx: &CompletionContext) {
74mod tests { 74mod tests {
75 use test_utils::covers; 75 use test_utils::covers;
76 76
77 use crate::completion::{CompletionKind, check_completion, do_completion}; 77 use crate::completion::{CompletionKind, do_completion, CompletionItem};
78 use insta::assert_debug_snapshot_matches;
78 79
79 fn check_reference_completion(code: &str, expected_completions: &str) { 80 fn do_reference_completion(code: &str) -> Vec<CompletionItem> {
80 check_completion(code, expected_completions, CompletionKind::Reference); 81 do_completion(code, CompletionKind::Reference)
81 } 82 }
82 83
83 #[test] 84 #[test]
@@ -115,227 +116,435 @@ mod tests {
115 116
116 #[test] 117 #[test]
117 fn completes_mod_with_docs() { 118 fn completes_mod_with_docs() {
118 check_reference_completion( 119 assert_debug_snapshot_matches!(
119 "mod_with_docs", 120 do_reference_completion(
120 r" 121 r"
121 use self::my<|>; 122 use self::my<|>;
122 123
123 /// Some simple 124 /// Some simple
124 /// docs describing `mod my`. 125 /// docs describing `mod my`.
125 mod my { 126 mod my {
126 struct Bar; 127 struct Bar;
127 } 128 }
128 ", 129 "
130 ),
131 @r###"[
132 CompletionItem {
133 label: "my",
134 source_range: [27; 29),
135 delete: [27; 29),
136 insert: "my",
137 kind: Module,
138 documentation: Documentation(
139 "Some simple\ndocs describing `mod my`.",
140 ),
141 },
142]"###
129 ); 143 );
130 } 144 }
131 145
132 #[test] 146 #[test]
133 fn completes_use_item_starting_with_self() { 147 fn completes_use_item_starting_with_self() {
134 check_reference_completion( 148 assert_debug_snapshot_matches!(
135 "use_item_starting_with_self", 149 do_reference_completion(
136 r" 150 r"
137 use self::m::<|>; 151 use self::m::<|>;
138 152
139 mod m { 153 mod m {
140 struct Bar; 154 struct Bar;
141 } 155 }
142 ", 156 "
157 ),
158 @r###"[
159 CompletionItem {
160 label: "Bar",
161 source_range: [30; 30),
162 delete: [30; 30),
163 insert: "Bar",
164 kind: Struct,
165 },
166]"###
143 ); 167 );
144 } 168 }
145 169
146 #[test] 170 #[test]
147 fn completes_use_item_starting_with_crate() { 171 fn completes_use_item_starting_with_crate() {
148 check_reference_completion( 172 assert_debug_snapshot_matches!(
149 "use_item_starting_with_crate", 173 do_reference_completion(
150 " 174 "
151 //- /lib.rs 175 //- /lib.rs
152 mod foo; 176 mod foo;
153 struct Spam; 177 struct Spam;
154 //- /foo.rs 178 //- /foo.rs
155 use crate::Sp<|> 179 use crate::Sp<|>
156 ", 180 "
181 ),
182 @r###"[
183 CompletionItem {
184 label: "Spam",
185 source_range: [11; 13),
186 delete: [11; 13),
187 insert: "Spam",
188 kind: Struct,
189 },
190 CompletionItem {
191 label: "foo",
192 source_range: [11; 13),
193 delete: [11; 13),
194 insert: "foo",
195 kind: Module,
196 },
197]"###
157 ); 198 );
158 } 199 }
159 200
160 #[test] 201 #[test]
161 fn completes_nested_use_tree() { 202 fn completes_nested_use_tree() {
162 check_reference_completion( 203 assert_debug_snapshot_matches!(
163 "nested_use_tree", 204 do_reference_completion(
164 " 205 "
165 //- /lib.rs 206 //- /lib.rs
166 mod foo; 207 mod foo;
167 struct Spam; 208 struct Spam;
168 //- /foo.rs 209 //- /foo.rs
169 use crate::{Sp<|>}; 210 use crate::{Sp<|>};
170 ", 211 "
212 ),
213 @r###"[
214 CompletionItem {
215 label: "Spam",
216 source_range: [12; 14),
217 delete: [12; 14),
218 insert: "Spam",
219 kind: Struct,
220 },
221 CompletionItem {
222 label: "foo",
223 source_range: [12; 14),
224 delete: [12; 14),
225 insert: "foo",
226 kind: Module,
227 },
228]"###
171 ); 229 );
172 } 230 }
173 231
174 #[test] 232 #[test]
175 fn completes_deeply_nested_use_tree() { 233 fn completes_deeply_nested_use_tree() {
176 check_reference_completion( 234 assert_debug_snapshot_matches!(
177 "deeply_nested_use_tree", 235 do_reference_completion(
178 " 236 "
179 //- /lib.rs 237 //- /lib.rs
180 mod foo; 238 mod foo;
181 pub mod bar { 239 pub mod bar {
182 pub mod baz { 240 pub mod baz {
183 pub struct Spam; 241 pub struct Spam;
242 }
184 } 243 }
185 } 244 //- /foo.rs
186 //- /foo.rs 245 use crate::{bar::{baz::Sp<|>}};
187 use crate::{bar::{baz::Sp<|>}}; 246 "
188 ", 247 ),
248 @r###"[
249 CompletionItem {
250 label: "Spam",
251 source_range: [23; 25),
252 delete: [23; 25),
253 insert: "Spam",
254 kind: Struct,
255 },
256]"###
189 ); 257 );
190 } 258 }
191 259
192 #[test] 260 #[test]
193 fn completes_enum_variant() { 261 fn completes_enum_variant() {
194 check_reference_completion( 262 assert_debug_snapshot_matches!(
195 "enum_variant", 263 do_reference_completion(
196 " 264 "
197 //- /lib.rs 265 //- /lib.rs
198 /// An enum 266 /// An enum
199 enum E { 267 enum E {
200 /// Foo Variant 268 /// Foo Variant
201 Foo, 269 Foo,
202 /// Bar Variant with i32 270 /// Bar Variant with i32
203 Bar(i32) 271 Bar(i32)
204 } 272 }
205 fn foo() { let _ = E::<|> } 273 fn foo() { let _ = E::<|> }
206 ", 274 "
275 ),
276 @r###"[
277 CompletionItem {
278 label: "Bar",
279 source_range: [116; 116),
280 delete: [116; 116),
281 insert: "Bar",
282 kind: EnumVariant,
283 detail: "(i32)",
284 documentation: Documentation(
285 "Bar Variant with i32",
286 ),
287 },
288 CompletionItem {
289 label: "Foo",
290 source_range: [116; 116),
291 delete: [116; 116),
292 insert: "Foo",
293 kind: EnumVariant,
294 detail: "()",
295 documentation: Documentation(
296 "Foo Variant",
297 ),
298 },
299]"###
207 ); 300 );
208 } 301 }
209 302
210 #[test] 303 #[test]
211 fn completes_enum_variant_with_details() { 304 fn completes_enum_variant_with_details() {
212 check_reference_completion( 305 assert_debug_snapshot_matches!(
213 "enum_variant_with_details", 306 do_reference_completion(
214 " 307 "
215 //- /lib.rs 308 //- /lib.rs
216 struct S { field: u32 } 309 struct S { field: u32 }
217 /// An enum 310 /// An enum
218 enum E { 311 enum E {
219 /// Foo Variant (empty) 312 /// Foo Variant (empty)
220 Foo, 313 Foo,
221 /// Bar Variant with i32 and u32 314 /// Bar Variant with i32 and u32
222 Bar(i32, u32), 315 Bar(i32, u32),
223 /// 316 ///
224 S(S), 317 S(S),
225 } 318 }
226 fn foo() { let _ = E::<|> } 319 fn foo() { let _ = E::<|> }
227 ", 320 "
321 ),
322 @r###"[
323 CompletionItem {
324 label: "Bar",
325 source_range: [180; 180),
326 delete: [180; 180),
327 insert: "Bar",
328 kind: EnumVariant,
329 detail: "(i32, u32)",
330 documentation: Documentation(
331 "Bar Variant with i32 and u32",
332 ),
333 },
334 CompletionItem {
335 label: "Foo",
336 source_range: [180; 180),
337 delete: [180; 180),
338 insert: "Foo",
339 kind: EnumVariant,
340 detail: "()",
341 documentation: Documentation(
342 "Foo Variant (empty)",
343 ),
344 },
345 CompletionItem {
346 label: "S",
347 source_range: [180; 180),
348 delete: [180; 180),
349 insert: "S",
350 kind: EnumVariant,
351 detail: "(S)",
352 documentation: Documentation(
353 "",
354 ),
355 },
356]"###
228 ); 357 );
229 } 358 }
230 359
231 #[test] 360 #[test]
232 fn completes_struct_associated_method() { 361 fn completes_struct_associated_method() {
233 check_reference_completion( 362 assert_debug_snapshot_matches!(
234 "struct_associated_method", 363 do_reference_completion(
235 " 364 "
236 //- /lib.rs 365 //- /lib.rs
237 /// A Struct 366 /// A Struct
238 struct S; 367 struct S;
239 368
240 impl S { 369 impl S {
241 /// An associated method 370 /// An associated method
242 fn m() { } 371 fn m() { }
243 } 372 }
244 373
245 fn foo() { let _ = S::<|> } 374 fn foo() { let _ = S::<|> }
246 ", 375 "
376 ),
377 @r###"[
378 CompletionItem {
379 label: "m",
380 source_range: [100; 100),
381 delete: [100; 100),
382 insert: "m()$0",
383 kind: Function,
384 detail: "fn m()",
385 documentation: Documentation(
386 "An associated method",
387 ),
388 },
389]"###
247 ); 390 );
248 } 391 }
249 392
250 #[test] 393 #[test]
251 fn completes_struct_associated_const() { 394 fn completes_struct_associated_const() {
252 check_reference_completion( 395 assert_debug_snapshot_matches!(
253 "struct_associated_const", 396 do_reference_completion(
254 " 397 "
255 //- /lib.rs 398 //- /lib.rs
256 /// A Struct 399 /// A Struct
257 struct S; 400 struct S;
258 401
259 impl S { 402 impl S {
260 /// An associated const 403 /// An associated const
261 const C: i32 = 42; 404 const C: i32 = 42;
262 } 405 }
263 406
264 fn foo() { let _ = S::<|> } 407 fn foo() { let _ = S::<|> }
265 ", 408 "
409 ),
410 @r###"[
411 CompletionItem {
412 label: "C",
413 source_range: [107; 107),
414 delete: [107; 107),
415 insert: "C",
416 kind: Const,
417 detail: "const C: i32 = 42;",
418 documentation: Documentation(
419 "An associated const",
420 ),
421 },
422]"###
266 ); 423 );
267 } 424 }
268 425
269 #[test] 426 #[test]
270 fn completes_struct_associated_type() { 427 fn completes_struct_associated_type() {
271 check_reference_completion( 428 assert_debug_snapshot_matches!(
272 "struct_associated_type", 429 do_reference_completion(
273 " 430 "
274 //- /lib.rs 431 //- /lib.rs
275 /// A Struct 432 /// A Struct
276 struct S; 433 struct S;
277 434
278 impl S { 435 impl S {
279 /// An associated type 436 /// An associated type
280 type T = i32; 437 type T = i32;
281 } 438 }
282 439
283 fn foo() { let _ = S::<|> } 440 fn foo() { let _ = S::<|> }
284 ", 441 "
442 ),
443 @r###"[
444 CompletionItem {
445 label: "T",
446 source_range: [101; 101),
447 delete: [101; 101),
448 insert: "T",
449 kind: TypeAlias,
450 detail: "type T = i32;",
451 documentation: Documentation(
452 "An associated type",
453 ),
454 },
455]"###
285 ); 456 );
286 } 457 }
287 458
288 #[test] 459 #[test]
289 fn completes_enum_associated_method() { 460 fn completes_enum_associated_method() {
290 check_reference_completion( 461 assert_debug_snapshot_matches!(
291 "enum_associated_method", 462 do_reference_completion(
292 " 463 "
293 //- /lib.rs 464 //- /lib.rs
294 /// An enum 465 /// An enum
295 enum S {}; 466 enum S {};
296 467
297 impl S { 468 impl S {
298 /// An associated method 469 /// An associated method
299 fn m() { } 470 fn m() { }
300 } 471 }
301 472
302 fn foo() { let _ = S::<|> } 473 fn foo() { let _ = S::<|> }
303 ", 474 "
475 ),
476 @r###"[
477 CompletionItem {
478 label: "m",
479 source_range: [100; 100),
480 delete: [100; 100),
481 insert: "m()$0",
482 kind: Function,
483 detail: "fn m()",
484 documentation: Documentation(
485 "An associated method",
486 ),
487 },
488]"###
304 ); 489 );
305 } 490 }
306 491
307 #[test] 492 #[test]
308 fn completes_union_associated_method() { 493 fn completes_union_associated_method() {
309 check_reference_completion( 494 assert_debug_snapshot_matches!(
310 "union_associated_method", 495 do_reference_completion(
311 " 496 "
312 //- /lib.rs 497 //- /lib.rs
313 /// A union 498 /// A union
314 union U {}; 499 union U {};
315 500
316 impl U { 501 impl U {
317 /// An associated method 502 /// An associated method
318 fn m() { } 503 fn m() { }
319 } 504 }
320 505
321 fn foo() { let _ = U::<|> } 506 fn foo() { let _ = U::<|> }
322 ", 507 "
508 ),
509 @r###"[
510 CompletionItem {
511 label: "m",
512 source_range: [101; 101),
513 delete: [101; 101),
514 insert: "m()$0",
515 kind: Function,
516 detail: "fn m()",
517 documentation: Documentation(
518 "An associated method",
519 ),
520 },
521]"###
323 ); 522 );
324 } 523 }
325 524
326 #[test] 525 #[test]
327 fn completes_use_paths_across_crates() { 526 fn completes_use_paths_across_crates() {
328 check_reference_completion( 527 assert_debug_snapshot_matches!(
329 "completes_use_paths_across_crates", 528 do_reference_completion(
330 " 529 "
331 //- /main.rs 530 //- /main.rs
332 use foo::<|>; 531 use foo::<|>;
333 532
334 //- /foo/lib.rs 533 //- /foo/lib.rs
335 pub mod bar { 534 pub mod bar {
336 pub struct S; 535 pub struct S;
337 } 536 }
338 ", 537 "
538 ),
539 @r###"[
540 CompletionItem {
541 label: "bar",
542 source_range: [9; 9),
543 delete: [9; 9),
544 insert: "bar",
545 kind: Module,
546 },
547]"###
339 ); 548 );
340 } 549 }
341} 550}