@@ -13,7 +13,8 @@ use serde::de::{
13
13
use serde:: Deserialize ;
14
14
use std:: any:: TypeId ;
15
15
use std:: fmt;
16
- use std:: fmt:: Formatter ;
16
+ use std:: fmt:: { Debug , Display , Formatter } ;
17
+ use std:: slice:: Iter ;
17
18
18
19
pub trait DeserializeValue {
19
20
fn deserialize (
@@ -25,7 +26,7 @@ pub trait DeserializeValue {
25
26
trait StructLikeInfo {
26
27
fn get_name ( & self ) -> & str ;
27
28
fn get_field ( & self , name : & str ) -> Option < & NamedField > ;
28
- fn get_field_names ( & self ) -> & [ & ' static str ] ;
29
+ fn iter_fields ( & self ) -> Iter < ' _ , NamedField > ;
29
30
}
30
31
31
32
trait TupleLikeInfo {
@@ -43,8 +44,8 @@ impl StructLikeInfo for StructInfo {
43
44
self . field ( name)
44
45
}
45
46
46
- fn get_field_names ( & self ) -> & [ & ' static str ] {
47
- self . field_names ( )
47
+ fn iter_fields ( & self ) -> Iter < ' _ , NamedField > {
48
+ self . iter ( )
48
49
}
49
50
}
50
51
@@ -57,8 +58,8 @@ impl StructLikeInfo for StructVariantInfo {
57
58
self . field ( name)
58
59
}
59
60
60
- fn get_field_names ( & self ) -> & [ & ' static str ] {
61
- self . field_names ( )
61
+ fn iter_fields ( & self ) -> Iter < ' _ , NamedField > {
62
+ self . iter ( )
62
63
}
63
64
}
64
65
@@ -90,6 +91,39 @@ impl TupleLikeInfo for TupleVariantInfo {
90
91
}
91
92
}
92
93
94
+ /// A debug struct used for error messages that displays a list of expected values.
95
+ ///
96
+ /// # Example
97
+ ///
98
+ /// ```ignore
99
+ /// let expected = vec!["foo", "bar", "baz"];
100
+ /// assert_eq!("`foo`, `bar`, `baz`", format!("{}", ExpectedValues(expected)));
101
+ /// ```
102
+ struct ExpectedValues < TIntoIter , TIter , TItem > ( TIntoIter )
103
+ where
104
+ TIntoIter : IntoIterator < IntoIter = TIter > + Clone ,
105
+ TIter : Iterator < Item = TItem > + ExactSizeIterator ,
106
+ TItem : Display ;
107
+
108
+ impl < TIntoIter , TIter , TItem > Debug for ExpectedValues < TIntoIter , TIter , TItem >
109
+ where
110
+ TIntoIter : IntoIterator < IntoIter = TIter > + Clone ,
111
+ TIter : Iterator < Item = TItem > + ExactSizeIterator ,
112
+ TItem : Display ,
113
+ {
114
+ fn fmt ( & self , f : & mut Formatter < ' _ > ) -> fmt:: Result {
115
+ let iter = self . 0 . clone ( ) . into_iter ( ) ;
116
+ let len = iter. len ( ) ;
117
+ for ( index, item) in iter. enumerate ( ) {
118
+ write ! ( f, "`{}`" , item) ?;
119
+ if index < len - 1 {
120
+ write ! ( f, ", " ) ?;
121
+ }
122
+ }
123
+ Ok ( ( ) )
124
+ }
125
+ }
126
+
93
127
/// Represents a simple reflected identifier.
94
128
#[ derive( Debug , Clone , Eq , PartialEq ) ]
95
129
struct Ident ( String ) ;
@@ -255,7 +289,8 @@ impl<'a, 'de> DeserializeSeed<'de> for TypedReflectDeserializer<'a> {
255
289
TypeInfo :: Struct ( struct_info) => {
256
290
let mut dynamic_struct = deserializer. deserialize_struct (
257
291
struct_info. name ( ) ,
258
- struct_info. field_names ( ) ,
292
+ // Field names are mainly just a hint, we don't necessarily need to store and pass that data
293
+ & [ ] ,
259
294
StructVisitor {
260
295
struct_info,
261
296
registry : self . registry ,
@@ -324,7 +359,8 @@ impl<'a, 'de> DeserializeSeed<'de> for TypedReflectDeserializer<'a> {
324
359
} else {
325
360
deserializer. deserialize_enum (
326
361
enum_info. name ( ) ,
327
- enum_info. variant_names ( ) ,
362
+ // Variant names are mainly just a hint, we don't necessarily need to store and pass that data
363
+ & [ ] ,
328
364
EnumVisitor {
329
365
enum_info,
330
366
registry : self . registry ,
@@ -583,15 +619,20 @@ impl<'a, 'de> Visitor<'de> for EnumVisitor<'a> {
583
619
{
584
620
let mut dynamic_enum = DynamicEnum :: default ( ) ;
585
621
let ( Ident ( variant_name) , variant) = data. variant ( ) . unwrap ( ) ;
586
- let variant_info = self
587
- . enum_info
588
- . variant ( & variant_name)
589
- . ok_or_else ( || Error :: unknown_variant ( & variant_name, self . enum_info . variant_names ( ) ) ) ?;
622
+ let variant_info = self . enum_info . variant ( & variant_name) . ok_or_else ( || {
623
+ let names = self . enum_info . iter ( ) . map ( |variant| variant. name ( ) ) ;
624
+ Error :: custom ( format_args ! (
625
+ "unknown variant `{}`, expected one of {:?}" ,
626
+ variant_name,
627
+ ExpectedValues ( names)
628
+ ) )
629
+ } ) ?;
590
630
let value: DynamicVariant = match variant_info {
591
631
VariantInfo :: Unit ( ..) => variant. unit_variant ( ) ?. into ( ) ,
592
632
VariantInfo :: Struct ( struct_info) => variant
593
633
. struct_variant (
594
- struct_info. field_names ( ) ,
634
+ // Field names are mainly just a hint, we don't necessarily need to store and pass that data
635
+ & [ ] ,
595
636
StructVariantVisitor {
596
637
struct_info,
597
638
registry : self . registry ,
@@ -727,9 +768,14 @@ where
727
768
{
728
769
let mut dynamic_struct = DynamicStruct :: default ( ) ;
729
770
while let Some ( Ident ( key) ) = map. next_key :: < Ident > ( ) ? {
730
- let field = info
731
- . get_field ( & key)
732
- . ok_or_else ( || Error :: unknown_field ( & key, info. get_field_names ( ) ) ) ?;
771
+ let field = info. get_field ( & key) . ok_or_else ( || {
772
+ let fields = info. iter_fields ( ) . map ( |field| field. name ( ) ) ;
773
+ Error :: custom ( format_args ! (
774
+ "unknown field `{}`, expected one of {:?}" ,
775
+ key,
776
+ ExpectedValues ( fields)
777
+ ) )
778
+ } ) ?;
733
779
let registration = get_registration ( field. type_id ( ) , field. type_name ( ) , registry) ?;
734
780
let value = map. next_value_seed ( TypedReflectDeserializer {
735
781
registration,
0 commit comments