@@ -18,7 +18,6 @@ use ide_db::{
18
18
imports:: insert_use:: { ImportGranularity , InsertUseConfig , PrefixKind } ,
19
19
SnippetCap ,
20
20
} ;
21
- use indexmap:: IndexMap ;
22
21
use itertools:: Itertools ;
23
22
use lsp_types:: { ClientCapabilities , MarkupKind } ;
24
23
use paths:: { Utf8Path , Utf8PathBuf } ;
@@ -382,8 +381,7 @@ config_data! {
382
381
/// Enables completions of private items and fields that are defined in the current workspace even if they are not visible at the current position.
383
382
completion_privateEditable_enable: bool = false ,
384
383
/// Custom completion snippets.
385
- // NOTE: we use IndexMap for deterministic serialization ordering
386
- completion_snippets_custom: IndexMap <String , SnippetDef > = serde_json:: from_str( r#"{
384
+ completion_snippets_custom: FxHashMap <String , SnippetDef > = serde_json:: from_str( r#"{
387
385
"Arc::new": {
388
386
"postfix": "arc",
389
387
"body": "Arc::new(${receiver})",
@@ -1243,7 +1241,19 @@ impl Config {
1243
1241
}
1244
1242
1245
1243
pub fn json_schema ( ) -> serde_json:: Value {
1246
- FullConfigInput :: json_schema ( )
1244
+ let mut s = FullConfigInput :: json_schema ( ) ;
1245
+
1246
+ fn sort_objects_by_field ( json : & mut serde_json:: Value ) {
1247
+ if let serde_json:: Value :: Object ( object) = json {
1248
+ let old = std:: mem:: take ( object) ;
1249
+ old. into_iter ( ) . sorted_by ( |( k, _) , ( k2, _) | k. cmp ( k2) ) . for_each ( |( k, mut v) | {
1250
+ sort_objects_by_field ( & mut v) ;
1251
+ object. insert ( k, v) ;
1252
+ } ) ;
1253
+ }
1254
+ }
1255
+ sort_objects_by_field ( & mut s) ;
1256
+ s
1247
1257
}
1248
1258
1249
1259
pub fn root_path ( & self ) -> & AbsPathBuf {
@@ -2640,9 +2650,8 @@ macro_rules! _config_data {
2640
2650
2641
2651
/// All fields `Option<T>`, `None` representing fields not set in a particular JSON/TOML blob.
2642
2652
#[ allow( non_snake_case) ]
2643
- #[ derive( Clone , Serialize , Default ) ]
2653
+ #[ derive( Clone , Default ) ]
2644
2654
struct $input { $(
2645
- #[ serde( skip_serializing_if = "Option::is_none" ) ]
2646
2655
$field: Option <$ty>,
2647
2656
) * }
2648
2657
@@ -2725,7 +2734,7 @@ struct DefaultConfigData {
2725
2734
/// All of the config levels, all fields `Option<T>`, to describe fields that are actually set by
2726
2735
/// some rust-analyzer.toml file or JSON blob. An empty rust-analyzer.toml corresponds to
2727
2736
/// all fields being None.
2728
- #[ derive( Debug , Clone , Default , Serialize ) ]
2737
+ #[ derive( Debug , Clone , Default ) ]
2729
2738
struct FullConfigInput {
2730
2739
global : GlobalConfigInput ,
2731
2740
local : LocalConfigInput ,
@@ -2770,7 +2779,7 @@ impl FullConfigInput {
2770
2779
/// All of the config levels, all fields `Option<T>`, to describe fields that are actually set by
2771
2780
/// some rust-analyzer.toml file or JSON blob. An empty rust-analyzer.toml corresponds to
2772
2781
/// all fields being None.
2773
- #[ derive( Debug , Clone , Default , Serialize ) ]
2782
+ #[ derive( Debug , Clone , Default ) ]
2774
2783
struct GlobalLocalConfigInput {
2775
2784
global : GlobalConfigInput ,
2776
2785
local : LocalConfigInput ,
@@ -2932,7 +2941,7 @@ fn field_props(field: &str, ty: &str, doc: &[&str], default: &str) -> serde_json
2932
2941
"FxHashMap<Box<str>, Box<[Box<str>]>>" => set ! {
2933
2942
"type" : "object" ,
2934
2943
} ,
2935
- "IndexMap <String, SnippetDef>" => set ! {
2944
+ "FxHashMap <String, SnippetDef>" => set ! {
2936
2945
"type" : "object" ,
2937
2946
} ,
2938
2947
"FxHashMap<String, String>" => set ! {
@@ -3347,6 +3356,7 @@ mod tests {
3347
3356
#[ test]
3348
3357
fn generate_package_json_config ( ) {
3349
3358
let s = Config :: json_schema ( ) ;
3359
+
3350
3360
let schema = format ! ( "{s:#}" ) ;
3351
3361
let mut schema = schema
3352
3362
. trim_start_matches ( '[' )
0 commit comments