about summary refs log tree commit diff
diff options
context:
space:
mode:
authorYoung-Flash <dongyang@apache.org>2024-01-28 18:28:13 +0800
committerYoung-Flash <dongyang@apache.org>2024-01-28 18:28:13 +0800
commit6f303f49fed35a0101b5fce1977bf719045d97df (patch)
tree3db1fbb78241de2fee2a59c1f872a44965ce1e08
parentd410d4a2baf9e99b37b03dd42f06238b14374bf7 (diff)
downloadrust-6f303f49fed35a0101b5fce1977bf719045d97df.tar.gz
rust-6f303f49fed35a0101b5fce1977bf719045d97df.zip
feat: enable excluding refs search results in test
-rw-r--r--crates/ide-db/src/search.rs37
-rw-r--r--crates/ide/src/highlight_related.rs1
-rw-r--r--crates/ide/src/references.rs3
-rw-r--r--crates/rust-analyzer/src/config.rs7
-rw-r--r--crates/rust-analyzer/src/handlers/request.rs4
-rw-r--r--crates/rust-analyzer/src/lsp/to_proto.rs1
-rw-r--r--docs/user/generated_config.adoc5
-rw-r--r--editors/code/package.json5
8 files changed, 60 insertions, 3 deletions
diff --git a/crates/ide-db/src/search.rs b/crates/ide-db/src/search.rs
index 7769d8fba10..5aa4186f822 100644
--- a/crates/ide-db/src/search.rs
+++ b/crates/ide-db/src/search.rs
@@ -15,7 +15,10 @@ use memchr::memmem::Finder;
 use nohash_hasher::IntMap;
 use once_cell::unsync::Lazy;
 use parser::SyntaxKind;
