alloy_eip8141/
serde_utils.rs1use alloy_primitives::{FixedBytes, U8, U64};
4use core::fmt;
5use serde::{Deserialize, Deserializer, Serialize, Serializer, de};
6
7pub(crate) mod quantity {
8 use super::*;
9
10 pub(crate) fn serialize<S: Serializer>(value: &u64, serializer: S) -> Result<S::Ok, S::Error> {
11 U64::from(*value).serialize(serializer)
12 }
13
14 pub(crate) fn deserialize<'de, D: Deserializer<'de>>(deserializer: D) -> Result<u64, D::Error> {
15 U64::deserialize(deserializer).map(|value| value.to())
16 }
17}
18
19pub(crate) mod quantity_u8 {
20 use super::*;
21
22 pub(crate) fn serialize<S: Serializer>(value: &u8, serializer: S) -> Result<S::Ok, S::Error> {
23 U8::from(*value).serialize(serializer)
24 }
25
26 pub(crate) fn deserialize<'de, D: Deserializer<'de>>(deserializer: D) -> Result<u8, D::Error> {
27 U8::deserialize(deserializer).map(|value| value.to())
28 }
29}
30
31pub(crate) fn serialize_optional_bytes<const N: usize, S: Serializer>(
32 value: Option<FixedBytes<N>>,
33 serializer: S,
34) -> Result<S::Ok, S::Error> {
35 match value {
36 Some(value) => value.serialize(serializer),
37 None => FixedBytes::<0>::ZERO.serialize(serializer),
38 }
39}
40
41pub(crate) fn deserialize_optional_bytes<'de, const N: usize, D: Deserializer<'de>>(
45 deserializer: D,
46) -> Result<Option<FixedBytes<N>>, D::Error> {
47 struct OptionalBytesVisitor<const N: usize>;
48
49 impl<'de, const N: usize> de::Visitor<'de> for OptionalBytesVisitor<N> {
50 type Value = Option<FixedBytes<N>>;
51
52 fn expecting(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result {
53 write!(formatter, "an empty byte string or exactly {N} bytes")
54 }
55
56 fn visit_none<E: de::Error>(self) -> Result<Self::Value, E> {
57 Ok(None)
58 }
59
60 fn visit_unit<E: de::Error>(self) -> Result<Self::Value, E> {
61 Ok(None)
62 }
63
64 fn visit_bytes<E: de::Error>(self, bytes: &[u8]) -> Result<Self::Value, E> {
65 if bytes.is_empty() {
66 Ok(None)
67 } else {
68 FixedBytes::try_from(bytes).map(Some).map_err(E::custom)
69 }
70 }
71
72 fn visit_str<E: de::Error>(self, value: &str) -> Result<Self::Value, E> {
73 if value == "0x" || value.is_empty() {
74 Ok(None)
75 } else {
76 value.parse().map(Some).map_err(E::custom)
77 }
78 }
79
80 fn visit_seq<A: de::SeqAccess<'de>>(self, mut seq: A) -> Result<Self::Value, A::Error> {
81 let mut bytes = [0u8; N];
82 let mut len = 0;
83 while len < N {
84 match seq.next_element()? {
85 Some(byte) => {
86 bytes[len] = byte;
87 len += 1;
88 }
89 None => break,
90 }
91 }
92 if len == 0 {
93 return Ok(None);
94 }
95 if len < N {
96 return Err(de::Error::invalid_length(len, &self));
97 }
98 if seq.next_element::<u8>()?.is_some() {
99 return Err(de::Error::invalid_length(N + 1, &self));
100 }
101 Ok(Some(bytes.into()))
102 }
103 }
104
105 if deserializer.is_human_readable() {
106 deserializer.deserialize_any(OptionalBytesVisitor::<N>)
107 } else {
108 deserializer.deserialize_bytes(OptionalBytesVisitor::<N>)
109 }
110}