1use crate::Decimal;
2use alloc::string::ToString;
3use core::{fmt, str::FromStr};
4use num_traits::FromPrimitive;
5use serde::{self, de::Unexpected};
6
7#[cfg(feature = "serde-with-arbitrary-precision")]
27pub mod arbitrary_precision {
28 use super::*;
29 use serde::Serialize;
30
31 pub fn deserialize<'de, D>(deserializer: D) -> Result<Decimal, D::Error>
32 where
33 D: serde::de::Deserializer<'de>,
34 {
35 deserializer.deserialize_any(DecimalVisitor)
36 }
37
38 pub fn serialize<S>(value: &Decimal, serializer: S) -> Result<S::Ok, S::Error>
39 where
40 S: serde::Serializer,
41 {
42 serde_json::Number::from_str(&value.to_string())
43 .map_err(serde::ser::Error::custom)?
44 .serialize(serializer)
45 }
46}
47
48#[cfg(feature = "serde-with-arbitrary-precision")]
74pub mod arbitrary_precision_option {
75 use super::*;
76 use serde::Serialize;
77
78 pub fn deserialize<'de, D>(deserializer: D) -> Result<Option<Decimal>, D::Error>
79 where
80 D: serde::de::Deserializer<'de>,
81 {
82 deserializer.deserialize_option(OptionDecimalVisitor)
83 }
84
85 pub fn serialize<S>(value: &Option<Decimal>, serializer: S) -> Result<S::Ok, S::Error>
86 where
87 S: serde::Serializer,
88 {
89 match *value {
90 Some(ref decimal) => serde_json::Number::from_str(&decimal.to_string())
91 .map_err(serde::ser::Error::custom)?
92 .serialize(serializer),
93 None => serializer.serialize_none(),
94 }
95 }
96}
97
98#[cfg(feature = "serde-with-float")]
118pub mod float {
119 use super::*;
120 use serde::Serialize;
121
122 pub fn deserialize<'de, D>(deserializer: D) -> Result<Decimal, D::Error>
123 where
124 D: serde::de::Deserializer<'de>,
125 {
126 deserializer.deserialize_any(DecimalVisitor)
127 }
128
129 pub fn serialize<S>(value: &Decimal, serializer: S) -> Result<S::Ok, S::Error>
130 where
131 S: serde::Serializer,
132 {
133 use num_traits::ToPrimitive;
134 value.to_f64().unwrap().serialize(serializer)
135 }
136}
137
138#[cfg(feature = "serde-with-float")]
164pub mod float_option {
165 use super::*;
166 use serde::Serialize;
167
168 pub fn deserialize<'de, D>(deserializer: D) -> Result<Option<Decimal>, D::Error>
169 where
170 D: serde::de::Deserializer<'de>,
171 {
172 deserializer.deserialize_option(OptionDecimalVisitor)
173 }
174
175 pub fn serialize<S>(value: &Option<Decimal>, serializer: S) -> Result<S::Ok, S::Error>
176 where
177 S: serde::Serializer,
178 {
179 match *value {
180 Some(ref decimal) => {
181 use num_traits::ToPrimitive;
182 decimal.to_f64().unwrap().serialize(serializer)
183 }
184 None => serializer.serialize_none(),
185 }
186 }
187}
188
189#[cfg(feature = "serde-with-str")]
210pub mod str {
211 use super::*;
212
213 pub fn deserialize<'de, D>(deserializer: D) -> Result<Decimal, D::Error>
214 where
215 D: serde::de::Deserializer<'de>,
216 {
217 deserializer.deserialize_str(DecimalVisitor)
218 }
219
220 pub fn serialize<S>(value: &Decimal, serializer: S) -> Result<S::Ok, S::Error>
221 where
222 S: serde::Serializer,
223 {
224 let value = crate::str::to_str_internal(value, true, None);
225 serializer.serialize_str(value.0.as_ref())
226 }
227}
228
229#[cfg(feature = "serde-with-str")]
255pub mod str_option {
256 use super::*;
257
258 pub fn deserialize<'de, D>(deserializer: D) -> Result<Option<Decimal>, D::Error>
259 where
260 D: serde::de::Deserializer<'de>,
261 {
262 deserializer.deserialize_option(OptionDecimalStrVisitor)
263 }
264
265 pub fn serialize<S>(value: &Option<Decimal>, serializer: S) -> Result<S::Ok, S::Error>
266 where
267 S: serde::Serializer,
268 {
269 match *value {
270 Some(ref decimal) => {
271 let decimal = crate::str::to_str_internal(decimal, true, None);
272 serializer.serialize_some::<str>(decimal.0.as_ref())
273 }
274 None => serializer.serialize_none(),
275 }
276 }
277}
278
279#[cfg(not(feature = "serde-str"))]
280impl<'de> serde::Deserialize<'de> for Decimal {
281 fn deserialize<D>(deserializer: D) -> Result<Decimal, D::Error>
282 where
283 D: serde::de::Deserializer<'de>,
284 {
285 deserializer.deserialize_any(DecimalVisitor)
286 }
287}
288
289#[cfg(all(feature = "serde-str", not(feature = "serde-float")))]
290impl<'de> serde::Deserialize<'de> for Decimal {
291 fn deserialize<D>(deserializer: D) -> Result<Decimal, D::Error>
292 where
293 D: serde::de::Deserializer<'de>,
294 {
295 deserializer.deserialize_str(DecimalVisitor)
296 }
297}
298
299#[cfg(all(feature = "serde-str", feature = "serde-float"))]
300impl<'de> serde::Deserialize<'de> for Decimal {
301 fn deserialize<D>(deserializer: D) -> Result<Decimal, D::Error>
302 where
303 D: serde::de::Deserializer<'de>,
304 {
305 deserializer.deserialize_f64(DecimalVisitor)
306 }
307}
308
309#[cfg(feature = "serde-with-arbitrary-precision")]
311const DECIMAL_KEY_TOKEN: &str = "$serde_json::private::Number";
312
313struct DecimalVisitor;
314
315impl<'de> serde::de::Visitor<'de> for DecimalVisitor {
316 type Value = Decimal;
317
318 fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
319 write!(formatter, "a Decimal type representing a fixed-point number")
320 }
321
322 fn visit_i64<E>(self, value: i64) -> Result<Decimal, E>
323 where
324 E: serde::de::Error,
325 {
326 match Decimal::from_i64(value) {
327 Some(s) => Ok(s),
328 None => Err(E::invalid_value(Unexpected::Signed(value), &self)),
329 }
330 }
331
332 fn visit_u64<E>(self, value: u64) -> Result<Decimal, E>
333 where
334 E: serde::de::Error,
335 {
336 match Decimal::from_u64(value) {
337 Some(s) => Ok(s),
338 None => Err(E::invalid_value(Unexpected::Unsigned(value), &self)),
339 }
340 }
341
342 fn visit_f64<E>(self, value: f64) -> Result<Decimal, E>
343 where
344 E: serde::de::Error,
345 {
346 Decimal::from_str(&value.to_string()).map_err(|_| E::invalid_value(Unexpected::Float(value), &self))
347 }
348
349 fn visit_str<E>(self, value: &str) -> Result<Decimal, E>
350 where
351 E: serde::de::Error,
352 {
353 Decimal::from_str(value)
354 .or_else(|_| Decimal::from_scientific(value))
355 .map_err(|_| E::invalid_value(Unexpected::Str(value), &self))
356 }
357
358 #[cfg(feature = "serde-with-arbitrary-precision")]
359 fn visit_map<A>(self, map: A) -> Result<Decimal, A::Error>
360 where
361 A: serde::de::MapAccess<'de>,
362 {
363 let mut map = map;
364 let value = map.next_key::<DecimalKey>()?;
365 if value.is_none() {
366 return Err(serde::de::Error::invalid_type(Unexpected::Map, &self));
367 }
368 let v: DecimalFromString = map.next_value()?;
369 Ok(v.value)
370 }
371}
372
373#[cfg(any(feature = "serde-with-float", feature = "serde-with-arbitrary-precision"))]
374struct OptionDecimalVisitor;
375
376#[cfg(any(feature = "serde-with-float", feature = "serde-with-arbitrary-precision"))]
377impl<'de> serde::de::Visitor<'de> for OptionDecimalVisitor {
378 type Value = Option<Decimal>;
379
380 fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
381 formatter.write_str("a Decimal type representing a fixed-point number")
382 }
383
384 fn visit_none<E>(self) -> Result<Option<Decimal>, E>
385 where
386 E: serde::de::Error,
387 {
388 Ok(None)
389 }
390
391 #[cfg(all(feature = "serde-str", feature = "serde-float"))]
392 fn visit_some<D>(self, d: D) -> Result<Option<Decimal>, D::Error>
393 where
394 D: serde::de::Deserializer<'de>,
395 {
396 d.deserialize_any(DecimalVisitor).map(Some)
398 }
399
400 #[cfg(not(all(feature = "serde-str", feature = "serde-float")))]
401 fn visit_some<D>(self, d: D) -> Result<Option<Decimal>, D::Error>
402 where
403 D: serde::de::Deserializer<'de>,
404 {
405 <Decimal as serde::Deserialize>::deserialize(d).map(Some)
406 }
407}
408
409#[cfg(feature = "serde-with-str")]
410struct OptionDecimalStrVisitor;
411
412#[cfg(feature = "serde-with-str")]
413impl<'de> serde::de::Visitor<'de> for OptionDecimalStrVisitor {
414 type Value = Option<Decimal>;
415
416 fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
417 formatter.write_str("a Decimal type representing a fixed-point number")
418 }
419
420 fn visit_none<E>(self) -> Result<Option<Decimal>, E>
421 where
422 E: serde::de::Error,
423 {
424 Ok(None)
425 }
426
427 fn visit_some<D>(self, d: D) -> Result<Option<Decimal>, D::Error>
428 where
429 D: serde::de::Deserializer<'de>,
430 {
431 d.deserialize_str(Self)
432 }
433
434 fn visit_str<E>(self, v: &str) -> Result<Self::Value, E>
435 where
436 E: serde::de::Error,
437 {
438 match v.is_empty() {
439 true => Ok(None),
440 false => {
441 let d = Decimal::from_str(v)
442 .or_else(|_| Decimal::from_scientific(v))
443 .map_err(serde::de::Error::custom)?;
444 Ok(Some(d))
445 }
446 }
447 }
448}
449
450#[cfg(feature = "serde-with-arbitrary-precision")]
451struct DecimalKey;
452
453#[cfg(feature = "serde-with-arbitrary-precision")]
454impl<'de> serde::de::Deserialize<'de> for DecimalKey {
455 fn deserialize<D>(deserializer: D) -> Result<DecimalKey, D::Error>
456 where
457 D: serde::de::Deserializer<'de>,
458 {
459 struct FieldVisitor;
460
461 impl<'de> serde::de::Visitor<'de> for FieldVisitor {
462 type Value = ();
463
464 fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
465 formatter.write_str("a valid decimal field")
466 }
467
468 fn visit_str<E>(self, s: &str) -> Result<(), E>
469 where
470 E: serde::de::Error,
471 {
472 if s == DECIMAL_KEY_TOKEN {
473 Ok(())
474 } else {
475 Err(serde::de::Error::custom("expected field with custom name"))
476 }
477 }
478 }
479
480 deserializer.deserialize_identifier(FieldVisitor)?;
481 Ok(DecimalKey)
482 }
483}
484
485#[cfg(feature = "serde-with-arbitrary-precision")]
486pub struct DecimalFromString {
487 pub value: Decimal,
488}
489
490#[cfg(feature = "serde-with-arbitrary-precision")]
491impl<'de> serde::de::Deserialize<'de> for DecimalFromString {
492 fn deserialize<D>(deserializer: D) -> Result<DecimalFromString, D::Error>
493 where
494 D: serde::de::Deserializer<'de>,
495 {
496 struct Visitor;
497
498 impl<'de> serde::de::Visitor<'de> for Visitor {
499 type Value = DecimalFromString;
500
501 fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
502 formatter.write_str("string containing a decimal")
503 }
504
505 fn visit_str<E>(self, value: &str) -> Result<DecimalFromString, E>
506 where
507 E: serde::de::Error,
508 {
509 let d = Decimal::from_str(value)
510 .or_else(|_| Decimal::from_scientific(value))
511 .map_err(serde::de::Error::custom)?;
512 Ok(DecimalFromString { value: d })
513 }
514 }
515
516 deserializer.deserialize_str(Visitor)
517 }
518}
519
520#[cfg(not(feature = "serde-float"))]
521impl serde::Serialize for Decimal {
522 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
523 where
524 S: serde::Serializer,
525 {
526 let value = crate::str::to_str_internal(self, true, None);
527 serializer.serialize_str(value.0.as_ref())
528 }
529}
530
531#[cfg(all(feature = "serde-float", not(feature = "serde-arbitrary-precision")))]
532impl serde::Serialize for Decimal {
533 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
534 where
535 S: serde::Serializer,
536 {
537 use num_traits::ToPrimitive;
538 serializer.serialize_f64(self.to_f64().unwrap())
539 }
540}
541
542#[cfg(all(feature = "serde-float", feature = "serde-arbitrary-precision"))]
543impl serde::Serialize for Decimal {
544 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
545 where
546 S: serde::Serializer,
547 {
548 serde_json::Number::from_str(&self.to_string())
549 .map_err(serde::ser::Error::custom)?
550 .serialize(serializer)
551 }
552}
553
554#[cfg(test)]
555mod test {
556 use super::*;
557 use serde::{Deserialize, Serialize};
558
559 #[derive(Serialize, Deserialize, Debug)]
560 struct Record {
561 amount: Decimal,
562 }
563
564 #[test]
565 #[cfg(not(feature = "serde-str"))]
566 fn deserialize_valid_decimal() {
567 let data = [
568 ("{\"amount\":\"1.234\"}", "1.234"),
569 ("{\"amount\":1234}", "1234"),
570 ("{\"amount\":1234.56}", "1234.56"),
571 ("{\"amount\":\"1.23456e3\"}", "1234.56"),
572 ];
573 for &(serialized, value) in data.iter() {
574 let result = serde_json::from_str(serialized);
575 assert!(
576 result.is_ok(),
577 "expected successful deserialization for {}. Error: {:?}",
578 serialized,
579 result.err().unwrap()
580 );
581 let record: Record = result.unwrap();
582 assert_eq!(
583 value,
584 record.amount.to_string(),
585 "expected: {}, actual: {}",
586 value,
587 record.amount
588 );
589 }
590 }
591
592 #[test]
593 #[cfg(feature = "serde-arbitrary-precision")]
594 fn deserialize_basic_decimal() {
595 let d: Decimal = serde_json::from_str("1.1234127836128763").unwrap();
596 assert_eq!(d.to_string(), "1.1234127836128763");
598 }
599
600 #[test]
601 #[should_panic]
602 fn deserialize_invalid_decimal() {
603 let serialized = "{\"amount\":\"foo\"}";
604 let _: Record = serde_json::from_str(serialized).unwrap();
605 }
606
607 #[test]
608 #[cfg(not(feature = "serde-float"))]
609 fn serialize_decimal() {
610 let record = Record {
611 amount: Decimal::new(1234, 3),
612 };
613 let serialized = serde_json::to_string(&record).unwrap();
614 assert_eq!("{\"amount\":\"1.234\"}", serialized);
615 }
616
617 #[test]
618 #[cfg(not(feature = "serde-float"))]
619 fn serialize_negative_zero() {
620 let record = Record { amount: -Decimal::ZERO };
621 let serialized = serde_json::to_string(&record).unwrap();
622 assert_eq!("{\"amount\":\"-0\"}", serialized);
623 }
624
625 #[test]
626 #[cfg(feature = "serde-float")]
627 fn serialize_decimal() {
628 let record = Record {
629 amount: Decimal::new(1234, 3),
630 };
631 let serialized = serde_json::to_string(&record).unwrap();
632 assert_eq!("{\"amount\":1.234}", serialized);
633 }
634
635 #[test]
636 #[cfg(all(feature = "serde-float", feature = "serde-arbitrary-precision"))]
637 fn serialize_decimal_roundtrip() {
638 let record = Record {
639 amount: Decimal::new(481, 2),
642 };
643 let serialized = serde_json::to_string(&record).unwrap();
644 assert_eq!("{\"amount\":4.81}", serialized);
645 let deserialized: Record = serde_json::from_str(&serialized).unwrap();
646 assert_eq!(record.amount, deserialized.amount);
647 }
648
649 #[test]
650 #[cfg(all(feature = "serde-str", not(feature = "serde-float")))]
651 fn serialize_decimal_roundtrip() {
652 let record = Record {
653 amount: Decimal::new(481, 2),
654 };
655 let serialized = serde_json::to_string(&record).unwrap();
656 assert_eq!("{\"amount\":\"4.81\"}", serialized);
657 let deserialized: Record = serde_json::from_str(&serialized).unwrap();
658 assert_eq!(record.amount, deserialized.amount);
659 }
660
661 #[test]
662 #[cfg(all(feature = "serde-str", not(feature = "serde-float")))]
663 fn bincode_serialization_not_float() {
664 use bincode::{deserialize, serialize};
665
666 let data = [
667 "0",
668 "0.00",
669 "3.14159",
670 "-3.14159",
671 "1234567890123.4567890",
672 "-1234567890123.4567890",
673 "5233.9008808150288439427720175",
674 "-5233.9008808150288439427720175",
675 ];
676 for &raw in data.iter() {
677 let value = Decimal::from_str(raw).unwrap();
678 let encoded = serialize(&value).unwrap();
679 let decoded: Decimal = deserialize(&encoded[..]).unwrap();
680 assert_eq!(value, decoded);
681 assert_eq!(8usize + raw.len(), encoded.len());
682 }
683 }
684
685 #[test]
686 #[cfg(all(feature = "serde-str", feature = "serde-float"))]
687 fn bincode_serialization_serde_float() {
688 use bincode::{deserialize, serialize};
689
690 let data = [
691 ("0", "0"),
692 ("0.00", "0.00"),
693 ("3.14159", "3.14159"),
694 ("-3.14159", "-3.14159"),
695 ("1234567890123.4567890", "1234567890123.4568"),
696 ("-1234567890123.4567890", "-1234567890123.4568"),
697 ];
698 for &(value, expected) in data.iter() {
699 let value = Decimal::from_str(value).unwrap();
700 let expected = Decimal::from_str(expected).unwrap();
701 let encoded = serialize(&value).unwrap();
702 let decoded: Decimal = deserialize(&encoded[..]).unwrap();
703 assert_eq!(expected, decoded);
704 assert_eq!(8usize, encoded.len());
705 }
706 }
707
708 #[test]
709 #[cfg(all(feature = "serde-str", not(feature = "serde-float")))]
710 fn bincode_nested_serialization() {
711 #[derive(Deserialize, Serialize, Debug)]
713 pub struct Foo {
714 value: Decimal,
715 }
716
717 let s = Foo {
718 value: Decimal::new(-1, 3).round_dp(0),
719 };
720 let ser = bincode::serialize(&s).unwrap();
721 let des: Foo = bincode::deserialize(&ser).unwrap();
722 assert_eq!(des.value, s.value);
723 }
724
725 #[test]
726 #[cfg(feature = "serde-with-arbitrary-precision")]
727 fn with_arbitrary_precision() {
728 #[derive(Serialize, Deserialize)]
729 pub struct ArbitraryExample {
730 #[serde(with = "crate::serde::arbitrary_precision")]
731 value: Decimal,
732 }
733
734 let value = ArbitraryExample {
735 value: Decimal::from_str("123.400").unwrap(),
736 };
737 assert_eq!(&serde_json::to_string(&value).unwrap(), r#"{"value":123.400}"#);
738 }
739
740 #[test]
741 #[cfg(feature = "serde-with-arbitrary-precision")]
742 fn with_arbitrary_precision_from_string() {
743 #[derive(Serialize, Deserialize)]
744 pub struct ArbitraryExample {
745 #[serde(with = "crate::serde::arbitrary_precision")]
746 value: Decimal,
747 }
748
749 let value: ArbitraryExample = serde_json::from_str(r#"{"value":"1.1234127836128763"}"#).unwrap();
750 assert_eq!(value.value.to_string(), "1.1234127836128763");
751 }
752
753 #[test]
754 #[cfg(feature = "serde-with-float")]
755 fn with_float() {
756 #[derive(Serialize, Deserialize)]
757 pub struct FloatExample {
758 #[serde(with = "crate::serde::float")]
759 value: Decimal,
760 }
761
762 let value = FloatExample {
763 value: Decimal::from_str("123.400").unwrap(),
764 };
765 assert_eq!(&serde_json::to_string(&value).unwrap(), r#"{"value":123.4}"#);
766 }
767
768 #[test]
769 #[cfg(feature = "serde-with-str")]
770 fn with_str() {
771 #[derive(Serialize, Deserialize)]
772 pub struct StringExample {
773 #[serde(with = "crate::serde::str")]
774 value: Decimal,
775 }
776
777 let value = StringExample {
778 value: Decimal::from_str("123.400").unwrap(),
779 };
780 assert_eq!(&serde_json::to_string(&value).unwrap(), r#"{"value":"123.400"}"#);
781 }
782
783 #[test]
784 #[cfg(feature = "serde-with-str")]
785 fn with_str_bincode() {
786 use bincode::{deserialize, serialize};
787
788 #[derive(Serialize, Deserialize)]
789 struct BincodeExample {
790 #[serde(with = "crate::serde::str")]
791 value: Decimal,
792 }
793
794 let data = [
795 ("0", "0"),
796 ("0.00", "0.00"),
797 ("1.234", "1.234"),
798 ("3.14159", "3.14159"),
799 ("-3.14159", "-3.14159"),
800 ("1234567890123.4567890", "1234567890123.4567890"),
801 ("-1234567890123.4567890", "-1234567890123.4567890"),
802 ];
803 for &(value, expected) in data.iter() {
804 let value = Decimal::from_str(value).unwrap();
805 let expected = Decimal::from_str(expected).unwrap();
806 let input = BincodeExample { value };
807
808 let encoded = serialize(&input).unwrap();
809 let decoded: BincodeExample = deserialize(&encoded[..]).unwrap();
810 assert_eq!(expected, decoded.value);
811 }
812 }
813
814 #[test]
815 #[cfg(feature = "serde-with-str")]
816 fn with_str_bincode_optional() {
817 use bincode::{deserialize, serialize};
818
819 #[derive(Serialize, Deserialize)]
820 struct BincodeExample {
821 #[serde(with = "crate::serde::str_option")]
822 value: Option<Decimal>,
823 }
824
825 let value = Some(Decimal::new(1234, 3));
827 let input = BincodeExample { value };
828 let encoded = serialize(&input).unwrap();
829 let decoded: BincodeExample = deserialize(&encoded[..]).unwrap();
830 assert_eq!(value, decoded.value, "Some(value)");
831
832 let input = BincodeExample { value: None };
834 let encoded = serialize(&input).unwrap();
835 let decoded: BincodeExample = deserialize(&encoded[..]).unwrap();
836 assert_eq!(None, decoded.value, "None");
837 }
838
839 #[test]
840 #[cfg(feature = "serde-with-str")]
841 fn with_str_optional() {
842 #[derive(Serialize, Deserialize)]
843 pub struct StringExample {
844 #[serde(with = "crate::serde::str_option")]
845 value: Option<Decimal>,
846 }
847
848 let original = StringExample {
849 value: Some(Decimal::from_str("123.400").unwrap()),
850 };
851 assert_eq!(&serde_json::to_string(&original).unwrap(), r#"{"value":"123.400"}"#);
852 let deserialized: StringExample = serde_json::from_str(r#"{"value":"123.400"}"#).unwrap();
853 assert_eq!(deserialized.value, original.value);
854 assert!(deserialized.value.is_some());
855 assert_eq!(deserialized.value.unwrap().unpack(), original.value.unwrap().unpack());
856
857 let original = StringExample { value: None };
859 assert_eq!(&serde_json::to_string(&original).unwrap(), r#"{"value":null}"#);
860 let deserialized: StringExample = serde_json::from_str(r#"{"value":null}"#).unwrap();
861 assert_eq!(deserialized.value, original.value);
862 assert!(deserialized.value.is_none());
863
864 let original = StringExample { value: None };
866 let deserialized: StringExample = serde_json::from_str(r#"{"value":""}"#).unwrap();
867 assert_eq!(deserialized.value, original.value);
868 assert!(deserialized.value.is_none());
869 }
870
871 #[test]
872 #[cfg(feature = "serde-with-float")]
873 fn with_float_optional() {
874 #[derive(Serialize, Deserialize)]
875 pub struct StringExample {
876 #[serde(with = "crate::serde::float_option")]
877 value: Option<Decimal>,
878 }
879
880 let original = StringExample {
881 value: Some(Decimal::from_str("123.400").unwrap()),
882 };
883 assert_eq!(&serde_json::to_string(&original).unwrap(), r#"{"value":123.4}"#);
884 let deserialized: StringExample = serde_json::from_str(r#"{"value":123.4}"#).unwrap();
885 assert_eq!(deserialized.value, original.value);
886 assert!(deserialized.value.is_some()); let original = StringExample { value: None };
890 assert_eq!(&serde_json::to_string(&original).unwrap(), r#"{"value":null}"#);
891 let deserialized: StringExample = serde_json::from_str(r#"{"value":null}"#).unwrap();
892 assert_eq!(deserialized.value, original.value);
893 assert!(deserialized.value.is_none());
894 }
895
896 #[test]
897 #[cfg(feature = "serde-with-arbitrary-precision")]
898 fn with_arbitrary_precision_optional() {
899 #[derive(Serialize, Deserialize)]
900 pub struct StringExample {
901 #[serde(with = "crate::serde::arbitrary_precision_option")]
902 value: Option<Decimal>,
903 }
904
905 let original = StringExample {
906 value: Some(Decimal::from_str("123.400").unwrap()),
907 };
908 assert_eq!(&serde_json::to_string(&original).unwrap(), r#"{"value":123.400}"#);
909 let deserialized: StringExample = serde_json::from_str(r#"{"value":123.400}"#).unwrap();
910 assert_eq!(deserialized.value, original.value);
911 assert!(deserialized.value.is_some());
912 assert_eq!(deserialized.value.unwrap().unpack(), original.value.unwrap().unpack());
913
914 let original = StringExample { value: None };
916 assert_eq!(&serde_json::to_string(&original).unwrap(), r#"{"value":null}"#);
917 let deserialized: StringExample = serde_json::from_str(r#"{"value":null}"#).unwrap();
918 assert_eq!(deserialized.value, original.value);
919 assert!(deserialized.value.is_none());
920 }
921}