Unnamed repository; edit this file 'description' to name the repository.
Auto merge of #17140 - harrysarson:harry-unused-self, r=Veykril
handle {self} when removing unused imports Fixes #17139 On master ```rs mod inner { pub struct X(); pub struct Y(); } mod z { use super::inner::{self, X}$0; fn f() { let y = inner::Y(); } } ``` becomes ```rs mod inner { pub struct X(); pub struct Y(); } mod z { use super::inner:self; fn f() { let y = inner::Y(); } } ``` with this fix it instead becomes ``` ```rs mod inner { pub struct X(); pub struct Y(); } mod z { use super::inner; fn f() { let y = inner::Y(); } } ```
bors 2024-05-23
parent 653b69e · parent a653ddf · commit e3e22c6
-rw-r--r--crates/ide-assists/src/handlers/remove_unused_imports.rs34
-rw-r--r--crates/syntax/src/ast/node_ext.rs21
2 files changed, 53 insertions, 2 deletions
diff --git a/crates/ide-assists/src/handlers/remove_unused_imports.rs b/crates/ide-assists/src/handlers/remove_unused_imports.rs
index 0f0f13bbc8..b653f3b665 100644
--- a/crates/ide-assists/src/handlers/remove_unused_imports.rs
+++ b/crates/ide-assists/src/handlers/remove_unused_imports.rs
@@ -777,6 +777,40 @@ mod z {
}
#[test]
+ fn remove_unused_fixes_nested_self() {
+ check_assist(
+ remove_unused_imports,
+ r#"
+mod inner {
+ pub struct X();
+ pub struct Y();
+}
+
+mod z {
+ use super::inner::{self, X}$0;
+
+ fn f() {
+ let y = inner::Y();
+ }
+}
+"#,
+ r#"mod inner {
+ pub struct X();
+ pub struct Y();
+}
+
+mod z {
+ use super::inner::{self};
+
+ fn f() {
+ let y = inner::Y();
+ }
+}
+"#,
+ );
+ }
+
+ #[test]
fn dont_remove_used_glob() {
check_assist_not_applicable(
remove_unused_imports,
diff --git a/crates/syntax/src/ast/node_ext.rs b/crates/syntax/src/ast/node_ext.rs
index c3d6f50e6b..b0fbe7101c 100644
--- a/crates/syntax/src/ast/node_ext.rs
+++ b/crates/syntax/src/ast/node_ext.rs
@@ -378,9 +378,26 @@ impl ast::UseTreeList {
/// Remove the unnecessary braces in current `UseTreeList`
pub fn remove_unnecessary_braces(mut self) {
+ // Returns true iff there is a single subtree and it is not the self keyword. The braces in
+ // `use x::{self};` are necessary and so we should not remove them.
+ let has_single_subtree_that_is_not_self = |u: &ast::UseTreeList| {
+ if let Some((single_subtree,)) = u.use_trees().collect_tuple() {
+ // We have a single subtree, check whether it is self.
+
+ let is_self = single_subtree.path().as_ref().map_or(false, |path| {
+ path.segment().and_then(|seg| seg.self_token()).is_some()
+ && path.qualifier().is_none()
+ });
+
+ !is_self
+ } else {
+ // Not a single subtree
+ false
+ }
+ };
+
let remove_brace_in_use_tree_list = |u: &ast::UseTreeList| {
- let use_tree_count = u.use_trees().count();
- if use_tree_count == 1 {
+ if has_single_subtree_that_is_not_self(u) {
if let Some(a) = u.l_curly_token() {
ted::remove(a)
}