1 module dhtags.tags;
2 
3 public import dhtags.tags.bundle;
4 public import dhtags.tags.tag : Tag;
5 public import dhtags.tags.define : DefineTag;
6 
7 unittest {
8    /** Tag content should allow more nested tags */
9    assert(
10       div(div(span("Hello!"))).toString
11       == "<div><div><span>Hello!</span></div></div>"
12    );
13 
14    /** Tag content should allow a list of tags */
15    assert(
16       div(span, a, form(input)).toString
17       == "<div><span></span><a></a><form><input></form></div>"
18    );
19 }
20 
21 unittest {
22    import dhtags.utils.html : stripMargin;
23 
24    /** Defining custom tags should be possible */
25 
26    mixin DefineTag!("ShoppingList");
27    mixin DefineTag!("Item");
28    mixin DefineTag!("Name");
29    mixin DefineTag!("Quantity");
30 
31    assert(
32       ShoppingList(
33          Item(
34             Name("Orange"),
35             Quantity(2)
36          ),
37          Item(
38             Name("Milk"),
39             Quantity(5)
40          )
41       ).toString ==
42       `<ShoppingList>
43          <Item>
44             <Name>Orange</Name>
45             <Quantity>2</Quantity>
46          </Item>
47          <Item>
48             <Name>Milk</Name>
49             <Quantity>5</Quantity>
50          </Item>
51       </ShoppingList>
52       `.stripMargin
53    );
54 }
55 
56 unittest {
57    import dhtags.utils.html : stripMargin;
58    import std.algorithm : map;
59 
60    /** Tag content should allow an range of tags */
61    assert(
62       div(
63          ul(
64             ["Coffee", "Eggs", "Bacon"].map!(x => li(x))
65          )
66       ).toString ==
67       "<div>
68          <ul>
69             <li>Coffee</li>
70             <li>Eggs</li>
71             <li>Bacon</li>
72          </ul>
73       </div>".stripMargin
74    );
75 
76    /** Tag content should allow an range of strings */
77    assert(
78       div(
79          ["Coffee", "Eggs", "Bacon"].map!(x => div("More " ~ x))
80       ).toString ==
81       "<div>
82          <div>More Coffee</div>
83          <div>More Eggs</div>
84          <div>More Bacon</div>
85       </div>".stripMargin
86    );
87 
88    /** Tag content should allow a range of built-in types */
89    assert(
90       div([1, 2, 3].map!(x => span(x + 1))).toString ==
91       "<div>
92          <span>2</span>
93          <span>3</span>
94          <span>4</span>
95       </div>".stripMargin
96    );
97 }
98 
99 unittest {
100    import dhtags.utils.html : stripMargin;
101 
102    /** Tag content should allow an array of tags */
103    Tag[2] ps = [p("Hello!"), p("Nice to meet you.")];
104    assert(
105       div(ps).toString ==
106       "<div>
107          <p>Hello!</p>
108          <p>Nice to meet you.</p>
109       </div>".stripMargin
110    );
111 
112    /** Tag content should allow an array of strings */
113    string[2] content = ["Hello!", " Nice to meet you."];
114    assert(
115       div(content).toString ==
116       "<div>Hello! Nice to meet you.</div>"
117    );
118 
119    /** Tag content should allow an array of built-in types */
120    int[3] numbers = [1, 2, 3];
121    assert(
122       div(numbers).toString ==
123       "<div>123</div>"
124    );
125 }
126 
127 unittest {
128    import dhtags.tags : div;
129 
130    /** Tag content should by default be escaped */
131    assert(
132       div(`"Hello <b>&</b> Goodbye"`).toString ==
133       "<div>&quot;Hello &lt;b&gt;&amp;&lt;/b&gt; Goodbye&quot;</div>"
134    );
135 
136    /** Unescaped strings should also be possible */
137    assert(
138       div(`"Hello <b>&</b> Goodbye"`).toString(false) ==
139       `<div>"Hello <b>&</b> Goodbye"</div>`
140    );
141 }
142 
143 unittest {
144    import dhtags.utils.html : stripMargin;
145 
146    /** Void tags should not have a closing tag */
147    assert(
148       div(base, hr, br, wbr, area, img, track, embed, param, source, col, input, keygen).toString ==
149       "<div>
150          <base>
151          <hr>
152          <br>
153          <wbr>
154          <area>
155          <img>
156          <track>
157          <embed>
158          <param>
159          <source>
160          <col>
161          <input>
162          <keygen>
163       </div>".stripMargin
164    );
165 }
166 
167 unittest {
168    /** Tag 'html' should not include a DOCTYPE */
169    assert(html.toString == "<html></html>");
170 
171    /** Tag 'htmlWithDoctype' should include a DOCTYPE */
172    assert(htmlWithDoctype.toString == "<!DOCTYPE html><html></html>");
173 }