From 7c519fd5934a0613a9e3c56b9c7fa27c79316083 Mon Sep 17 00:00:00 2001 From: Nadav Ivgi Date: Tue, 3 Nov 2020 12:00:36 +0200 Subject: [PATCH] Make uint types (un)serializable --- src/util/uint.rs | 64 ++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 64 insertions(+) diff --git a/src/util/uint.rs b/src/util/uint.rs index 376dc7d243..43f1b112d8 100644 --- a/src/util/uint.rs +++ b/src/util/uint.rs @@ -403,6 +403,58 @@ macro_rules! construct_uint { Ok($name(ret)) } } + + #[cfg(feature = "serde")] + impl $crate::serde::Serialize for $name { + fn serialize(&self, serializer: S) -> Result + where + S: $crate::serde::Serializer, + { + use $crate::serde::ser::SerializeTuple; + let mut tup = serializer.serialize_tuple($n_words)?; + for i in 0..$n_words { + tup.serialize_element(&self.0[i])?; + } + tup.end() + } + } + + #[cfg(feature = "serde")] + impl<'de> $crate::serde::Deserialize<'de> for $name { + fn deserialize>( + deserializer: D, + ) -> Result { + use ::std::fmt::{self, Formatter}; + use $crate::serde::de::Error; + struct Visitor; + impl<'de> $crate::serde::de::Visitor<'de> for Visitor { + type Value = $name; + + fn expecting(&self, formatter: &mut Formatter) -> fmt::Result { + write!(formatter, "array with {} integers", $n_words) + } + + fn visit_seq(self, mut seq: S) -> Result + where + S: $crate::serde::de::SeqAccess<'de>, + { + let mut ints: Vec = vec![]; + for _ in 0..$n_words { + ints.push(seq.next_element()?.ok_or_else(|| { + Error::invalid_length(ints.len(), &$n_words.to_string().as_str()) + })?); + } + if seq.next_element::()?.is_some() { + Err(Error::invalid_length($n_words + 1, &$n_words.to_string().as_str())) + } else { + Ok(ints[..].into()) + } + } + } + + deserializer.deserialize_tuple($n_words, Visitor) + } + } ); } @@ -612,4 +664,16 @@ mod tests { assert_eq!(end1.ok(), Some(start1)); assert_eq!(end2.ok(), Some(start2)); } + + #[cfg(feature = "serde")] + #[test] + pub fn uint_serde_test() { + let init = Uint256::from(&[111,222,333,444][..]); + let json = serde_json::to_string(&init).unwrap(); + assert_eq!(serde_json::from_str::(&json).unwrap(), init); + + let init = Uint128::from(&[111,222][..]); + let json = serde_json::to_string(&init).unwrap(); + assert_eq!(serde_json::from_str::(&json).unwrap(), init); + } }