-use syntax::{ast, match_ast, AstNode, AstToken, SyntaxElement, TextRange, TextSize};
+use syntax::{
+    ast::{self, HasAttrs as _},
+    match_ast, AstNode, AstToken, SyntaxElement, TextRange, TextSize,
+};
 use triomphe::Arc;
 
 use crate::{
@@ -134,6 +137,7 @@ pub enum ReferenceCategory {
     // FIXME: Some day should be able to search in doc comments. Would probably
     // need to switch from enum to bitflags then?
     // DocComment
+    Test,
 }
 
 /// Generally, `search_scope` returns files that might contain references for the element.
@@ -872,6 +876,10 @@ fn def_to_ty(sema: &Semantics<'_, RootDatabase>, def: &Definition) -> Option<hir
 
 impl ReferenceCategory {
     fn new(def: &Definition, r: &ast::NameRef) -> Option<ReferenceCategory> {
+        if is_name_ref_in_test(r) {
+            return Some(ReferenceCategory::Test);
+        }
+
         // Only Locals and Fields have accesses for now.
         if !matches!(def, Definition::Local(_) | Definition::Field(_)) {
             return is_name_ref_in_import(r).then_some(ReferenceCategory::Import);
@@ -910,3 +918,30 @@ fn is_name_ref_in_import(name_ref: &ast::NameRef) -> bool {
         .and_then(|it| it.parent_path().top_path().syntax().parent())
         .map_or(false, |it| it.kind() == SyntaxKind::USE_TREE)
 }
+
+fn is_name_ref_in_test(name_ref: &ast::NameRef) -> bool {
+    let mode = name_ref.syntax().ancestors().find_map(|node| {
+        match_ast! {
+            match node {
+                ast::Fn(f) => {
+                    let attrs = f.attrs();
+                    let mut is_test = false;
+                    for attr in attrs {
+                        if attr.to_string() == "#[test]" {
+                            is_test = true;
+                            break;
+                        }
+                    }
+                    if is_test {
+                        Some(ReferenceCategory::Test)
+                    }
+                    else {
+                        None
+                    }
+                },
+                _ => None
+            }
+        }
+    });
+    mode.is_some()
+}
diff --git a/crates/ide/src/highlight_related.rs b/crates/ide/src/highlight_related.rs
index c3a403b1070..53ed117060a 100644
--- a/crates/ide/src/highlight_related.rs
+++ b/crates/ide/src/highlight_related.rs
@@ -519,6 +519,7 @@ mod tests {
                             ReferenceCategory::Read => "read",
                             ReferenceCategory::Write => "write",
                             ReferenceCategory::Import => "import",
+                            ReferenceCategory::Test => "test",
                         }
                         .to_string()
                     }),
diff --git a/crates/ide/src/references.rs b/crates/ide/src/references.rs
index 78fe84f70d3..bcf862012a6 100644
--- a/crates/ide/src/references.rs
+++ b/crates/ide/src/references.rs
@@ -454,6 +454,7 @@ fn main() {
             "#]],
         );
     }
+
     #[test]
     fn test_variant_tuple_before_paren() {
         check(
@@ -1435,7 +1436,7 @@ fn test$0() {
             expect![[r#"
                 test Function FileId(0) 0..33 11..15
 
-                FileId(0) 24..28
+                FileId(0) 24..28 Test
             "#]],
         );
     }
diff --git a/crates/rust-analyzer/src/config.rs b/crates/rust-analyzer/src/config.rs
index 3c1b464c3c1..eeb28b8fe42 100644
--- a/crates/rust-analyzer/src/config.rs
+++ b/crates/rust-analyzer/src/config.rs
@@ -494,6 +494,9 @@ config_data! {
         /// Exclude imports from find-all-references.
         references_excludeImports: bool = "false",
 
+        /// Exclude tests from find-all-references.
+        references_excludeTests: bool = "false",
+
         /// Allow renaming of items not belonging to the loaded workspaces.
         rename_allowExternalItems: bool = "false",
 
@@ -1545,6 +1548,10 @@ impl Config {
         self.data.references_excludeImports
     }
 
+    pub fn find_all_refs_exclude_tests(&self) -> bool {
+        self.data.references_excludeTests
+    }
+
     pub fn snippet_cap(&self) -> bool {
         self.experimental("snippetTextEdit")
     }
diff --git a/crates/rust-analyzer/src/handlers/request.rs b/crates/rust-analyzer/src/handlers/request.rs
index f3c2df24d95..03725daedd3 100644
--- a/crates/rust-analyzer/src/handlers/request.rs
+++ b/crates/rust-analyzer/src/handlers/request.rs
@@ -1055,6 +1055,7 @@ pub(crate) fn handle_references(
     let position = from_proto::file_position(&snap, params.text_document_position)?;
 
     let exclude_imports = snap.config.find_all_refs_exclude_imports();
+    let exclude_tests = snap.config.find_all_refs_exclude_tests();
 
     let refs = match snap.analysis.find_all_refs(position, None)? {
         None => return Ok(None),
@@ -1078,7 +1079,8 @@ pub(crate) fn handle_references(
                 .flat_map(|(file_id, refs)| {
                     refs.into_iter()
                         .filter(|&(_, category)| {
-                            !exclude_imports || category != Some(ReferenceCategory::Import)
+                            (!exclude_imports || category != Some(ReferenceCategory::Import))
+                                && (!exclude_tests || category != Some(ReferenceCategory::Test))
                         })
                         .map(move |(range, _)| FileRange { file_id, range })
                 })
diff --git a/crates/rust-analyzer/src/lsp/to_proto.rs b/crates/rust-analyzer/src/lsp/to_proto.rs
index fe381fbeb3f..f221863aff0 100644
--- a/crates/rust-analyzer/src/lsp/to_proto.rs
+++ b/crates/rust-analyzer/src/lsp/to_proto.rs
@@ -92,6 +92,7 @@ pub(crate) fn document_highlight_kind(
         ReferenceCategory::Read => Some(lsp_types::DocumentHighlightKind::READ),
         ReferenceCategory::Write => Some(lsp_types::DocumentHighlightKind::WRITE),
         ReferenceCategory::Import => None,
+        ReferenceCategory::Test => None,
     }
 }
 
diff --git a/docs/user/generated_config.adoc b/docs/user/generated_config.adoc
index f887bb9df31..cfa7503d739 100644
--- a/docs/user/generated_config.adoc
+++ b/docs/user/generated_config.adoc
@@ -777,6 +777,11 @@ Internal config, path to proc-macro server executable.
 --
 Exclude imports from find-all-references.
 --
+[[rust-analyzer.references.excludeTests]]rust-analyzer.references.excludeTests (default: `false`)::
++
+--
+Exclude tests from find-all-references.
+--
 [[rust-analyzer.rename.allowExternalItems]]rust-analyzer.rename.allowExternalItems (default: `false`)::
 +
 --
diff --git a/editors/code/package.json b/editors/code/package.json
index 5ed5146ea1b..841e364ed84 100644
--- a/editors/code/package.json
+++ b/editors/code/package.json
@@ -1505,6 +1505,11 @@
                     "default": false,
                     "type": "boolean"
                 },
+                "rust-analyzer.references.excludeTests": {
+                    "markdownDescription": "Exclude tests from find-all-references.",
+                    "default": false,
+                    "type": "boolean"
+                },
                 "rust-analyzer.rename.allowExternalItems": {
                     "markdownDescription": "Allow renaming of items not belonging to the loaded workspaces.",
                     "default": false,