1 /**
2  * Parsing mime/XMLnamespaces files.
3  * Authors:
4  *  $(LINK2 https://github.com/FreeSlave, Roman Chistokhodov)
5  * License:
6  *  $(LINK2 http://www.boost.org/LICENSE_1_0.txt, Boost License 1.0).
7  * Copyright:
8  *  Roman Chistokhodov, 2015-2016
9  */
10 
11 module mime.files.namespaces;
12 
13 public import mime.files.common;
14 
15 private {
16     import std.algorithm;
17     import std.exception;
18     import std.range;
19     import std.traits;
20     import std.typecons;
21 }
22 
23 ///Represents one line in XMLnamespaces file.
24 alias Tuple!(string, "namespaceUri", string, "localName", string, "mimeType") NamespaceLine;
25 
26 /**
27  * Parse mime/XMLnamespaces file by line ignoring empty lines and comments.
28  * Returns:
29  *  Range of $(D NamespaceLine) tuples.
30  * Throws:
31  *  $(D mime.files.common.MimeFileException) on parsing error.
32  */
33 auto namespacesFileReader(Range)(Range byLine) if(isInputRange!Range && is(ElementType!Range : string)) {
34     return byLine.filter!(lineFilter).map!(function(string line) {
35         auto splitted = std.algorithm.splitter(line);
36         if (!splitted.empty) {
37             auto namespaceUri = splitted.front;
38             splitted.popFront();
39             if (!splitted.empty) {
40                 auto localName = splitted.front;
41                 splitted.popFront();
42                 if (!splitted.empty) {
43                     auto mimeType = splitted.front;
44                     return NamespaceLine(namespaceUri, localName, mimeType);
45                 }
46             }
47         }
48         throw new MimeFileException("Malformed namespaces file: must be 3 words per line", line);
49     });
50 }
51 
52 ///
53 unittest
54 {
55     string[] lines = ["http://www.w3.org/1999/xhtml html application/xhtml+xml", "http://www.w3.org/2000/svg svg image/svg+xml"];
56     auto expected = [NamespaceLine("http://www.w3.org/1999/xhtml", "html", "application/xhtml+xml"), NamespaceLine("http://www.w3.org/2000/svg", "svg", "image/svg+xml")];
57     assert(equal(namespacesFileReader(lines), expected));
58 
59     assertThrown!MimeFileException(namespacesFileReader(["http://www.example.org nameonly"]).array, "must throw");
60     assertThrown!MimeFileException(namespacesFileReader(["http://www.example.org"]).array, "must throw");
61 }