Unnamed repository; edit this file 'description' to name the repository.
Diffstat (limited to 'crates/ide-assists/src/handlers/sort_items.rs')
-rw-r--r--crates/ide-assists/src/handlers/sort_items.rs111
1 files changed, 105 insertions, 6 deletions
diff --git a/crates/ide-assists/src/handlers/sort_items.rs b/crates/ide-assists/src/handlers/sort_items.rs
index a93704b394..3a0121f55f 100644
--- a/crates/ide-assists/src/handlers/sort_items.rs
+++ b/crates/ide-assists/src/handlers/sort_items.rs
@@ -87,11 +87,7 @@ pub(crate) fn sort_items(acc: &mut Assists, ctx: &AssistContext<'_>) -> Option<(
return None;
}
- if let Some(trait_ast) = ctx.find_node_at_offset::<ast::Trait>() {
- add_sort_methods_assist(acc, trait_ast.assoc_item_list()?)
- } else if let Some(impl_ast) = ctx.find_node_at_offset::<ast::Impl>() {
- add_sort_methods_assist(acc, impl_ast.assoc_item_list()?)
- } else if let Some(struct_ast) = ctx.find_node_at_offset::<ast::Struct>() {
+ if let Some(struct_ast) = ctx.find_node_at_offset::<ast::Struct>() {
add_sort_field_list_assist(acc, struct_ast.field_list())
} else if let Some(union_ast) = ctx.find_node_at_offset::<ast::Union>() {
add_sort_fields_assist(acc, union_ast.record_field_list()?)
@@ -103,6 +99,10 @@ pub(crate) fn sort_items(acc: &mut Assists, ctx: &AssistContext<'_>) -> Option<(
add_sort_fields_assist(acc, enum_struct_variant_ast)
} else if let Some(enum_ast) = ctx.find_node_at_offset::<ast::Enum>() {
add_sort_variants_assist(acc, enum_ast.variant_list()?)
+ } else if let Some(trait_ast) = ctx.find_node_at_offset::<ast::Trait>() {
+ add_sort_methods_assist(acc, ctx, trait_ast.assoc_item_list()?)
+ } else if let Some(impl_ast) = ctx.find_node_at_offset::<ast::Impl>() {
+ add_sort_methods_assist(acc, ctx, impl_ast.assoc_item_list()?)
} else {
None
}
@@ -116,9 +116,11 @@ trait AddRewrite {
new: Vec<T>,
target: TextRange,
) -> Option<()>;
+ fn yeet() {}
}
impl AddRewrite for Assists {
+ fn yeet() {}
fn add_rewrite<T: AstNode>(
&mut self,
label: &str,
@@ -146,7 +148,19 @@ fn add_sort_field_list_assist(acc: &mut Assists, field_list: Option<ast::FieldLi
}
}
-fn add_sort_methods_assist(acc: &mut Assists, item_list: ast::AssocItemList) -> Option<()> {
+fn add_sort_methods_assist(
+ acc: &mut Assists,
+ ctx: &AssistContext<'_>,
+ item_list: ast::AssocItemList,
+) -> Option<()> {
+ let selection = ctx.selection_trimmed();
+
+ // ignore assist if the selection intersects with an associated item.
+ if item_list.assoc_items().any(|item| item.syntax().text_range().intersect(selection).is_some())
+ {
+ return None;
+ }
+
let methods = get_methods(&item_list);
let sorted = sort_by_name(&methods);
@@ -217,6 +231,51 @@ mod tests {
use super::*;
#[test]
+ fn not_applicable_if_selection_in_fn_body() {
+ check_assist_not_applicable(
+ sort_items,
+ r#"
+struct S;
+impl S {
+ fn func2() {
+ $0 bar $0
+ }
+ fn func() {}
+}
+ "#,
+ )
+ }
+
+ #[test]
+ fn not_applicable_if_selection_at_associated_const() {
+ check_assist_not_applicable(
+ sort_items,
+ r#"
+struct S;
+impl S {
+ fn func2() {}
+ fn func() {}
+ const C: () = $0()$0;
+}
+ "#,
+ )
+ }
+
+ #[test]
+ fn not_applicable_if_selection_overlaps_nodes() {
+ check_assist_not_applicable(
+ sort_items,
+ r#"
+struct S;
+impl $0S {
+ fn$0 func2() {}
+ fn func() {}
+}
+ "#,
+ )
+ }
+
+ #[test]
fn not_applicable_if_no_selection() {
cov_mark::check!(not_applicable_if_no_selection);
@@ -232,6 +291,21 @@ t$0rait Bar {
}
#[test]
+ fn not_applicable_if_selection_in_trait_fn_body() {
+ check_assist_not_applicable(
+ sort_items,
+ r#"
+trait Bar {
+ fn b() {
+ $0 hello $0
+ }
+ fn a();
+}
+ "#,
+ )
+ }
+
+ #[test]
fn not_applicable_if_trait_empty() {
cov_mark::check!(not_applicable_if_sorted_or_empty_or_single);
@@ -459,6 +533,31 @@ struct Bar {
}
#[test]
+ fn sort_struct_inside_a_function() {
+ check_assist(
+ sort_items,
+ r#"
+fn hello() {
+ $0struct Bar$0 {
+ b: u8,
+ a: u32,
+ c: u64,
+ }
+}
+ "#,
+ r#"
+fn hello() {
+ struct Bar {
+ a: u32,
+ b: u8,
+ c: u64,
+ }
+}
+ "#,
+ )
+ }
+
+ #[test]
fn sort_generic_struct_with_lifetime() {
check_assist(
sort_items,