@@ -7,7 +7,7 @@ use ide_db::{
7
7
helpers:: mod_path_to_ast,
8
8
imports:: insert_use:: { insert_use, ImportScope } ,
9
9
source_change:: SourceChangeBuilder ,
10
- RootDatabase ,
10
+ FxHashMap , RootDatabase ,
11
11
} ;
12
12
use itertools:: Itertools ;
13
13
use stdx:: { format_to, never} ;
@@ -22,15 +22,21 @@ use crate::{fix, Diagnostic, DiagnosticCode, DiagnosticsConfig, Severity};
22
22
#[ derive( Default ) ]
23
23
struct State {
24
24
result : String ,
25
- struct_counts : usize ,
26
25
has_serialize : bool ,
27
26
has_deserialize : bool ,
27
+ names : FxHashMap < String , usize > ,
28
28
}
29
29
30
30
impl State {
31
- fn generate_new_name ( & mut self ) -> ast:: Name {
32
- self . struct_counts += 1 ;
33
- make:: name ( & format ! ( "Struct{}" , self . struct_counts) )
31
+ fn generate_new_name ( & mut self , name : & str ) -> ast:: Name {
32
+ let name = stdx:: to_camel_case ( name) ;
33
+ let count = if let Some ( count) = self . names . get ( & name) {
34
+ * count
35
+ } else {
36
+ self . names . insert ( name. clone ( ) , 1 ) ;
37
+ 1
38
+ } ;
39
+ make:: name ( & format ! ( "{}{}" , name, count) )
34
40
}
35
41
36
42
fn serde_derive ( & self ) -> String {
@@ -52,36 +58,42 @@ impl State {
52
58
}
53
59
}
54
60
55
- fn build_struct ( & mut self , value : & serde_json:: Map < String , serde_json:: Value > ) -> ast:: Type {
56
- let name = self . generate_new_name ( ) ;
61
+ fn build_struct (
62
+ & mut self ,
63
+ name : & str ,
64
+ value : & serde_json:: Map < String , serde_json:: Value > ,
65
+ ) -> ast:: Type {
66
+ let name = self . generate_new_name ( name) ;
57
67
let ty = make:: ty ( & name. to_string ( ) ) ;
58
68
let strukt = make:: struct_ (
59
69
None ,
60
70
name,
61
71
None ,
62
72
make:: record_field_list ( value. iter ( ) . sorted_unstable_by_key ( |x| x. 0 ) . map (
63
- |( name, value) | make:: record_field ( None , make:: name ( name) , self . type_of ( value) ) ,
73
+ |( name, value) | {
74
+ make:: record_field ( None , make:: name ( name) , self . type_of ( name, value) )
75
+ } ,
64
76
) )
65
77
. into ( ) ,
66
78
) ;
67
79
format_to ! ( self . result, "{}{}\n " , self . serde_derive( ) , strukt) ;
68
80
ty
69
81
}
70
82
71
- fn type_of ( & mut self , value : & serde_json:: Value ) -> ast:: Type {
83
+ fn type_of ( & mut self , name : & str , value : & serde_json:: Value ) -> ast:: Type {
72
84
match value {
73
85
serde_json:: Value :: Null => make:: ty_unit ( ) ,
74
86
serde_json:: Value :: Bool ( _) => make:: ty ( "bool" ) ,
75
87
serde_json:: Value :: Number ( it) => make:: ty ( if it. is_i64 ( ) { "i64" } else { "f64" } ) ,
76
88
serde_json:: Value :: String ( _) => make:: ty ( "String" ) ,
77
89
serde_json:: Value :: Array ( it) => {
78
90
let ty = match it. iter ( ) . next ( ) {
79
- Some ( x) => self . type_of ( x) ,
91
+ Some ( x) => self . type_of ( name , x) ,
80
92
None => make:: ty_placeholder ( ) ,
81
93
} ;
82
94
make:: ty ( & format ! ( "Vec<{ty}>" ) )
83
95
}
84
- serde_json:: Value :: Object ( x) => self . build_struct ( x) ,
96
+ serde_json:: Value :: Object ( x) => self . build_struct ( name , x) ,
85
97
}
86
98
}
87
99
}
@@ -113,7 +125,7 @@ pub(crate) fn json_in_items(
113
125
let serialize_resolved = scope_resolve ( "::serde::Serialize" ) ;
114
126
state. has_deserialize = deserialize_resolved. is_some ( ) ;
115
127
state. has_serialize = serialize_resolved. is_some ( ) ;
116
- state. build_struct ( & it) ;
128
+ state. build_struct ( "Root" , & it) ;
117
129
edit. insert ( range. start ( ) , state. result ) ;
118
130
acc. push (
119
131
Diagnostic :: new (
@@ -218,7 +230,7 @@ mod tests {
218
230
}
219
231
220
232
#[derive(Serialize)]
221
- struct Struct1 { bar: f64, bay: i64, baz: (), r#box: bool, foo: String }
233
+ struct Root1 { bar: f64, bay: i64, baz: (), r#box: bool, foo: String }
222
234
223
235
"# ,
224
236
) ;
@@ -237,9 +249,9 @@ mod tests {
237
249
}
238
250
"# ,
239
251
r#"
240
- struct Struct3 { }
241
- struct Struct2 { kind: String, value: Struct3 }
242
- struct Struct1 { bar: Struct2 , foo: String }
252
+ struct Value1 { }
253
+ struct Bar1 { kind: String, value: Value1 }
254
+ struct Root1 { bar: Bar1 , foo: String }
243
255
244
256
"# ,
245
257
) ;
@@ -276,9 +288,9 @@ mod tests {
276
288
use serde::Deserialize;
277
289
278
290
#[derive(Serialize, Deserialize)]
279
- struct Struct2 { x: i64, y: i64 }
291
+ struct OfObject1 { x: i64, y: i64 }
280
292
#[derive(Serialize, Deserialize)]
281
- struct Struct1 { empty: Vec<_>, nested: Vec<Vec<Vec<i64>>>, of_object: Vec<Struct2 >, of_string: Vec<String> }
293
+ struct Root1 { empty: Vec<_>, nested: Vec<Vec<Vec<i64>>>, of_object: Vec<OfObject1 >, of_string: Vec<String> }
282
294
283
295
"# ,
284
296
) ;
0 commit comments