openzeppelin_relayer/utils/serde/
u128_deserializer.rs

1//! Deserialization utilities for u128 values
2//!
3//! This module provides a custom deserializer for u128 values.
4
5use std::fmt;
6
7use serde::{de, Deserializer};
8
9use super::deserialize_u64;
10
11#[derive(Debug)]
12struct U128Visitor;
13
14impl de::Visitor<'_> for U128Visitor {
15    type Value = u128;
16
17    fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
18        formatter.write_str("a string containing a u128 number or a u128 integer")
19    }
20
21    // Handle string inputs like "340282366920938463463374607431768211455"
22    fn visit_str<E>(self, value: &str) -> Result<Self::Value, E>
23    where
24        E: de::Error,
25    {
26        value.parse::<u128>().map_err(de::Error::custom)
27    }
28
29    // Handle u64 inputs
30    fn visit_u64<E>(self, value: u64) -> Result<Self::Value, E>
31    where
32        E: de::Error,
33    {
34        Ok(value as u128)
35    }
36
37    // Handle i64 inputs
38    fn visit_i64<E>(self, value: i64) -> Result<Self::Value, E>
39    where
40        E: de::Error,
41    {
42        if value < 0 {
43            Err(de::Error::custom(
44                "negative value cannot be converted to u128",
45            ))
46        } else {
47            Ok(value as u128)
48        }
49    }
50}
51
52pub fn deserialize_u128<'de, D>(deserializer: D) -> Result<u128, D::Error>
53where
54    D: Deserializer<'de>,
55{
56    deserializer.deserialize_any(U128Visitor)
57}
58
59pub fn deserialize_optional_u128<'de, D>(deserializer: D) -> Result<Option<u128>, D::Error>
60where
61    D: Deserializer<'de>,
62{
63    Ok(Some(deserialize_u128(deserializer)?))
64}
65
66pub fn deserialize_optional_u64<'de, D>(deserializer: D) -> Result<Option<u64>, D::Error>
67where
68    D: Deserializer<'de>,
69{
70    Ok(Some(deserialize_u64(deserializer)?))
71}
72
73#[cfg(test)]
74mod tests {
75    use super::*;
76    use serde::de::value::{
77        Error as ValueError, I64Deserializer, StringDeserializer, U64Deserializer,
78    };
79
80    #[test]
81    fn test_deserialize_u128_from_string() {
82        let input = "12345";
83        let deserializer = StringDeserializer::<ValueError>::new(input.to_string());
84        let result = deserialize_u128(deserializer);
85        assert!(result.is_ok());
86        assert_eq!(result.unwrap(), 12345);
87    }
88
89    #[test]
90    fn test_deserialize_u128_from_string_large_value() {
91        let input = "340282366920938463463374607431768211455"; // u128::MAX
92        let deserializer = StringDeserializer::<ValueError>::new(input.to_string());
93        let result = deserialize_u128(deserializer);
94        assert!(result.is_ok());
95        assert_eq!(result.unwrap(), u128::MAX);
96    }
97
98    #[test]
99    fn test_deserialize_u128_from_invalid_string() {
100        let input = "not a number";
101        let deserializer = StringDeserializer::<ValueError>::new(input.to_string());
102        let result = deserialize_u128(deserializer);
103        assert!(result.is_err());
104    }
105
106    #[test]
107    fn test_deserialize_u128_from_u64() {
108        let input: u64 = 54321;
109        let deserializer = U64Deserializer::<ValueError>::new(input);
110        let result = deserialize_u128(deserializer);
111        assert!(result.is_ok());
112        assert_eq!(result.unwrap(), 54321u128);
113    }
114
115    #[test]
116    fn test_deserialize_u128_from_i64_positive() {
117        let input: i64 = 9876;
118        let deserializer = I64Deserializer::<ValueError>::new(input);
119        let result = deserialize_u128(deserializer);
120        assert!(result.is_ok());
121        assert_eq!(result.unwrap(), 9876u128);
122    }
123
124    #[test]
125    fn test_deserialize_u128_from_i64_negative() {
126        let input: i64 = -123;
127        let deserializer = I64Deserializer::<ValueError>::new(input);
128        let result = deserialize_u128(deserializer);
129        assert!(result.is_err());
130    }
131
132    #[test]
133    fn test_deserialize_optional_u128() {
134        let input = "12345";
135        let deserializer = StringDeserializer::<ValueError>::new(input.to_string());
136        let result = deserialize_optional_u128(deserializer);
137        assert!(result.is_ok());
138        assert_eq!(result.unwrap(), Some(12345u128));
139    }
140
141    #[test]
142    fn test_deserialize_optional_u64() {
143        let input = "12345";
144        let deserializer = StringDeserializer::<ValueError>::new(input.to_string());
145        let result = deserialize_optional_u64(deserializer);
146        assert!(result.is_ok());
147        assert_eq!(result.unwrap(), Some(12345u64));
148    }
149}