rust_eureka/request/
dcname.rs

1use serde::ser::{Serialize, Serializer};
2use serde::de::{Deserialize, Deserializer, Visitor, Error as DeError};
3use std::iter::Iterator;
4use std::fmt;
5use std::convert::From;
6use std::str::FromStr;
7use std::error::Error;
8
9const MY_OWN: &'static str = "MyOwn";
10const AMAZON: &'static str = "Amazon";
11
12#[derive(Debug, PartialEq)]
13pub enum DcName {
14    MyOwn,
15    Amazon
16}
17
18impl DcName {
19    pub fn values() -> Vec<DcName> {
20        vec![DcName::MyOwn, DcName::Amazon]
21    }
22}
23
24#[derive(Debug)]
25pub struct InvalidDcNameError {
26    invalid_value: String
27}
28
29impl InvalidDcNameError {
30    pub fn new(invalid_nm: &str) -> Self {
31        InvalidDcNameError {
32            invalid_value: invalid_nm.to_owned()
33        }
34    }
35}
36
37
38impl fmt::Display for InvalidDcNameError {
39    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
40        write!(f, "InvalidDcNameError({})", self.invalid_value)
41    }
42}
43
44impl Error for InvalidDcNameError {
45    fn description(&self) -> &str {
46        "Not a valid DCName"
47    }
48}
49
50impl FromStr for DcName {
51    type Err = InvalidDcNameError;
52
53    fn from_str(s: &str) -> Result<Self, Self::Err> {
54        match s {
55            "MyOwn" => Ok(DcName::MyOwn),
56            "Amazon" => Ok(DcName::Amazon),
57            _ => Err(InvalidDcNameError::new(s))
58        }
59    }
60}
61
62impl From<DcName> for String {
63    fn from(s: DcName) -> Self {
64        match s {
65            DcName::MyOwn => MY_OWN.to_owned(),
66            DcName::Amazon => AMAZON.to_owned()
67        }
68    }
69}
70
71impl<'a> From<&'a DcName> for String {
72    fn from(s: &'a DcName) -> Self {
73        match s {
74            &DcName::MyOwn => MY_OWN.to_owned(),
75            &DcName::Amazon => AMAZON.to_owned()
76        }
77    }
78}
79
80impl Serialize for DcName {
81    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error> where
82        S: Serializer {
83        serializer.serialize_str(String::from(self).as_ref())
84    }
85}
86
87impl<'de> Deserialize<'de> for DcName {
88    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error> where
89        D: Deserializer<'de> {
90        struct DcNameVisitor;
91
92        impl<'de> Visitor<'de> for DcNameVisitor {
93            type Value = DcName;
94
95            fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
96                let values = DcName::values()
97                    .iter()
98                    .fold(String::new(), |mut acc, v| {
99                        acc.push_str(String::from(v).as_ref());
100                        acc
101                    });
102
103                formatter.write_fmt(format_args!("Expecting {}", values))
104            }
105
106            fn visit_str<E>(self, v: &str) -> Result<Self::Value, E> where
107                E: DeError {
108
109                DcName::from_str(v)
110                    .map_err(|err| E::custom(format!("{}", err)))
111            }
112        }
113
114        deserializer.deserialize_str(DcNameVisitor)
115    }
116}
117
118#[cfg(test)]
119mod test {
120    use super::*;
121
122    #[test]
123    fn test_from_str() {
124        assert_eq!(DcName::Amazon, DcName::from_str(AMAZON).unwrap());
125        assert_eq!(DcName::MyOwn, DcName::from_str(MY_OWN).unwrap());
126    }
127
128    #[test]
129    #[should_panic]
130    fn test_from_str_invalid() {
131        DcName::from_str("sfd2ef").unwrap();
132    }
133
134    #[test]
135    fn test_to_string() {
136        assert_eq!(AMAZON.to_owned(), String::from(DcName::Amazon));
137        assert_eq!(MY_OWN.to_owned(), String::from(DcName::MyOwn));
138    }
139}
140