1use {
2 super::super::{serde::SerdeError, Ipld},
3 crate::cid::{
4 serde::{BytesToCidVisitor, CID_SERDE_PRIVATE_IDENTIFIER},
5 Cid,
6 },
7 alloc::{
8 borrow::ToOwned,
9 collections::BTreeMap,
10 format,
11 string::String,
12 vec::Vec,
13 },
14 core::{convert::TryFrom, fmt},
15 serde::{
16 de::{self, IntoDeserializer},
17 forward_to_deserialize_any,
18 Deserialize,
19 },
20};
21
22pub fn from_ipld<T>(value: Ipld) -> Result<T, SerdeError>
61where
62 T: serde::de::DeserializeOwned,
63{
64 T::deserialize(value)
65}
66
67impl<'de> de::Deserialize<'de> for Ipld {
68 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
69 where
70 D: de::Deserializer<'de>,
71 {
72 struct IpldVisitor;
73
74 impl<'de> de::Visitor<'de> for IpldVisitor {
75 type Value = Ipld;
76
77 fn expecting(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
78 fmt.write_str("any valid IPLD kind")
79 }
80
81 #[inline]
82 fn visit_str<E>(self, value: &str) -> Result<Self::Value, E>
83 where
84 E: de::Error,
85 {
86 Ok(Ipld::String(String::from(value)))
87 }
88
89 #[inline]
90 fn visit_bytes<E>(self, v: &[u8]) -> Result<Self::Value, E>
91 where
92 E: de::Error,
93 {
94 self.visit_byte_buf(v.to_owned())
95 }
96
97 #[inline]
98 fn visit_byte_buf<E>(self, v: Vec<u8>) -> Result<Self::Value, E>
99 where
100 E: de::Error,
101 {
102 Ok(Ipld::Bytes(v))
103 }
104
105 #[inline]
106 fn visit_u64<E>(self, v: u64) -> Result<Self::Value, E>
107 where
108 E: de::Error,
109 {
110 Ok(Ipld::Integer(v.into()))
111 }
112
113 #[inline]
114 fn visit_i64<E>(self, v: i64) -> Result<Self::Value, E>
115 where
116 E: de::Error,
117 {
118 Ok(Ipld::Integer(v.into()))
119 }
120
121 #[inline]
122 fn visit_i128<E>(self, v: i128) -> Result<Self::Value, E>
123 where
124 E: de::Error,
125 {
126 Ok(Ipld::Integer(v))
127 }
128
129 #[inline]
130 fn visit_f64<E>(self, v: f64) -> Result<Self::Value, E>
131 where
132 E: de::Error,
133 {
134 Ok(Ipld::Float(v))
135 }
136
137 #[inline]
138 fn visit_bool<E>(self, v: bool) -> Result<Self::Value, E>
139 where
140 E: de::Error,
141 {
142 Ok(Ipld::Bool(v))
143 }
144
145 #[inline]
146 fn visit_none<E>(self) -> Result<Self::Value, E>
147 where
148 E: de::Error,
149 {
150 Ok(Ipld::Null)
151 }
152
153 #[inline]
154 fn visit_some<D>(self, deserializer: D) -> Result<Self::Value, D::Error>
155 where
156 D: de::Deserializer<'de>,
157 {
158 Deserialize::deserialize(deserializer)
159 }
160
161 #[inline]
162 fn visit_unit<E>(self) -> Result<Self::Value, E>
163 where
164 E: de::Error,
165 {
166 Ok(Ipld::Null)
167 }
168
169 #[inline]
170 fn visit_seq<V>(self, mut visitor: V) -> Result<Self::Value, V::Error>
171 where
172 V: de::SeqAccess<'de>,
173 {
174 let mut vec = Vec::with_capacity(visitor.size_hint().unwrap_or(0));
175
176 while let Some(elem) = visitor.next_element()? {
177 vec.push(elem);
178 }
179
180 Ok(Ipld::List(vec))
181 }
182
183 #[inline]
184 fn visit_map<V>(self, mut visitor: V) -> Result<Self::Value, V::Error>
185 where
186 V: de::MapAccess<'de>,
187 {
188 let mut values = BTreeMap::new();
189
190 while let Some((key, value)) = visitor.next_entry()? {
191 let prev_value = values.insert(key, value);
192 if prev_value.is_some() {
193 return Err(de::Error::custom("Duplicate map key"));
194 }
195 }
196
197 Ok(Ipld::Map(values))
198 }
199
200 #[inline]
202 fn visit_newtype_struct<D>(
203 self,
204 deserializer: D,
205 ) -> Result<Self::Value, D::Error>
206 where
207 D: de::Deserializer<'de>,
208 {
209 deserializer
210 .deserialize_bytes(BytesToCidVisitor)
211 .map(Ipld::Link)
212 }
213 }
214
215 deserializer.deserialize_any(IpldVisitor)
216 }
217}
218
219macro_rules! impl_deserialize_integer {
220 ($ty:ident, $deserialize:ident, $visit:ident) => {
221 fn $deserialize<V: de::Visitor<'de>>(
222 self,
223 visitor: V,
224 ) -> Result<V::Value, Self::Error> {
225 match self {
226 Self::Integer(integer) => match $ty::try_from(integer) {
227 Ok(int) => visitor.$visit(int),
228 Err(_) => error(format!(
229 "`Ipld::Integer` value was bigger than `{}`",
230 stringify!($ty)
231 )),
232 },
233 _ => error(format!(
234 "Only `Ipld::Integer` can be deserialized to `{}`, input was `{:#?}`",
235 stringify!($ty),
236 self
237 )),
238 }
239 }
240 };
241}
242
243struct CidDeserializer(Cid);
248
249impl<'de> de::Deserializer<'de> for CidDeserializer {
250 type Error = SerdeError;
251
252 forward_to_deserialize_any! {
253 bool byte_buf char enum f32 f64 i8 i16 i32 i64 identifier ignored_any map newtype_struct
254 option seq str string struct tuple tuple_struct u8 u16 u32 u64 unit unit_struct
255 }
256
257 #[inline]
258 fn deserialize_any<V: de::Visitor<'de>>(
259 self,
260 _visitor: V,
261 ) -> Result<V::Value, Self::Error> {
262 error("Only bytes can be deserialized into a CID")
263 }
264
265 fn deserialize_bytes<V: de::Visitor<'de>>(
266 self,
267 visitor: V,
268 ) -> Result<V::Value, Self::Error> {
269 visitor.visit_bytes(&self.0.to_bytes())
270 }
271}
272
273impl<'de> de::Deserializer<'de> for Ipld {
282 type Error = SerdeError;
283
284 impl_deserialize_integer!(i8, deserialize_i8, visit_i8);
285
286 impl_deserialize_integer!(i16, deserialize_i16, visit_i16);
287
288 impl_deserialize_integer!(i32, deserialize_i32, visit_i32);
289
290 impl_deserialize_integer!(i64, deserialize_i64, visit_i64);
291
292 impl_deserialize_integer!(u8, deserialize_u8, visit_u8);
293
294 impl_deserialize_integer!(u16, deserialize_u16, visit_u16);
295
296 impl_deserialize_integer!(u32, deserialize_u32, visit_u32);
297
298 impl_deserialize_integer!(u64, deserialize_u64, visit_u64);
299
300 #[inline]
301 fn deserialize_any<V>(self, visitor: V) -> Result<V::Value, Self::Error>
302 where
303 V: de::Visitor<'de>,
304 {
305 match self {
306 Self::Null => visitor.visit_none(),
307 Self::Bool(bool) => visitor.visit_bool(bool),
308 Self::Integer(i128) => visitor.visit_i128(i128),
309 Self::Float(f64) => visitor.visit_f64(f64),
310 Self::String(string) => visitor.visit_str(&string),
311 Self::Bytes(bytes) => visitor.visit_bytes(&bytes),
312 Self::List(list) => visit_seq(list, visitor),
313 Self::Map(map) => visit_map(map, visitor),
314 Self::Link(cid) => visitor.visit_newtype_struct(CidDeserializer(cid)),
315 }
316 }
317
318 fn deserialize_unit<V: de::Visitor<'de>>(
319 self,
320 visitor: V,
321 ) -> Result<V::Value, Self::Error> {
322 match self {
323 Self::Null => visitor.visit_unit(),
324 _ => error(format!(
325 "Only `Ipld::Null` can be deserialized to unit, input was `{:#?}`",
326 self
327 )),
328 }
329 }
330
331 fn deserialize_bool<V: de::Visitor<'de>>(
332 self,
333 visitor: V,
334 ) -> Result<V::Value, Self::Error> {
335 match self {
336 Self::Bool(bool) => visitor.visit_bool(bool),
337 _ => error(format!(
338 "Only `Ipld::Bool` can be deserialized to bool, input was `{:#?}`",
339 self
340 )),
341 }
342 }
343
344 fn deserialize_f32<V: de::Visitor<'de>>(
345 self,
346 visitor: V,
347 ) -> Result<V::Value, Self::Error> {
348 match self {
349 Self::Float(float) => {
350 if !float.is_finite() {
351 error(format!(
352 "`Ipld::Float` must be a finite number, not infinity or NaN, \
353 input was `{}`",
354 float
355 ))
356 } else if (float as f32) as f64 != float {
357 error(
358 "`Ipld::Float` cannot be deserialized to `f32`, without loss of \
359 precision`",
360 )
361 } else {
362 visitor.visit_f32(float as f32)
363 }
364 }
365 _ => error(format!(
366 "Only `Ipld::Float` can be deserialized to `f32`, input was `{:#?}`",
367 self
368 )),
369 }
370 }
371
372 fn deserialize_f64<V: de::Visitor<'de>>(
373 self,
374 visitor: V,
375 ) -> Result<V::Value, Self::Error> {
376 match self {
377 Self::Float(float) => {
378 if float.is_finite() {
379 visitor.visit_f64(float)
380 } else {
381 error(format!(
382 "`Ipld::Float` must be a finite number, not infinity or NaN, \
383 input was `{}`",
384 float
385 ))
386 }
387 }
388 _ => error(format!(
389 "Only `Ipld::Float` can be deserialized to `f64`, input was `{:#?}`",
390 self
391 )),
392 }
393 }
394
395 fn deserialize_char<V: de::Visitor<'de>>(
396 self,
397 visitor: V,
398 ) -> Result<V::Value, Self::Error> {
399 match self {
400 Self::String(string) => {
401 if string.chars().count() == 1 {
402 visitor.visit_char(string.chars().next().unwrap())
403 } else {
404 error("`Ipld::String` was longer than a single character")
405 }
406 }
407 _ => error(format!(
408 "Only `Ipld::String` can be deserialized to string, input was `{:#?}`",
409 self
410 )),
411 }
412 }
413
414 fn deserialize_str<V: de::Visitor<'de>>(
415 self,
416 visitor: V,
417 ) -> Result<V::Value, Self::Error> {
418 match self {
419 Self::String(string) => visitor.visit_str(&string),
420 _ => error(format!(
421 "Only `Ipld::String` can be deserialized to string, input was `{:#?}`",
422 self
423 )),
424 }
425 }
426
427 fn deserialize_string<V: de::Visitor<'de>>(
428 self,
429 visitor: V,
430 ) -> Result<V::Value, Self::Error> {
431 match self {
432 Self::String(string) => visitor.visit_string(string),
433 _ => error(format!(
434 "Only `Ipld::String` can be deserialized to string, input was `{:#?}`",
435 self
436 )),
437 }
438 }
439
440 fn deserialize_bytes<V: de::Visitor<'de>>(
441 self,
442 visitor: V,
443 ) -> Result<V::Value, Self::Error> {
444 match self {
445 Self::Bytes(bytes) => visitor.visit_bytes(&bytes),
446 _ => error(format!(
447 "Only `Ipld::Bytes` can be deserialized to bytes, input was `{:#?}`",
448 self
449 )),
450 }
451 }
452
453 fn deserialize_byte_buf<V: de::Visitor<'de>>(
454 self,
455 visitor: V,
456 ) -> Result<V::Value, Self::Error> {
457 match self {
458 Self::Bytes(bytes) => visitor.visit_byte_buf(bytes),
459 _ => error(format!(
460 "Only `Ipld::Bytes` can be deserialized to bytes, input was `{:#?}`",
461 self
462 )),
463 }
464 }
465
466 fn deserialize_seq<V: de::Visitor<'de>>(
467 self,
468 visitor: V,
469 ) -> Result<V::Value, Self::Error> {
470 match self {
471 Self::List(list) => visit_seq(list, visitor),
472 _ => error(format!(
473 "Only `Ipld::List` can be deserialized to sequence, input was `{:#?}`",
474 self
475 )),
476 }
477 }
478
479 fn deserialize_tuple<V: de::Visitor<'de>>(
480 self,
481 len: usize,
482 visitor: V,
483 ) -> Result<V::Value, Self::Error> {
484 match self {
485 Self::List(list) => {
486 if len == list.len() {
487 visit_seq(list, visitor)
488 } else {
489 error(format!(
490 "The tuple size must match the length of the `Ipld::List`, tuple \
491 size: {}, `Ipld::List` length: {}",
492 len,
493 list.len()
494 ))
495 }
496 }
497 _ => error(format!(
498 "Only `Ipld::List` can be deserialized to tuple, input was `{:#?}`",
499 self
500 )),
501 }
502 }
503
504 fn deserialize_tuple_struct<V: de::Visitor<'de>>(
505 self,
506 _name: &str,
507 len: usize,
508 visitor: V,
509 ) -> Result<V::Value, Self::Error> {
510 self.deserialize_tuple(len, visitor)
511 }
512
513 fn deserialize_map<V: de::Visitor<'de>>(
514 self,
515 visitor: V,
516 ) -> Result<V::Value, Self::Error> {
517 match self {
518 Self::Map(map) => visit_map(map, visitor),
519 _ => error(format!(
520 "Only `Ipld::Map` can be deserialized to map, input was `{:#?}`",
521 self
522 )),
523 }
524 }
525
526 fn deserialize_identifier<V: de::Visitor<'de>>(
527 self,
528 visitor: V,
529 ) -> Result<V::Value, Self::Error> {
530 match self {
531 Self::String(string) => visitor.visit_str(&string),
532 _ => error(format!(
533 "Only `Ipld::String` can be deserialized to identifier, input was \
534 `{:#?}`",
535 self
536 )),
537 }
538 }
539
540 fn deserialize_struct<V: de::Visitor<'de>>(
541 self,
542 _name: &str,
543 _fields: &[&str],
544 visitor: V,
545 ) -> Result<V::Value, Self::Error> {
546 match self {
547 Self::Map(map) => visit_map(map, visitor),
548 _ => error(format!(
549 "Only `Ipld::Map` can be deserialized to struct, input was `{:#?}`",
550 self
551 )),
552 }
553 }
554
555 fn deserialize_unit_struct<V: de::Visitor<'de>>(
556 self,
557 _name: &str,
558 _visitor: V,
559 ) -> Result<V::Value, Self::Error> {
560 error("Unit struct cannot be deserialized")
561 }
562
563 fn deserialize_newtype_struct<V: de::Visitor<'de>>(
564 self,
565 name: &str,
566 visitor: V,
567 ) -> Result<V::Value, Self::Error> {
568 if name == CID_SERDE_PRIVATE_IDENTIFIER {
569 match self {
570 Ipld::Link(cid) => visitor.visit_newtype_struct(CidDeserializer(cid)),
571 _ => error(format!(
572 "Only `Ipld::Link`s can be deserialized to CIDs, input was `{:#?}`",
573 self
574 )),
575 }
576 } else {
577 visitor.visit_newtype_struct(self)
578 }
579 }
580
581 fn deserialize_enum<V: de::Visitor<'de>>(
584 self,
585 _name: &str,
586 _variants: &[&str],
587 visitor: V,
588 ) -> Result<V::Value, Self::Error> {
589 let (variant, value) = match self {
590 Ipld::Map(map) => {
591 let mut iter = map.into_iter();
592 let (variant, value) = match iter.next() {
593 Some(v) => v,
594 None => {
595 return error(
596 "Only `Ipld::Map`s with a single key can be deserialized to \
597 `enum`, input had no keys",
598 );
599 }
600 };
601 if iter.next().is_some() {
603 return error(
604 "Only `Ipld::Map`s with a single key can be deserialized to \
605 `enum`, input had more keys",
606 );
607 }
608 (variant, Some(value))
609 }
610 Ipld::String(variant) => (variant, None),
611 _ => {
612 return error(format!(
613 "Only `Ipld::Map` and `Ipld::String` can be deserialized to `enum`, \
614 input was `{:#?}`",
615 self
616 ))
617 }
618 };
619
620 visitor.visit_enum(EnumDeserializer { variant, value })
621 }
622
623 fn deserialize_ignored_any<V: de::Visitor<'de>>(
626 self,
627 visitor: V,
628 ) -> Result<V::Value, Self::Error> {
629 drop(self);
630 visitor.visit_unit()
631 }
632
633 fn deserialize_option<V: de::Visitor<'de>>(
634 self,
635 visitor: V,
636 ) -> Result<V::Value, Self::Error> {
637 match self {
638 Self::Null => visitor.visit_none(),
639 _ => visitor.visit_some(self),
640 }
641 }
642
643 fn is_human_readable(&self) -> bool {
644 false
645 }
646}
647
648fn visit_map<'de, V>(
649 map: BTreeMap<String, Ipld>,
650 visitor: V,
651) -> Result<V::Value, SerdeError>
652where
653 V: de::Visitor<'de>,
654{
655 let mut deserializer = MapDeserializer::new(map);
656 visitor.visit_map(&mut deserializer)
657}
658
659fn visit_seq<'de, V>(
660 list: Vec<Ipld>,
661 visitor: V,
662) -> Result<V::Value, SerdeError>
663where
664 V: de::Visitor<'de>,
665{
666 let mut deserializer = SeqDeserializer::new(list);
667 visitor.visit_seq(&mut deserializer)
668}
669
670struct MapDeserializer {
673 iter: <BTreeMap<String, Ipld> as IntoIterator>::IntoIter,
674 value: Option<Ipld>,
675}
676
677impl MapDeserializer {
678 fn new(map: BTreeMap<String, Ipld>) -> Self {
679 Self {
680 iter: map.into_iter(),
681 value: None,
682 }
683 }
684}
685
686impl<'de> de::MapAccess<'de> for MapDeserializer {
687 type Error = SerdeError;
688
689 fn next_key_seed<K>(
690 &mut self,
691 seed: K,
692 ) -> Result<Option<K::Value>, Self::Error>
693 where
694 K: de::DeserializeSeed<'de>,
695 {
696 match self.iter.next() {
697 Some((key, value)) => {
698 self.value = Some(value);
699 seed.deserialize(Ipld::String(key)).map(Some)
700 }
701 None => Ok(None),
702 }
703 }
704
705 fn next_value_seed<T>(&mut self, seed: T) -> Result<T::Value, Self::Error>
706 where
707 T: de::DeserializeSeed<'de>,
708 {
709 match self.value.take() {
710 Some(value) => seed.deserialize(value),
711 None => error("value is missing"),
712 }
713 }
714
715 fn size_hint(&self) -> Option<usize> {
716 match self.iter.size_hint() {
717 (lower, Some(upper)) if lower == upper => Some(upper),
718 _ => None,
719 }
720 }
721}
722
723struct SeqDeserializer {
726 iter: <Vec<Ipld> as IntoIterator>::IntoIter,
727}
728
729impl SeqDeserializer {
730 fn new(vec: Vec<Ipld>) -> Self {
731 Self {
732 iter: vec.into_iter(),
733 }
734 }
735}
736
737impl<'de> de::SeqAccess<'de> for SeqDeserializer {
738 type Error = SerdeError;
739
740 fn next_element_seed<T>(
741 &mut self,
742 seed: T,
743 ) -> Result<Option<T::Value>, Self::Error>
744 where
745 T: de::DeserializeSeed<'de>,
746 {
747 match self.iter.next() {
748 Some(value) => seed.deserialize(value).map(Some),
749 None => Ok(None),
750 }
751 }
752
753 fn size_hint(&self) -> Option<usize> {
754 match self.iter.size_hint() {
755 (lower, Some(upper)) if lower == upper => Some(upper),
756 _ => None,
757 }
758 }
759}
760
761struct EnumDeserializer {
764 variant: String,
765 value: Option<Ipld>,
766}
767
768impl<'de> de::EnumAccess<'de> for EnumDeserializer {
769 type Error = SerdeError;
770 type Variant = VariantDeserializer;
771
772 fn variant_seed<V>(
773 self,
774 seed: V,
775 ) -> Result<(V::Value, Self::Variant), Self::Error>
776 where
777 V: de::DeserializeSeed<'de>,
778 {
779 let variant = self.variant.into_deserializer();
780 let visitor = VariantDeserializer(self.value);
781 seed.deserialize(variant).map(|v| (v, visitor))
782 }
783}
784
785struct VariantDeserializer(Option<Ipld>);
788
789impl<'de> de::VariantAccess<'de> for VariantDeserializer {
790 type Error = SerdeError;
791
792 fn unit_variant(self) -> Result<(), Self::Error> {
793 match self.0 {
794 Some(value) => de::Deserialize::deserialize(value),
795 None => Ok(()),
796 }
797 }
798
799 fn newtype_variant_seed<T>(self, seed: T) -> Result<T::Value, Self::Error>
800 where
801 T: de::DeserializeSeed<'de>,
802 {
803 match self.0 {
804 Some(value) => seed.deserialize(value),
805 None => Err(de::Error::invalid_type(
806 de::Unexpected::UnitVariant,
807 &"newtype variant",
808 )),
809 }
810 }
811
812 fn tuple_variant<V>(
813 self,
814 len: usize,
815 visitor: V,
816 ) -> Result<V::Value, Self::Error>
817 where
818 V: de::Visitor<'de>,
819 {
820 match self.0 {
821 Some(Ipld::List(list)) => {
822 if len == list.len() {
823 visit_seq(list, visitor)
824 } else {
825 error(format!(
826 "The tuple variant size must match the length of the \
827 `Ipld::List`, tuple variant size: {}, `Ipld::List` length: {}",
828 len,
829 list.len()
830 ))
831 }
832 }
833 Some(_) => error(format!(
834 "Only `Ipld::List` can be deserialized to tuple variant, input was \
835 `{:#?}`",
836 self.0
837 )),
838 None => Err(de::Error::invalid_type(
839 de::Unexpected::UnitVariant,
840 &"tuple variant",
841 )),
842 }
843 }
844
845 fn struct_variant<V>(
846 self,
847 _fields: &'static [&'static str],
848 visitor: V,
849 ) -> Result<V::Value, Self::Error>
850 where
851 V: de::Visitor<'de>,
852 {
853 match self.0 {
854 Some(Ipld::Map(v)) => visit_map(v, visitor),
855 Some(_) => error(format!(
856 "Only `Ipld::Map` can be deserialized to struct variant, input was \
857 `{:#?}`",
858 self.0
859 )),
860 None => Err(de::Error::invalid_type(
861 de::Unexpected::UnitVariant,
862 &"struct variant",
863 )),
864 }
865 }
866}
867
868fn error<S, T>(message: S) -> Result<T, SerdeError>
870where
871 S: AsRef<str> + fmt::Display,
872{
873 Err(de::Error::custom(message))
874}