messagebird_async/sms/
originator.rs1use super::*;
2
3use serde::de::{self, Deserialize, Deserializer, Unexpected, Visitor};
4
5use std::fmt;
6
7use regex::Regex;
8
9#[derive(Debug, Clone, Serialize, Deserialize, Eq, PartialEq)]
12pub struct TelephoneNumber(pub String);
13
14impl TelephoneNumber {
15 pub fn as_str(&self) -> &str {
16 self.0.as_str()
17 }
18}
19
20impl FromStr for TelephoneNumber {
21 type Err = MessageBirdError;
22 fn from_str(s: &str) -> Result<Self, Self::Err> {
23 lazy_static! {
24 static ref RE: Regex = Regex::new(r"^\+?[1-9][0-9]+$").unwrap();
25 }
26 if RE.is_match(s) {
27 Ok(TelephoneNumber(String::from(s)))
28 } else {
29 Err(MessageBirdError::FormatError {
30 chunk: String::from(s),
31 })
32 }
33 }
34}
35
36impl From<u64> for TelephoneNumber {
37 fn from(raw: u64) -> Self {
39 TelephoneNumber(raw.to_string())
40 }
41}
42
43#[derive(Debug, Clone, Serialize, Deserialize, Eq, PartialEq)]
45pub struct AlphaNumeric(pub String);
46
47impl AlphaNumeric {
48 pub fn as_str(&self) -> &str {
49 self.0.as_str()
50 }
51}
52
53impl FromStr for AlphaNumeric {
54 type Err = MessageBirdError;
55 fn from_str(s: &str) -> Result<Self, Self::Err> {
56 lazy_static! {
57 static ref RE: Regex = Regex::new(r"^[A-Za-z0-9_-]+$").unwrap();
58 }
59 if RE.is_match(s) {
60 Ok(AlphaNumeric(String::from(s)))
61 } else {
62 Err(MessageBirdError::FormatError {
63 chunk: String::from(s),
64 })
65 }
66 }
67}
68
69#[derive(Debug, Clone, Serialize, Eq, PartialEq)]
74#[serde(rename_all = "camelCase")]
75#[serde(untagged)]
76pub enum Originator {
77 TelephoneNumber(TelephoneNumber),
78 Other(AlphaNumeric),
79}
80
81impl Originator {
82 pub fn as_str(&self) -> &str {
83 match self {
84 Originator::TelephoneNumber(ref telephonenumber) => telephonenumber.as_str(),
85 Originator::Other(ref alphanumeric) => alphanumeric.as_str(),
86 }
87 }
88}
89
90impl Default for Originator {
91 fn default() -> Self {
92 AlphaNumeric::from_str("inbox").unwrap().into()
93 }
94}
95
96impl FromStr for Originator {
97 type Err = MessageBirdError;
98 fn from_str(s: &str) -> Result<Self, Self::Err> {
99 TelephoneNumber::from_str(s)
100 .and_then(|telephonenumber| Ok(Originator::TelephoneNumber(telephonenumber)))
101 .or_else(|_e| {
102 AlphaNumeric::from_str(s)
103 .and_then(|alphanumeric| Ok(Originator::Other(alphanumeric)))
104 })
105 }
106}
107
108impl From<u64> for Originator {
109 fn from(raw: u64) -> Self {
110 Originator::TelephoneNumber(raw.into())
111 }
112}
113
114impl ToString for Originator {
124 fn to_string(&self) -> String {
125 serde_plain::to_string(self).unwrap()
126 }
127}
128
129impl From<TelephoneNumber> for Originator {
130 fn from(telephonenumber: TelephoneNumber) -> Self {
131 Originator::TelephoneNumber(telephonenumber)
132 }
133}
134
135impl From<AlphaNumeric> for Originator {
136 fn from(alphanumeric: AlphaNumeric) -> Self {
137 Originator::Other(alphanumeric)
138 }
139}
140
141struct OriginatorVisitor;
142
143impl<'de> Visitor<'de> for OriginatorVisitor {
144 type Value = Originator;
145
146 fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
147 formatter.write_str("a valid originator")
148 }
149
150 fn visit_str<E>(self, value: &str) -> Result<Self::Value, E>
151 where
152 E: de::Error,
153 {
154 Originator::from_str(value)
155 .map_err(|_e| de::Error::invalid_value(Unexpected::Str(value), &self))
156 }
157}
158
159impl<'de> Deserialize<'de> for Originator {
160 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
161 where
162 D: Deserializer<'de>,
163 {
164 deserializer.deserialize_str(OriginatorVisitor)
165 }
166}
167
168#[cfg(test)]
169mod test {
170 use super::*;
171 static RAW: &str = r#"
172"123456789"
173"#;
174
175 deser_roundtrip!(originator_deser, Originator, RAW);
176 serde_roundtrip!(
177 originator_serde,
178 Originator,
179 TelephoneNumber::from_str("49123456789").unwrap().into()
180 );
181}