@@ -27,31 +27,34 @@ use std::collections::BTreeSet;
2727// # pub mod std { pub mod collections { pub struct HashMap { } } }
2828// ```
2929pub ( crate ) fn auto_import ( ctx : AssistCtx ) -> Option < Assist > {
30- let path_to_import: ast:: Path = ctx. find_node_at_offset ( ) ?;
31- let path_to_import_syntax = path_to_import. syntax ( ) ;
32- if path_to_import_syntax. ancestors ( ) . find_map ( ast:: UseItem :: cast) . is_some ( ) {
30+ let path_under_caret: ast:: Path = ctx. find_node_at_offset ( ) ?;
31+ if path_under_caret. syntax ( ) . ancestors ( ) . find_map ( ast:: UseItem :: cast) . is_some ( ) {
3332 return None ;
3433 }
35- let name_to_import =
36- path_to_import_syntax. descendants ( ) . find_map ( ast:: NameRef :: cast) ?. syntax ( ) . to_string ( ) ;
3734
38- let module = path_to_import_syntax . ancestors ( ) . find_map ( ast:: Module :: cast) ;
35+ let module = path_under_caret . syntax ( ) . ancestors ( ) . find_map ( ast:: Module :: cast) ;
3936 let position = match module. and_then ( |it| it. item_list ( ) ) {
4037 Some ( item_list) => item_list. syntax ( ) . clone ( ) ,
4138 None => {
42- let current_file = path_to_import_syntax. ancestors ( ) . find_map ( ast:: SourceFile :: cast) ?;
39+ let current_file =
40+ path_under_caret. syntax ( ) . ancestors ( ) . find_map ( ast:: SourceFile :: cast) ?;
4341 current_file. syntax ( ) . clone ( )
4442 }
4543 } ;
4644 let source_analyzer = ctx. source_analyzer ( & position, None ) ;
4745 let module_with_name_to_import = source_analyzer. module ( ) ?;
48- if source_analyzer. resolve_path ( ctx. db , & path_to_import) . is_some ( ) {
46+
47+ let name_ref_to_import =
48+ path_under_caret. syntax ( ) . descendants ( ) . find_map ( ast:: NameRef :: cast) ?;
49+ if source_analyzer
50+ . resolve_path ( ctx. db , & name_ref_to_import. syntax ( ) . ancestors ( ) . find_map ( ast:: Path :: cast) ?)
51+ . is_some ( )
52+ {
4953 return None ;
5054 }
5155
52- let mut imports_locator = ImportsLocator :: new ( ctx. db ) ;
53-
54- let proposed_imports = imports_locator
56+ let name_to_import = name_ref_to_import. syntax ( ) . to_string ( ) ;
57+ let proposed_imports = ImportsLocator :: new ( ctx. db )
5558 . find_imports ( & name_to_import)
5659 . into_iter ( )
5760 . filter_map ( |module_def| module_with_name_to_import. find_use_path ( ctx. db , module_def) )
@@ -66,10 +69,10 @@ pub(crate) fn auto_import(ctx: AssistCtx) -> Option<Assist> {
6669 let mut group = ctx. add_assist_group ( format ! ( "Import {}" , name_to_import) ) ;
6770 for import in proposed_imports {
6871 group. add_assist ( AssistId ( "auto_import" ) , format ! ( "Import `{}`" , & import) , |edit| {
69- edit. target ( path_to_import_syntax . text_range ( ) ) ;
72+ edit. target ( path_under_caret . syntax ( ) . text_range ( ) ) ;
7073 insert_use_statement (
7174 & position,
72- path_to_import_syntax ,
75+ path_under_caret . syntax ( ) ,
7376 & import,
7477 edit. text_edit_builder ( ) ,
7578 ) ;
@@ -266,4 +269,25 @@ mod tests {
266269 "GroupLabel" ,
267270 )
268271 }
272+
273+ #[ test]
274+ fn not_applicable_when_path_start_is_imported ( ) {
275+ check_assist_not_applicable (
276+ auto_import,
277+ r"
278+ pub mod mod1 {
279+ pub mod mod2 {
280+ pub mod mod3 {
281+ pub struct TestStruct;
282+ }
283+ }
284+ }
285+
286+ use mod1::mod2;
287+ fn main() {
288+ mod2::mod3::TestStruct<|>
289+ }
290+ " ,
291+ ) ;
292+ }
269293}
0 commit comments