1use crate::{
2 serde::{
3 de::{
4 error_utils::make_custom_error,
5 helpers::ExpectedValues,
6 registration_utils::try_get_registration,
7 struct_utils::{visit_struct, visit_struct_seq},
8 tuple_utils::{visit_tuple, TupleLikeInfo},
9 },
10 TypedReflectDeserializer,
11 },
12 DynamicEnum, DynamicStruct, DynamicTuple, DynamicVariant, EnumInfo, StructVariantInfo,
13 TupleVariantInfo, TypeRegistration, TypeRegistry, VariantInfo,
14};
15use core::{fmt, fmt::Formatter};
16use serde::de::{DeserializeSeed, EnumAccess, Error, MapAccess, SeqAccess, VariantAccess, Visitor};
17
18use super::ReflectDeserializerProcessor;
19
20pub(super) struct EnumVisitor<'a, P> {
24 pub enum_info: &'static EnumInfo,
25 pub registration: &'a TypeRegistration,
26 pub registry: &'a TypeRegistry,
27 pub processor: Option<&'a mut P>,
28}
29
30impl<'de, P: ReflectDeserializerProcessor> Visitor<'de> for EnumVisitor<'_, P> {
31 type Value = DynamicEnum;
32
33 fn expecting(&self, formatter: &mut Formatter) -> fmt::Result {
34 formatter.write_str("reflected enum value")
35 }
36
37 fn visit_enum<A>(self, data: A) -> Result<Self::Value, A::Error>
38 where
39 A: EnumAccess<'de>,
40 {
41 let mut dynamic_enum = DynamicEnum::default();
42 let (variant_info, variant) = data.variant_seed(VariantDeserializer {
43 enum_info: self.enum_info,
44 })?;
45
46 let value: DynamicVariant = match variant_info {
47 VariantInfo::Unit(..) => variant.unit_variant()?.into(),
48 VariantInfo::Struct(struct_info) => variant
49 .struct_variant(
50 struct_info.field_names(),
51 StructVariantVisitor {
52 struct_info,
53 registration: self.registration,
54 registry: self.registry,
55 processor: self.processor,
56 },
57 )?
58 .into(),
59 VariantInfo::Tuple(tuple_info) if tuple_info.field_len() == 1 => {
60 let registration = try_get_registration(
61 *TupleLikeInfo::field_at(tuple_info, 0)?.ty(),
62 self.registry,
63 )?;
64 let value =
65 variant.newtype_variant_seed(TypedReflectDeserializer::new_internal(
66 registration,
67 self.registry,
68 self.processor,
69 ))?;
70 let mut dynamic_tuple = DynamicTuple::default();
71 dynamic_tuple.insert_boxed(value);
72 dynamic_tuple.into()
73 }
74 VariantInfo::Tuple(tuple_info) => variant
75 .tuple_variant(
76 tuple_info.field_len(),
77 TupleVariantVisitor {
78 tuple_info,
79 registration: self.registration,
80 registry: self.registry,
81 processor: self.processor,
82 },
83 )?
84 .into(),
85 };
86 let variant_name = variant_info.name();
87 let variant_index = self
88 .enum_info
89 .index_of(variant_name)
90 .expect("variant should exist");
91 dynamic_enum.set_variant_with_index(variant_index, variant_name, value);
92 Ok(dynamic_enum)
93 }
94}
95
96struct VariantDeserializer {
97 enum_info: &'static EnumInfo,
98}
99
100impl<'de> DeserializeSeed<'de> for VariantDeserializer {
101 type Value = &'static VariantInfo;
102
103 fn deserialize<D>(self, deserializer: D) -> Result<Self::Value, D::Error>
104 where
105 D: serde::Deserializer<'de>,
106 {
107 struct VariantVisitor(&'static EnumInfo);
108
109 impl<'de> Visitor<'de> for VariantVisitor {
110 type Value = &'static VariantInfo;
111
112 fn expecting(&self, formatter: &mut Formatter) -> fmt::Result {
113 formatter.write_str("expected either a variant index or variant name")
114 }
115
116 fn visit_u32<E>(self, variant_index: u32) -> Result<Self::Value, E>
117 where
118 E: Error,
119 {
120 self.0.variant_at(variant_index as usize).ok_or_else(|| {
121 make_custom_error(format_args!(
122 "no variant found at index `{}` on enum `{}`",
123 variant_index,
124 self.0.type_path()
125 ))
126 })
127 }
128
129 fn visit_str<E>(self, variant_name: &str) -> Result<Self::Value, E>
130 where
131 E: Error,
132 {
133 self.0.variant(variant_name).ok_or_else(|| {
134 let names = self.0.iter().map(VariantInfo::name);
135 make_custom_error(format_args!(
136 "unknown variant `{}`, expected one of {:?}",
137 variant_name,
138 ExpectedValues::from_iter(names)
139 ))
140 })
141 }
142 }
143
144 deserializer.deserialize_identifier(VariantVisitor(self.enum_info))
145 }
146}
147
148struct StructVariantVisitor<'a, P> {
149 struct_info: &'static StructVariantInfo,
150 registration: &'a TypeRegistration,
151 registry: &'a TypeRegistry,
152 processor: Option<&'a mut P>,
153}
154
155impl<'de, P: ReflectDeserializerProcessor> Visitor<'de> for StructVariantVisitor<'_, P> {
156 type Value = DynamicStruct;
157
158 fn expecting(&self, formatter: &mut Formatter) -> fmt::Result {
159 formatter.write_str("reflected struct variant value")
160 }
161
162 fn visit_seq<A>(self, mut seq: A) -> Result<Self::Value, A::Error>
163 where
164 A: SeqAccess<'de>,
165 {
166 visit_struct_seq(
167 &mut seq,
168 self.struct_info,
169 self.registration,
170 self.registry,
171 self.processor,
172 )
173 }
174
175 fn visit_map<V>(self, mut map: V) -> Result<Self::Value, V::Error>
176 where
177 V: MapAccess<'de>,
178 {
179 visit_struct(
180 &mut map,
181 self.struct_info,
182 self.registration,
183 self.registry,
184 self.processor,
185 )
186 }
187}
188
189struct TupleVariantVisitor<'a, P> {
190 tuple_info: &'static TupleVariantInfo,
191 registration: &'a TypeRegistration,
192 registry: &'a TypeRegistry,
193 processor: Option<&'a mut P>,
194}
195
196impl<'de, P: ReflectDeserializerProcessor> Visitor<'de> for TupleVariantVisitor<'_, P> {
197 type Value = DynamicTuple;
198
199 fn expecting(&self, formatter: &mut Formatter) -> fmt::Result {
200 formatter.write_str("reflected tuple variant value")
201 }
202
203 fn visit_seq<V>(self, mut seq: V) -> Result<Self::Value, V::Error>
204 where
205 V: SeqAccess<'de>,
206 {
207 visit_tuple(
208 &mut seq,
209 self.tuple_info,
210 self.registration,
211 self.registry,
212 self.processor,
213 )
214 }
215}