Skip to content

Commit 7f226fc

Browse files
committed
Auto merge of rust-lang#12324 - jonas-schievink:rm-attribute, r=jonas-schievink
feat: Revert the "Add attribute" assist Reverts rust-lang/rust-analyzer#12296, as the added indirection and "assist noise" (the assist has to trigger inside the body of an item to match what the "Add `#[derive]`" does) makes this not really pull its weight over just using attribute completions. Keeps the changes to "Add getter". `#[must_use]` can be applied using the attribute completions.
2 parents 4bad195 + e52d463 commit 7f226fc

File tree

6 files changed

+158
-226
lines changed

6 files changed

+158
-226
lines changed

crates/ide-assists/src/handlers/add_attribute.rs

-196
This file was deleted.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,132 @@
1+
use syntax::{
2+
ast::{self, AstNode, HasAttrs},
3+
SyntaxKind::{COMMENT, WHITESPACE},
4+
TextSize,
5+
};
6+
7+
use crate::{AssistContext, AssistId, AssistKind, Assists};
8+
9+
// Assist: generate_derive
10+
//
11+
// Adds a new `#[derive()]` clause to a struct or enum.
12+
//
13+
// ```
14+
// struct Point {
15+
// x: u32,
16+
// y: u32,$0
17+
// }
18+
// ```
19+
// ->
20+
// ```
21+
// #[derive($0)]
22+
// struct Point {
23+
// x: u32,
24+
// y: u32,
25+
// }
26+
// ```
27+
pub(crate) fn generate_derive(acc: &mut Assists, ctx: &AssistContext) -> Option<()> {
28+
let cap = ctx.config.snippet_cap?;
29+
let nominal = ctx.find_node_at_offset::<ast::Adt>()?;
30+
let node_start = derive_insertion_offset(&nominal)?;
31+
let target = nominal.syntax().text_range();
32+
acc.add(
33+
AssistId("generate_derive", AssistKind::Generate),
34+
"Add `#[derive]`",
35+
target,
36+
|builder| {
37+
let derive_attr = nominal
38+
.attrs()
39+
.filter_map(|x| x.as_simple_call())
40+
.filter(|(name, _arg)| name == "derive")
41+
.map(|(_name, arg)| arg)
42+
.next();
43+
match derive_attr {
44+
None => {
45+
builder.insert_snippet(cap, node_start, "#[derive($0)]\n");
46+
}
47+
Some(tt) => {
48+
// Just move the cursor.
49+
builder.insert_snippet(
50+
cap,
51+
tt.syntax().text_range().end() - TextSize::of(')'),
52+
"$0",
53+
)
54+
}
55+
};
56+
},
57+
)
58+
}
59+
60+
// Insert `derive` after doc comments.
61+
fn derive_insertion_offset(nominal: &ast::Adt) -> Option<TextSize> {
62+
let non_ws_child = nominal
63+
.syntax()
64+
.children_with_tokens()
65+
.find(|it| it.kind() != COMMENT && it.kind() != WHITESPACE)?;
66+
Some(non_ws_child.text_range().start())
67+
}
68+
69+
#[cfg(test)]
70+
mod tests {
71+
use crate::tests::{check_assist, check_assist_target};
72+
73+
use super::*;
74+
75+
#[test]
76+
fn add_derive_new() {
77+
check_assist(
78+
generate_derive,
79+
"struct Foo { a: i32, $0}",
80+
"#[derive($0)]\nstruct Foo { a: i32, }",
81+
);
82+
check_assist(
83+
generate_derive,
84+
"struct Foo { $0 a: i32, }",
85+
"#[derive($0)]\nstruct Foo { a: i32, }",
86+
);
87+
}
88+
89+
#[test]
90+
fn add_derive_existing() {
91+
check_assist(
92+
generate_derive,
93+
"#[derive(Clone)]\nstruct Foo { a: i32$0, }",
94+
"#[derive(Clone$0)]\nstruct Foo { a: i32, }",
95+
);
96+
}
97+
98+
#[test]
99+
fn add_derive_new_with_doc_comment() {
100+
check_assist(
101+
generate_derive,
102+
"
103+
/// `Foo` is a pretty important struct.
104+
/// It does stuff.
105+
struct Foo { a: i32$0, }
106+
",
107+
"
108+
/// `Foo` is a pretty important struct.
109+
/// It does stuff.
110+
#[derive($0)]
111+
struct Foo { a: i32, }
112+
",
113+
);
114+
}
115+
116+
#[test]
117+
fn add_derive_target() {
118+
check_assist_target(
119+
generate_derive,
120+
"
121+
struct SomeThingIrrelevant;
122+
/// `Foo` is a pretty important struct.
123+
/// It does stuff.
124+
struct Foo { a: i32$0, }
125+
struct EvenMoreIrrelevant;
126+
",
127+
"/// `Foo` is a pretty important struct.
128+
/// It does stuff.
129+
struct Foo { a: i32, }",
130+
);
131+
}
132+
}

crates/ide-assists/src/lib.rs

+3-3
Original file line numberDiff line numberDiff line change
@@ -106,8 +106,6 @@ mod handlers {
106106
mod add_explicit_type;
107107
mod add_lifetime_to_type;
108108
mod add_missing_impl_members;
109-
mod add_missing_match_arms;
110-
mod add_attribute;
111109
mod add_turbo_fish;
112110
mod apply_demorgan;
113111
mod auto_import;
@@ -128,6 +126,7 @@ mod handlers {
128126
mod extract_struct_from_enum_variant;
129127
mod extract_type_alias;
130128
mod extract_variable;
129+
mod add_missing_match_arms;
131130
mod fix_visibility;
132131
mod flip_binexpr;
133132
mod flip_comma;
@@ -136,6 +135,7 @@ mod handlers {
136135
mod generate_default_from_enum_variant;
137136
mod generate_default_from_new;
138137
mod generate_deref;
138+
mod generate_derive;
139139
mod generate_documentation_template;
140140
mod generate_enum_is_method;
141141
mod generate_enum_projection_method;
@@ -191,7 +191,6 @@ mod handlers {
191191
pub(crate) fn all() -> &'static [Handler] {
192192
&[
193193
// These are alphabetic for the foolish consistency
194-
add_attribute::add_attribute,
195194
add_explicit_type::add_explicit_type,
196195
add_missing_match_arms::add_missing_match_arms,
197196
add_lifetime_to_type::add_lifetime_to_type,
@@ -222,6 +221,7 @@ mod handlers {
222221
generate_constant::generate_constant,
223222
generate_default_from_enum_variant::generate_default_from_enum_variant,
224223
generate_default_from_new::generate_default_from_new,
224+
generate_derive::generate_derive,
225225
generate_documentation_template::generate_documentation_template,
226226
generate_documentation_template::generate_doc_example,
227227
generate_enum_is_method::generate_enum_is_method,

crates/ide-assists/src/tests.rs

-1
Original file line numberDiff line numberDiff line change
@@ -251,7 +251,6 @@ pub fn test_some_range(a: int) -> bool {
251251
Extract into variable
252252
Extract into function
253253
Replace if let with match
254-
Add attribute
255254
"#]]
256255
.assert_eq(&expected);
257256
}

0 commit comments

Comments
 (0)