1use ip_in_subnet::iface_in_subnet;
2use phonenumber::country;
3use phonenumber::country::Id;
4use serde::{Deserialize, Serialize};
5
6pub fn clean_str_parse_country(country_code: &str, str: &str) -> String {
7 let id = country_code.parse().unwrap_or_else(|_| country::GB);
8 clean_str(id, str)
9}
10
11pub fn clean_str(country: Id, str: &str) -> String {
12 let clean: String = str
13 .replace("+", "")
14 .replace("<sip:", "")
15 .replace(">", "")
16 .split(":")
17 .next()
18 .unwrap_or(str)
19 .into();
20
21 parse_number(country, clean.clone())
22}
23
24pub fn format_number(str: &str, country_code: &str, format: NumberFormat) -> String {
25 let clean_str = clean_str_parse_country(country_code, str);
26 let plus_string = ["+", clean_str.as_str()].join("");
27 match format {
28 NumberFormat::National => national_number(clean_str, country_code),
29 NumberFormat::E164 => clean_str,
30 NumberFormat::E164Plus => plus_string,
31 }
32}
33
34fn national_number(str: String, country_code: &str) -> String {
35 let id = country_code.parse().unwrap_or_else(|_| country::GB);
36 parse_number(id, str)
37}
38
39fn parse_number(country: Id, clean: String) -> String {
40 match phonenumber::parse(Some(country), &clean) {
41 Ok(number) => {
42 let valid = phonenumber::is_valid(&number);
43 if valid {
44 format!("{}{}", number.code().value(), number.national().value())
45 } else {
46 clean
47 }
48 }
49 Err(_) => clean,
50 }
51}
52
53pub fn ip_in_subnet(ip: &str, subnet: &str) -> bool {
54 ip == subnet || iface_in_subnet(ip, subnet).unwrap_or_else(|_| false)
55}
56
57#[derive(Serialize, Deserialize, Clone)]
58pub enum NumberFormat {
59 #[serde(rename = "national")]
60 National,
61 #[serde(rename = "e164")]
62 E164,
63 #[serde(rename = "e164p")]
64 E164Plus,
65}