aboutsummaryrefslogtreecommitdiff
path: root/crates/ide_db/src
diff options
context:
space:
mode:
Diffstat (limited to 'crates/ide_db/src')
-rw-r--r--crates/ide_db/src/defs.rs4
-rw-r--r--crates/ide_db/src/helpers/insert_use.rs15
-rw-r--r--crates/ide_db/src/helpers/insert_use/tests.rs14
-rw-r--r--crates/ide_db/src/search.rs2
-rw-r--r--crates/ide_db/src/symbol_index.rs48
5 files changed, 71 insertions, 12 deletions
diff --git a/crates/ide_db/src/defs.rs b/crates/ide_db/src/defs.rs
index bd2afc887..9d7dce1d4 100644
--- a/crates/ide_db/src/defs.rs
+++ b/crates/ide_db/src/defs.rs
@@ -66,7 +66,7 @@ impl Definition {
66 hir::Adt::Union(it) => it.name(db), 66 hir::Adt::Union(it) => it.name(db),
67 hir::Adt::Enum(it) => it.name(db), 67 hir::Adt::Enum(it) => it.name(db),
68 }, 68 },
69 hir::ModuleDef::EnumVariant(it) => it.name(db), 69 hir::ModuleDef::Variant(it) => it.name(db),
70 hir::ModuleDef::Const(it) => it.name(db)?, 70 hir::ModuleDef::Const(it) => it.name(db)?,
71 hir::ModuleDef::Static(it) => it.name(db)?, 71 hir::ModuleDef::Static(it) => it.name(db)?,
72 hir::ModuleDef::Trait(it) => it.name(db), 72 hir::ModuleDef::Trait(it) => it.name(db),
@@ -207,7 +207,7 @@ impl NameClass {
207 Some(NameClass::Definition(Definition::ModuleDef(def.into()))) 207 Some(NameClass::Definition(Definition::ModuleDef(def.into())))
208 }, 208 },
209 ast::Variant(it) => { 209 ast::Variant(it) => {
210 let def: hir::EnumVariant = sema.to_def(&it)?; 210 let def: hir::Variant = sema.to_def(&it)?;
211 Some(NameClass::Definition(Definition::ModuleDef(def.into()))) 211 Some(NameClass::Definition(Definition::ModuleDef(def.into())))
212 }, 212 },
213 ast::Fn(it) => { 213 ast::Fn(it) => {
diff --git a/crates/ide_db/src/helpers/insert_use.rs b/crates/ide_db/src/helpers/insert_use.rs
index 9be36d59b..d6b498be3 100644
--- a/crates/ide_db/src/helpers/insert_use.rs
+++ b/crates/ide_db/src/helpers/insert_use.rs
@@ -9,7 +9,7 @@ use syntax::{
9 ast::{ 9 ast::{
10 self, 10 self,
11 edit::{AstNodeEdit, IndentLevel}, 11 edit::{AstNodeEdit, IndentLevel},
12 make, AstNode, PathSegmentKind, VisibilityOwner, 12 make, AstNode, AttrsOwner, PathSegmentKind, VisibilityOwner,
13 }, 13 },
14 AstToken, InsertPosition, NodeOrToken, SyntaxElement, SyntaxNode, SyntaxToken, 14 AstToken, InsertPosition, NodeOrToken, SyntaxElement, SyntaxNode, SyntaxToken,
15}; 15};
@@ -180,6 +180,15 @@ fn eq_visibility(vis0: Option<ast::Visibility>, vis1: Option<ast::Visibility>) -
180 } 180 }
181} 181}
182 182
183fn eq_attrs(
184 attrs0: impl Iterator<Item = ast::Attr>,
185 attrs1: impl Iterator<Item = ast::Attr>,
186) -> bool {
187 let attrs0 = attrs0.map(|attr| attr.to_string());
188 let attrs1 = attrs1.map(|attr| attr.to_string());
189 attrs0.eq(attrs1)
190}
191
183pub fn try_merge_imports( 192pub fn try_merge_imports(
184 lhs: &ast::Use, 193 lhs: &ast::Use,
185 rhs: &ast::Use, 194 rhs: &ast::Use,
@@ -189,6 +198,10 @@ pub fn try_merge_imports(
189 if !eq_visibility(lhs.visibility(), rhs.visibility()) { 198 if !eq_visibility(lhs.visibility(), rhs.visibility()) {
190 return None; 199 return None;
191 } 200 }
201 if !eq_attrs(lhs.attrs(), rhs.attrs()) {
202 return None;
203 }
204
192 let lhs_tree = lhs.use_tree()?; 205 let lhs_tree = lhs.use_tree()?;
193 let rhs_tree = rhs.use_tree()?; 206 let rhs_tree = rhs.use_tree()?;
194 let merged = try_merge_trees(&lhs_tree, &rhs_tree, merge_behavior)?; 207 let merged = try_merge_trees(&lhs_tree, &rhs_tree, merge_behavior)?;
diff --git a/crates/ide_db/src/helpers/insert_use/tests.rs b/crates/ide_db/src/helpers/insert_use/tests.rs
index 9e194354e..a603fe87f 100644
--- a/crates/ide_db/src/helpers/insert_use/tests.rs
+++ b/crates/ide_db/src/helpers/insert_use/tests.rs
@@ -448,6 +448,20 @@ use std::io;",
448} 448}
449 449
450#[test] 450#[test]
451fn merge_groups_skip_attributed() {
452 check_full(
453 "std::io",
454 r#"
455#[cfg(feature = "gated")] use std::fmt::{Result, Display};
456"#,
457 r#"
458#[cfg(feature = "gated")] use std::fmt::{Result, Display};
459use std::io;
460"#,
461 )
462}
463
464#[test]
451#[ignore] // FIXME: Support this 465#[ignore] // FIXME: Support this
452fn split_out_merge() { 466fn split_out_merge() {
453 check_last( 467 check_last(
diff --git a/crates/ide_db/src/search.rs b/crates/ide_db/src/search.rs
index 525c8a41f..ff10f71c3 100644
--- a/crates/ide_db/src/search.rs
+++ b/crates/ide_db/src/search.rs
@@ -141,7 +141,7 @@ impl Definition {
141 hir::GenericDef::Trait(it) => it.source(db).value.syntax().text_range(), 141 hir::GenericDef::Trait(it) => it.source(db).value.syntax().text_range(),
142 hir::GenericDef::TypeAlias(it) => it.source(db).value.syntax().text_range(), 142 hir::GenericDef::TypeAlias(it) => it.source(db).value.syntax().text_range(),
143 hir::GenericDef::Impl(it) => it.source(db).value.syntax().text_range(), 143 hir::GenericDef::Impl(it) => it.source(db).value.syntax().text_range(),
144 hir::GenericDef::EnumVariant(it) => it.source(db).value.syntax().text_range(), 144 hir::GenericDef::Variant(it) => it.source(db).value.syntax().text_range(),
145 hir::GenericDef::Const(it) => it.source(db).value.syntax().text_range(), 145 hir::GenericDef::Const(it) => it.source(db).value.syntax().text_range(),
146 }; 146 };
147 let mut res = FxHashMap::default(); 147 let mut res = FxHashMap::default();
diff --git a/crates/ide_db/src/symbol_index.rs b/crates/ide_db/src/symbol_index.rs
index ca455fa03..0aa6a0765 100644
--- a/crates/ide_db/src/symbol_index.rs
+++ b/crates/ide_db/src/symbol_index.rs
@@ -39,7 +39,7 @@ use rustc_hash::{FxHashMap, FxHashSet};
39use syntax::{ 39use syntax::{
40 ast::{self, NameOwner}, 40 ast::{self, NameOwner},
41 match_ast, AstNode, Parse, SmolStr, SourceFile, 41 match_ast, AstNode, Parse, SmolStr, SourceFile,
42 SyntaxKind::{self, *}, 42 SyntaxKind::*,
43 SyntaxNode, SyntaxNodePtr, TextRange, WalkEvent, 43 SyntaxNode, SyntaxNodePtr, TextRange, WalkEvent,
44}; 44};
45 45
@@ -323,7 +323,7 @@ impl Query {
323 let (start, end) = SymbolIndex::map_value_to_range(indexed_value.value); 323 let (start, end) = SymbolIndex::map_value_to_range(indexed_value.value);
324 324
325 for symbol in &symbol_index.symbols[start..end] { 325 for symbol in &symbol_index.symbols[start..end] {
326 if self.only_types && !is_type(symbol.kind) { 326 if self.only_types && !symbol.kind.is_type() {
327 continue; 327 continue;
328 } 328 }
329 if self.exact && symbol.name != self.query { 329 if self.exact && symbol.name != self.query {
@@ -341,23 +341,44 @@ impl Query {
341 } 341 }
342} 342}
343 343
344fn is_type(kind: SyntaxKind) -> bool {
345 matches!(kind, STRUCT | ENUM | TRAIT | TYPE_ALIAS)
346}
347
348/// The actual data that is stored in the index. It should be as compact as 344/// The actual data that is stored in the index. It should be as compact as
349/// possible. 345/// possible.
350#[derive(Debug, Clone, PartialEq, Eq, Hash)] 346#[derive(Debug, Clone, PartialEq, Eq, Hash)]
351pub struct FileSymbol { 347pub struct FileSymbol {
352 pub file_id: FileId, 348 pub file_id: FileId,
353 pub name: SmolStr, 349 pub name: SmolStr,
354 pub kind: SyntaxKind, 350 pub kind: FileSymbolKind,
355 pub range: TextRange, 351 pub range: TextRange,
356 pub ptr: SyntaxNodePtr, 352 pub ptr: SyntaxNodePtr,
357 pub name_range: Option<TextRange>, 353 pub name_range: Option<TextRange>,
358 pub container_name: Option<SmolStr>, 354 pub container_name: Option<SmolStr>,
359} 355}
360 356
357#[derive(PartialEq, Eq, Hash, Clone, Copy, Debug)]
358pub enum FileSymbolKind {
359 Function,
360 Struct,
361 Enum,
362 Trait,
363 Module,
364 TypeAlias,
365 Const,
366 Static,
367 Macro,
368}
369
370impl FileSymbolKind {
371 fn is_type(self: FileSymbolKind) -> bool {
372 matches!(
373 self,
374 FileSymbolKind::Struct
375 | FileSymbolKind::Enum
376 | FileSymbolKind::Trait
377 | FileSymbolKind::TypeAlias
378 )
379 }
380}
381
361fn source_file_to_file_symbols(source_file: &SourceFile, file_id: FileId) -> Vec<FileSymbol> { 382fn source_file_to_file_symbols(source_file: &SourceFile, file_id: FileId) -> Vec<FileSymbol> {
362 let mut symbols = Vec::new(); 383 let mut symbols = Vec::new();
363 let mut stack = Vec::new(); 384 let mut stack = Vec::new();
@@ -412,7 +433,18 @@ fn to_symbol(node: &SyntaxNode) -> Option<(SmolStr, SyntaxNodePtr, TextRange)> {
412fn to_file_symbol(node: &SyntaxNode, file_id: FileId) -> Option<FileSymbol> { 433fn to_file_symbol(node: &SyntaxNode, file_id: FileId) -> Option<FileSymbol> {
413 to_symbol(node).map(move |(name, ptr, name_range)| FileSymbol { 434 to_symbol(node).map(move |(name, ptr, name_range)| FileSymbol {
414 name, 435 name,
415 kind: node.kind(), 436 kind: match node.kind() {
437 FN => FileSymbolKind::Function,
438 STRUCT => FileSymbolKind::Struct,
439 ENUM => FileSymbolKind::Enum,
440 TRAIT => FileSymbolKind::Trait,
441 MODULE => FileSymbolKind::Module,
442 TYPE_ALIAS => FileSymbolKind::TypeAlias,
443 CONST => FileSymbolKind::Const,
444 STATIC => FileSymbolKind::Static,
445 MACRO_RULES => FileSymbolKind::Macro,
446 kind => unreachable!("{:?}", kind),
447 },
416 range: node.text_range(), 448 range: node.text_range(),
417 ptr, 449 ptr,
418 file_id, 450 file_id,