1extern crate alloc;
4
5mod error;
6
7pub use self::error::*;
8use muffy_document::html::Element;
9use muffy_validation_macro::html;
10
11html! {}
12
13#[cfg(test)]
14mod tests {
15 use super::*;
16 use muffy_document::html::Node;
17 use std::sync::Arc;
18
19 fn create_element(
20 name: &str,
21 attributes: Vec<(&str, &str)>,
22 children: Vec<Element>,
23 ) -> Element {
24 Element::new(
25 name.to_owned(),
26 attributes
27 .into_iter()
28 .map(|(k, v)| (k.to_owned(), v.to_owned()))
29 .collect(),
30 children
31 .into_iter()
32 .map(|e| Arc::new(Node::Element(e)))
33 .collect(),
34 )
35 }
36
37 #[test]
38 fn validate_invalid_element_name() {
39 let element = create_element("invalid", vec![], vec![]);
40
41 assert_eq!(
42 validate_element(&element),
43 Err(ValidationError::UnknownTag("invalid".to_owned()))
44 );
45 }
46
47 mod div {
48 use super::*;
49
50 #[test]
51 fn validate_valid_element() {
52 let element = create_element("div", vec![], vec![]);
53
54 assert_eq!(validate_element(&element), Ok(()));
55 }
56
57 #[test]
58 fn validate_valid_attributes() {
59 let element = create_element("div", vec![("id", "foo"), ("class", "bar")], vec![]);
60
61 assert_eq!(validate_element(&element), Ok(()));
62 }
63
64 #[test]
65 fn validate_invalid_attribute() {
66 let element = create_element("div", vec![("invalid", "foo")], vec![]);
67
68 assert_eq!(
69 validate_element(&element),
70 Err(ValidationError::InvalidElement {
71 attributes: [("invalid".into(), [AttributeError::NotAllowed].into())].into(),
72 children: Default::default(),
73 })
74 );
75 }
76
77 #[test]
78 fn validate_multiple_invalid_attributes() {
79 let element = create_element(
80 "div",
81 vec![("invalid-one", "foo"), ("invalid-two", "bar")],
82 vec![],
83 );
84
85 assert_eq!(
86 validate_element(&element),
87 Err(ValidationError::InvalidElement {
88 attributes: [
89 ("invalid-one".into(), [AttributeError::NotAllowed].into()),
90 ("invalid-two".into(), [AttributeError::NotAllowed].into()),
91 ]
92 .into(),
93 children: Default::default(),
94 })
95 );
96 }
97
98 #[test]
99 fn validate_valid_child() {
100 let element = create_element("div", vec![], vec![create_element("p", vec![], vec![])]);
101
102 assert_eq!(validate_element(&element), Ok(()));
103 }
104 }
105
106 mod p {
107 use super::*;
108
109 #[test]
110 fn validate_valid_element() {
111 let element = create_element("p", vec![], vec![]);
112
113 assert_eq!(validate_element(&element), Ok(()));
114 }
115
116 #[test]
117 fn validate_invalid_child() {
118 let element = create_element("p", vec![], vec![create_element("div", vec![], vec![])]);
119
120 assert_eq!(
121 validate_element(&element),
122 Err(ValidationError::InvalidElement {
123 attributes: Default::default(),
124 children: [("div".into(), [ChildError::NotAllowed].into())].into(),
125 })
126 );
127 }
128
129 #[test]
130 fn validate_multiple_invalid_children() {
131 let element = create_element(
132 "p",
133 vec![],
134 vec![
135 create_element("div", vec![], vec![]),
136 create_element("table", vec![], vec![]),
137 ],
138 );
139
140 assert_eq!(
141 validate_element(&element),
142 Err(ValidationError::InvalidElement {
143 attributes: Default::default(),
144 children: [
145 ("div".into(), [ChildError::NotAllowed].into()),
146 ("table".into(), [ChildError::NotAllowed].into()),
147 ]
148 .into(),
149 })
150 );
151 }
152 }
153
154 mod html {
155 use super::*;
156
157 #[test]
158 fn validate_valid_element() {
159 let element = create_element("html", vec![], vec![]);
160
161 assert_eq!(validate_element(&element), Ok(()));
162 }
163
164 #[test]
165 fn validate_valid_children() {
166 let element = create_element(
167 "html",
168 vec![],
169 vec![
170 create_element("head", vec![], vec![]),
171 create_element("body", vec![], vec![]),
172 ],
173 );
174
175 assert_eq!(validate_element(&element), Ok(()));
176 }
177 }
178
179 mod head {
180 use super::*;
181
182 #[test]
183 fn validate_valid_child() {
184 let element = create_element(
185 "head",
186 vec![],
187 vec![create_element("title", vec![], vec![])],
188 );
189
190 assert_eq!(validate_element(&element), Ok(()));
191 }
192
193 #[test]
194 fn validate_invalid_child() {
195 let element = create_element("head", vec![], vec![create_element("p", vec![], vec![])]);
196
197 assert_eq!(
198 validate_element(&element),
199 Err(ValidationError::InvalidElement {
200 attributes: Default::default(),
201 children: [("p".into(), [ChildError::NotAllowed].into())].into(),
202 })
203 );
204 }
205 }
206
207 mod title {
208 use super::*;
209
210 #[test]
211 fn validate_invalid_child() {
212 let element =
213 create_element("title", vec![], vec![create_element("div", vec![], vec![])]);
214
215 assert_eq!(
216 validate_element(&element),
217 Err(ValidationError::InvalidElement {
218 attributes: Default::default(),
219 children: [("div".into(), [ChildError::NotAllowed].into())].into(),
220 })
221 );
222 }
223 }
224
225 mod ul {
226 use super::*;
227
228 #[test]
229 fn validate_valid_child() {
230 let element = create_element("ul", vec![], vec![create_element("li", vec![], vec![])]);
231
232 assert_eq!(validate_element(&element), Ok(()));
233 }
234
235 #[test]
236 fn validate_invalid_child() {
237 let element = create_element("ul", vec![], vec![create_element("p", vec![], vec![])]);
238
239 assert_eq!(
240 validate_element(&element),
241 Err(ValidationError::InvalidElement {
242 attributes: Default::default(),
243 children: [("p".into(), [ChildError::NotAllowed].into())].into(),
244 })
245 );
246 }
247 }
248
249 mod table {
250 use super::*;
251
252 #[test]
253 fn validate_valid_child() {
254 let element =
255 create_element("table", vec![], vec![create_element("tr", vec![], vec![])]);
256
257 assert_eq!(validate_element(&element), Ok(()));
258 }
259
260 #[test]
261 fn validate_invalid_child() {
262 let element =
263 create_element("table", vec![], vec![create_element("p", vec![], vec![])]);
264
265 assert_eq!(
266 validate_element(&element),
267 Err(ValidationError::InvalidElement {
268 attributes: Default::default(),
269 children: [("p".into(), [ChildError::NotAllowed].into())].into(),
270 })
271 );
272 }
273 }
274
275 mod tr {
276 use super::*;
277
278 #[test]
279 fn validate_valid_children() {
280 let element = create_element(
281 "tr",
282 vec![],
283 vec![
284 create_element("th", vec![], vec![]),
285 create_element("td", vec![], vec![]),
286 ],
287 );
288
289 assert_eq!(validate_element(&element), Ok(()));
290 }
291 }
292
293 mod form {
294 use super::*;
295
296 #[test]
297 fn validate_valid_attributes() {
298 let element = create_element("form", vec![("action", "/"), ("method", "post")], vec![]);
299
300 assert_eq!(validate_element(&element), Ok(()));
301 }
302
303 #[test]
304 fn validate_valid_child() {
305 let element = create_element(
306 "form",
307 vec![],
308 vec![create_element("input", vec![], vec![])],
309 );
310
311 assert_eq!(validate_element(&element), Ok(()));
312 }
313 }
314
315 mod img {
316 use super::*;
317
318 #[test]
319 fn validate_valid_attributes() {
320 let element = create_element(
321 "img",
322 vec![("src", "img.png"), ("alt", "description")],
323 vec![],
324 );
325
326 assert_eq!(validate_element(&element), Ok(()));
327 }
328 }
329
330 mod video {
331 use super::*;
332
333 #[test]
334 fn validate_valid_attributes() {
335 let element =
336 create_element("video", vec![("src", "vid.mp4"), ("controls", "")], vec![]);
337
338 assert_eq!(validate_element(&element), Ok(()));
339 }
340
341 #[test]
342 fn validate_valid_child() {
343 let element = create_element(
344 "video",
345 vec![],
346 vec![create_element("track", vec![], vec![])],
347 );
348
349 assert_eq!(validate_element(&element), Ok(()));
350 }
351 }
352
353 mod meta {
354 use super::*;
355
356 #[test]
357 fn validate_valid_name_content() {
358 let element = create_element(
359 "meta",
360 vec![("name", "description"), ("content", "stuff")],
361 vec![],
362 );
363
364 assert_eq!(validate_element(&element), Ok(()));
365 }
366
367 #[test]
368 fn validate_valid_charset() {
369 let element = create_element("meta", vec![("charset", "utf-8")], vec![]);
370
371 assert_eq!(validate_element(&element), Ok(()));
372 }
373
374 #[test]
375 fn validate_valid_property() {
376 let element = create_element("meta", vec![("property", "og:image")], vec![]);
377
378 assert_eq!(validate_element(&element), Ok(()));
379 }
380 }
381
382 mod link {
383 use super::*;
384
385 #[test]
386 fn validate_valid_attributes() {
387 let element = create_element(
388 "link",
389 vec![("rel", "stylesheet"), ("href", "style.css")],
390 vec![],
391 );
392
393 assert_eq!(validate_element(&element), Ok(()));
394 }
395 }
396}