diff --git a/src/lib.rs b/src/lib.rs index befb61f..c4e1514 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -280,6 +280,7 @@ An informal description can be found on [Wikipedia](https://en.wikipedia.org/wik #[cfg(feature = "serde_support")] use serde::{Deserialize, Serialize}; +use std::fmt; use std::fmt::{Debug, Display, Formatter}; use std::str::FromStr; @@ -325,7 +326,7 @@ pub enum Error { /// independently. /// #[derive(Debug, Clone, PartialEq, Eq, Hash)] -#[cfg_attr(feature = "serde_support", derive(Deserialize, Serialize))] +#[cfg_attr(feature = "serde_support", derive(Serialize))] pub struct EmailAddress(String); // ------------------------------------------------------------------------------------------------ @@ -431,6 +432,38 @@ impl AsRef for EmailAddress { } } +#[cfg(feature = "serde_support")] +impl<'de> Deserialize<'de> for EmailAddress { + fn deserialize(deserializer: D) -> Result + where + D: serde::Deserializer<'de>, + { + use serde::de::{Error, Unexpected, Visitor}; + + struct EmailAddressVisitor; + + impl Visitor<'_> for EmailAddressVisitor { + type Value = EmailAddress; + + fn expecting(&self, fmt: &mut Formatter<'_>) -> fmt::Result { + fmt.write_str("data") + } + + fn visit_str(self, s: &str) -> Result + where + E: Error, + { + EmailAddress::from_str(s).map_err(|err| { + let exp = format!("{}", err); + Error::invalid_value(Unexpected::Str(s), &exp.as_ref()) + }) + } + } + + deserializer.deserialize_str(EmailAddressVisitor) + } +} + impl EmailAddress { /// /// Determine whether the `address` string is a valid email address. Note this is equivalent to