diff options
Diffstat (limited to 'crates/ide/src/diagnostics/field_shorthand.rs')
-rw-r--r-- | crates/ide/src/diagnostics/field_shorthand.rs | 200 |
1 files changed, 0 insertions, 200 deletions
diff --git a/crates/ide/src/diagnostics/field_shorthand.rs b/crates/ide/src/diagnostics/field_shorthand.rs deleted file mode 100644 index 01bd2dba6..000000000 --- a/crates/ide/src/diagnostics/field_shorthand.rs +++ /dev/null | |||
@@ -1,200 +0,0 @@ | |||
1 | //! Suggests shortening `Foo { field: field }` to `Foo { field }` in both | ||
2 | //! expressions and patterns. | ||
3 | |||
4 | use ide_db::{base_db::FileId, source_change::SourceChange}; | ||
5 | use syntax::{ast, match_ast, AstNode, SyntaxNode}; | ||
6 | use text_edit::TextEdit; | ||
7 | |||
8 | use crate::{diagnostics::fix, Diagnostic}; | ||
9 | |||
10 | pub(super) fn check(acc: &mut Vec<Diagnostic>, file_id: FileId, node: &SyntaxNode) { | ||
11 | match_ast! { | ||
12 | match node { | ||
13 | ast::RecordExpr(it) => check_expr_field_shorthand(acc, file_id, it), | ||
14 | ast::RecordPat(it) => check_pat_field_shorthand(acc, file_id, it), | ||
15 | _ => () | ||
16 | } | ||
17 | }; | ||
18 | } | ||
19 | |||
20 | fn check_expr_field_shorthand( | ||
21 | acc: &mut Vec<Diagnostic>, | ||
22 | file_id: FileId, | ||
23 | record_expr: ast::RecordExpr, | ||
24 | ) { | ||
25 | let record_field_list = match record_expr.record_expr_field_list() { | ||
26 | Some(it) => it, | ||
27 | None => return, | ||
28 | }; | ||
29 | for record_field in record_field_list.fields() { | ||
30 | let (name_ref, expr) = match record_field.name_ref().zip(record_field.expr()) { | ||
31 | Some(it) => it, | ||
32 | None => continue, | ||
33 | }; | ||
34 | |||
35 | let field_name = name_ref.syntax().text().to_string(); | ||
36 | let field_expr = expr.syntax().text().to_string(); | ||
37 | let field_name_is_tup_index = name_ref.as_tuple_field().is_some(); | ||
38 | if field_name != field_expr || field_name_is_tup_index { | ||
39 | continue; | ||
40 | } | ||
41 | |||
42 | let mut edit_builder = TextEdit::builder(); | ||
43 | edit_builder.delete(record_field.syntax().text_range()); | ||
44 | edit_builder.insert(record_field.syntax().text_range().start(), field_name); | ||
45 | let edit = edit_builder.finish(); | ||
46 | |||
47 | let field_range = record_field.syntax().text_range(); | ||
48 | acc.push( | ||
49 | Diagnostic::hint(field_range, "Shorthand struct initialization".to_string()) | ||
50 | .with_fixes(Some(vec![fix( | ||
51 | "use_expr_field_shorthand", | ||
52 | "Use struct shorthand initialization", | ||
53 | SourceChange::from_text_edit(file_id, edit), | ||
54 | field_range, | ||
55 | )])), | ||
56 | ); | ||
57 | } | ||
58 | } | ||
59 | |||
60 | fn check_pat_field_shorthand( | ||
61 | acc: &mut Vec<Diagnostic>, | ||
62 | file_id: FileId, | ||
63 | record_pat: ast::RecordPat, | ||
64 | ) { | ||
65 | let record_pat_field_list = match record_pat.record_pat_field_list() { | ||
66 | Some(it) => it, | ||
67 | None => return, | ||
68 | }; | ||
69 | for record_pat_field in record_pat_field_list.fields() { | ||
70 | let (name_ref, pat) = match record_pat_field.name_ref().zip(record_pat_field.pat()) { | ||
71 | Some(it) => it, | ||
72 | None => continue, | ||
73 | }; | ||
74 | |||
75 | let field_name = name_ref.syntax().text().to_string(); | ||
76 | let field_pat = pat.syntax().text().to_string(); | ||
77 | let field_name_is_tup_index = name_ref.as_tuple_field().is_some(); | ||
78 | if field_name != field_pat || field_name_is_tup_index { | ||
79 | continue; | ||
80 | } | ||
81 | |||
82 | let mut edit_builder = TextEdit::builder(); | ||
83 | edit_builder.delete(record_pat_field.syntax().text_range()); | ||
84 | edit_builder.insert(record_pat_field.syntax().text_range().start(), field_name); | ||
85 | let edit = edit_builder.finish(); | ||
86 | |||
87 | let field_range = record_pat_field.syntax().text_range(); | ||
88 | acc.push(Diagnostic::hint(field_range, "Shorthand struct pattern".to_string()).with_fixes( | ||
89 | Some(vec![fix( | ||
90 | "use_pat_field_shorthand", | ||
91 | "Use struct field shorthand", | ||
92 | SourceChange::from_text_edit(file_id, edit), | ||
93 | field_range, | ||
94 | )]), | ||
95 | )); | ||
96 | } | ||
97 | } | ||
98 | |||
99 | #[cfg(test)] | ||
100 | mod tests { | ||
101 | use crate::diagnostics::tests::{check_fix, check_no_diagnostics}; | ||
102 | |||
103 | #[test] | ||
104 | fn test_check_expr_field_shorthand() { | ||
105 | check_no_diagnostics( | ||
106 | r#" | ||
107 | struct A { a: &'static str } | ||
108 | fn main() { A { a: "hello" } } | ||
109 | "#, | ||
110 | ); | ||
111 | check_no_diagnostics( | ||
112 | r#" | ||
113 | struct A(usize); | ||
114 | fn main() { A { 0: 0 } } | ||
115 | "#, | ||
116 | ); | ||
117 | |||
118 | check_fix( | ||
119 | r#" | ||
120 | struct A { a: &'static str } | ||
121 | fn main() { | ||
122 | let a = "haha"; | ||
123 | A { a$0: a } | ||
124 | } | ||
125 | "#, | ||
126 | r#" | ||
127 | struct A { a: &'static str } | ||
128 | fn main() { | ||
129 | let a = "haha"; | ||
130 | A { a } | ||
131 | } | ||
132 | "#, | ||
133 | ); | ||
134 | |||
135 | check_fix( | ||
136 | r#" | ||
137 | struct A { a: &'static str, b: &'static str } | ||
138 | fn main() { | ||
139 | let a = "haha"; | ||
140 | let b = "bb"; | ||
141 | A { a$0: a, b } | ||
142 | } | ||
143 | "#, | ||
144 | r#" | ||
145 | struct A { a: &'static str, b: &'static str } | ||
146 | fn main() { | ||
147 | let a = "haha"; | ||
148 | let b = "bb"; | ||
149 | A { a, b } | ||
150 | } | ||
151 | "#, | ||
152 | ); | ||
153 | } | ||
154 | |||
155 | #[test] | ||
156 | fn test_check_pat_field_shorthand() { | ||
157 | check_no_diagnostics( | ||
158 | r#" | ||
159 | struct A { a: &'static str } | ||
160 | fn f(a: A) { let A { a: hello } = a; } | ||
161 | "#, | ||
162 | ); | ||
163 | check_no_diagnostics( | ||
164 | r#" | ||
165 | struct A(usize); | ||
166 | fn f(a: A) { let A { 0: 0 } = a; } | ||
167 | "#, | ||
168 | ); | ||
169 | |||
170 | check_fix( | ||
171 | r#" | ||
172 | struct A { a: &'static str } | ||
173 | fn f(a: A) { | ||
174 | let A { a$0: a } = a; | ||
175 | } | ||
176 | "#, | ||
177 | r#" | ||
178 | struct A { a: &'static str } | ||
179 | fn f(a: A) { | ||
180 | let A { a } = a; | ||
181 | } | ||
182 | "#, | ||
183 | ); | ||
184 | |||
185 | check_fix( | ||
186 | r#" | ||
187 | struct A { a: &'static str, b: &'static str } | ||
188 | fn f(a: A) { | ||
189 | let A { a$0: a, b } = a; | ||
190 | } | ||
191 | "#, | ||
192 | r#" | ||
193 | struct A { a: &'static str, b: &'static str } | ||
194 | fn f(a: A) { | ||
195 | let A { a, b } = a; | ||
196 | } | ||
197 | "#, | ||
198 | ); | ||
199 | } | ||
200 | } | ||