xmpp_parsers/
server_info.rs1use crate::data_forms::{DataForm, DataFormType, Field, FieldType};
7use crate::ns;
8use xso::error::Error;
9
10#[derive(Debug, Clone, PartialEq, Default)]
12pub struct ServerInfo {
13 pub abuse: Vec<String>,
15
16 pub admin: Vec<String>,
18
19 pub feedback: Vec<String>,
21
22 pub sales: Vec<String>,
24
25 pub security: Vec<String>,
27
28 pub support: Vec<String>,
30}
31
32impl TryFrom<DataForm> for ServerInfo {
33 type Error = Error;
34
35 fn try_from(form: DataForm) -> Result<ServerInfo, Error> {
36 if form.type_ != DataFormType::Result_ {
37 return Err(Error::Other("Wrong type of form."));
38 }
39 if form.form_type() != Some(ns::SERVER_INFO) {
40 return Err(Error::Other("Wrong FORM_TYPE for form."));
41 }
42 let mut server_info = ServerInfo::default();
43 for field in form.fields {
44 if field.var.as_deref().unwrap_or("") == "FORM_TYPE" {
45 continue;
46 }
47 if field.type_ != FieldType::ListMulti {
48 return Err(Error::Other("Field is not of the required type."));
49 }
50 if field.var.as_deref() == Some("abuse-addresses") {
51 server_info.abuse = field.values;
52 } else if field.var.as_deref() == Some("admin-addresses") {
53 server_info.admin = field.values;
54 } else if field.var.as_deref() == Some("feedback-addresses") {
55 server_info.feedback = field.values;
56 } else if field.var.as_deref() == Some("sales-addresses") {
57 server_info.sales = field.values;
58 } else if field.var.as_deref() == Some("security-addresses") {
59 server_info.security = field.values;
60 } else if field.var.as_deref() == Some("support-addresses") {
61 server_info.support = field.values;
62 } else {
63 return Err(Error::Other("Unknown form field var."));
64 }
65 }
66
67 Ok(server_info)
68 }
69}
70
71impl From<ServerInfo> for DataForm {
72 fn from(server_info: ServerInfo) -> DataForm {
73 let mut form = DataForm {
74 type_: DataFormType::Result_,
75 title: None,
76 instructions: None,
77 fields: vec![
78 generate_address_field("abuse-addresses", server_info.abuse),
79 generate_address_field("admin-addresses", server_info.admin),
80 generate_address_field("feedback-addresses", server_info.feedback),
81 generate_address_field("sales-addresses", server_info.sales),
82 generate_address_field("security-addresses", server_info.security),
83 generate_address_field("support-addresses", server_info.support),
84 ],
85 };
86 form.set_form_type(ns::SERVER_INFO.to_owned());
87 form
88 }
89}
90
91pub fn generate_address_field<S: Into<String>>(var: S, values: Vec<String>) -> Field {
93 Field {
94 var: Some(var.into()),
95 type_: FieldType::ListMulti,
96 label: None,
97 required: false,
98 desc: None,
99 options: vec![],
100 values,
101 media: vec![],
102 validate: None,
103 }
104}
105
106#[cfg(test)]
107mod tests {
108 use super::*;
109
110 #[cfg(target_pointer_width = "32")]
111 #[test]
112 fn test_size() {
113 assert_size!(ServerInfo, 72);
114 }
115
116 #[cfg(target_pointer_width = "64")]
117 #[test]
118 fn test_size() {
119 assert_size!(ServerInfo, 144);
120 }
121
122 #[test]
123 fn test_simple() {
124 let form = DataForm::new(
125 DataFormType::Result_,
126 ns::SERVER_INFO,
127 vec![
128 Field::new("abuse-addresses", FieldType::ListMulti),
129 Field::new("admin-addresses", FieldType::ListMulti)
130 .with_value("xmpp:admin@foo.bar")
131 .with_value("https://foo.bar/chat/")
132 .with_value("mailto:admin@foo.bar"),
133 Field::new("feedback-addresses", FieldType::ListMulti),
134 Field::new("sales-addresses", FieldType::ListMulti),
135 Field::new("security-addresses", FieldType::ListMulti)
136 .with_value("xmpp:security@foo.bar")
137 .with_value("mailto:security@foo.bar"),
138 Field::new("support-addresses", FieldType::ListMulti)
139 .with_value("mailto:support@foo.bar"),
140 ],
141 );
142
143 let server_info = ServerInfo {
144 abuse: vec![],
145 admin: vec![
146 String::from("xmpp:admin@foo.bar"),
147 String::from("https://foo.bar/chat/"),
148 String::from("mailto:admin@foo.bar"),
149 ],
150 feedback: vec![],
151 sales: vec![],
152 security: vec![
153 String::from("xmpp:security@foo.bar"),
154 String::from("mailto:security@foo.bar"),
155 ],
156 support: vec![String::from("mailto:support@foo.bar")],
157 };
158
159 assert_eq!(ServerInfo::try_from(form).unwrap(), server_info);
161 }
162}