diff --git a/crates/ide-assists/src/handlers/generate_blanket_trait_impl.rs b/crates/ide-assists/src/handlers/generate_blanket_trait_impl.rs index 4454e4701312..1e3f2ac67725 100644 --- a/crates/ide-assists/src/handlers/generate_blanket_trait_impl.rs +++ b/crates/ide-assists/src/handlers/generate_blanket_trait_impl.rs @@ -15,7 +15,7 @@ use syntax::{ self, AssocItem, GenericParam, HasAttrs, HasGenericParams, HasName, HasTypeBounds, HasVisibility, edit::AstNodeEdit, syntax_factory::SyntaxFactory, }, - syntax_editor::Position, + syntax_editor::{Position, Removable}, }; // Assist: generate_blanket_trait_impl @@ -99,10 +99,15 @@ pub(crate) fn generate_blanket_trait_impl( ast::AssocItem::Fn(method) if method.body().is_none() => { todo_fn(make, &method, ctx.config).into() } - ast::AssocItem::Const(_) | ast::AssocItem::TypeAlias(_) => item, + ast::AssocItem::Const(it) if it.body().is_none() => { + ast::AssocItem::Const(it.reset_indent()) + } + ast::AssocItem::TypeAlias(it) if it.ty().is_none() => { + remove_bounds(it.reset_indent()).into() + } _ => return None, }; - Some(item.reset_indent().indent(1.into())) + Some(item.indent(1.into())) }) .collect::>(); (!items.is_empty()).then(|| make.assoc_item_list(items)) @@ -284,6 +289,16 @@ fn todo_fn(make: &SyntaxFactory, f: &ast::Fn, config: &AssistConfig) -> ast::Fn ) } +fn remove_bounds(alias: ast::TypeAlias) -> ast::TypeAlias { + let (editor, alias) = syntax::syntax_editor::SyntaxEditor::with_ast_node(&alias); + + if let Some(type_bound_list) = alias.type_bound_list() { + type_bound_list.remove(&editor); + } + + ast::TypeAlias::cast(editor.finish().new_root().clone()).unwrap() +} + fn cfg_attrs(node: &impl HasAttrs) -> impl Iterator { node.attrs().filter(|attr| matches!(attr.meta(), Some(ast::Meta::CfgMeta(_)))) } @@ -533,6 +548,33 @@ impl Foo for $0T { ); } + #[test] + fn test_gen_blanket_assoc_items_with_default() { + check_assist( + generate_blanket_trait_impl, + r#" +trait $0Foo { + type Item = (); + + const N: usize = 3; + + fn foo(&self) {} +} +"#, + r#" +trait Foo { + type Item = (); + + const N: usize = 3; + + fn foo(&self) {} +} + +impl Foo for $0T {} +"#, + ); + } + #[test] fn test_gen_blanket_indent() { check_assist( @@ -775,7 +817,7 @@ mod foo { mod foo { mod bar { trait $0Foo { - type Item: Bar< + type Item where Self: Bar< Self, >; @@ -790,7 +832,7 @@ mod foo { mod foo { mod bar { trait Foo { - type Item: Bar< + type Item where Self: Bar< Self, >; @@ -800,7 +842,7 @@ mod foo { } impl Foo for $0T { - type Item: Bar< + type Item where Self: Bar< Self, >; @@ -894,7 +936,7 @@ impl Foo for $0T1 where Self::Owned: Default, { - type X: Sync; + type X; fn foo(&self, x: Self::X) -> T { todo!() @@ -943,7 +985,7 @@ where Self: ToOwned, Self::Owned: Default, { - type X: Sync; + type X; fn foo(&self, x: Self::X) -> T { todo!() @@ -980,7 +1022,7 @@ trait Foo { } impl Foo for $0T1 { - type X: Sync; + type X; fn foo(&self, x: Self::X) -> T { todo!() @@ -1017,7 +1059,7 @@ trait Foo { } impl Foo for $0T { - type X: Sync; + type X; fn foo(&self, x: Self::X) -> i32 { todo!()