Skip to main content

fastnum/decimal/dec/extras/serde/
utils.rs

1//! # Decimal number serialization and deserialization utils for serde
2
3#[cfg(feature = "serde-arbitrary-precision")]
4mod details;
5
6#[cfg(feature = "serde-arbitrary-precision")]
7type D<const N: usize> = crate::decimal::Decimal<N>;
8
9/// Serialize/deserialize [crate::decimal::Decimal] as arbitrary precision
10/// numbers in JSON using the `arbitrary_precision` feature within `serde_json`.
11///
12/// ```
13/// # use serde::Deserialize;
14/// # use fastnum::*;
15///
16/// #[derive(Deserialize)]
17/// pub struct Arbitrary {
18///     #[serde(with = "decimal::serde::dec::arbitrary_precision")]
19///     value: D128,
20/// }
21///
22/// let data: Arbitrary = serde_json::from_str(r#"{"value": -1.09861228866810969139524523692252570465}"#).unwrap();
23/// assert_eq!(dec128!(-1.09861228866810969139524523692252570465), data.value);
24/// ```
25#[cfg(feature = "serde-arbitrary-precision")]
26pub mod arbitrary_precision {
27
28    use super::*;
29
30    use serde::{de, Serialize};
31    use std::str::FromStr;
32
33    /// Deserializer for [`#[serde(with = "...")]`](<https://serde.rs/field-attrs.html#with>).
34    pub fn deserialize<'de, Ds, const N: usize>(deserializer: Ds) -> Result<D<N>, Ds::Error>
35    where
36        Ds: de::Deserializer<'de>,
37    {
38        deserializer.deserialize_any(details::Visitor)
39    }
40
41    /// Serializer for [`#[serde(with = "...")]`](<https://serde.rs/field-attrs.html#with>).
42    pub fn serialize<S, const N: usize>(value: &D<N>, serializer: S) -> Result<S::Ok, S::Error>
43    where
44        S: serde::Serializer,
45    {
46        serde_json::Number::from_str(&value.to_string())
47            .map_err(serde::ser::Error::custom)?
48            .serialize(serializer)
49    }
50}
51
52/// Serialize/deserialize optional [crate::decimal::Decimal] as arbitrary
53/// precision numbers in JSON using the `arbitrary_precision` feature within
54/// `serde_json`.
55///
56/// ```
57/// # use serde::Deserialize;
58/// # use fastnum::*;
59///
60/// #[derive(Deserialize)]
61/// pub struct Arbitrary {
62///     #[serde(with = "decimal::serde::dec::arbitrary_precision_option")]
63///     value: Option<D128>,
64/// }
65///
66/// let data: Arbitrary = serde_json::from_str(r#"{"value": -1.09861228866810969139524523692252570465}"#).unwrap();
67/// assert_eq!(Some(dec128!(-1.09861228866810969139524523692252570465)), data.value);
68///
69/// let data: Arbitrary = serde_json::from_str(r#"{"value": null}"#).unwrap();
70/// assert_eq!(None, data.value);
71/// ```
72#[cfg(feature = "serde-arbitrary-precision")]
73pub mod arbitrary_precision_option {
74    use super::*;
75
76    use serde::{de, Serialize};
77
78    /// Deserializer for [`#[serde(with = "...")]`](<https://serde.rs/field-attrs.html#with>).
79    pub fn deserialize<'de, Ds, const N: usize>(deserializer: Ds) -> Result<Option<D<N>>, Ds::Error>
80    where
81        Ds: de::Deserializer<'de>,
82    {
83        deserializer.deserialize_option(details::OptionVisitor)
84    }
85
86    /// Serializer for [`#[serde(with = "...")]`](<https://serde.rs/field-attrs.html#with>).
87    pub fn serialize<S, const N: usize>(
88        value: &Option<D<N>>,
89        serializer: S,
90    ) -> Result<S::Ok, S::Error>
91    where
92        S: serde::Serializer,
93    {
94        match value {
95            Some(decimal) => {
96                serde_json::Number::from_string_unchecked(decimal.to_string()).serialize(serializer)
97            }
98            None => serializer.serialize_none(),
99        }
100    }
101}