diff --git a/src/htmlnode.py b/src/htmlnode.py new file mode 100644 index 0000000..bd672ff --- /dev/null +++ b/src/htmlnode.py @@ -0,0 +1,58 @@ +class HTMLNode: + def __init__(self, tag=None, value=None, children=None, props=None) -> None: + self.tag = tag + self.value = value + self.children = children + self.props = props + + def to_html(self): + raise NotImplementedError("to_html method not implemented") + + def props_to_html(self): + props = "" + + if self.props is None: + return props + + for key in self.props: + props += f" {key}=\"{self.props[key]}\"" + + return props + + def __repr__(self): + return f"HTMLNode({self.tag}, {self.value}, {self.children}, {self.props})" + +class LeafNode(HTMLNode): + def __init__(self, tag=None, value=None, props=None) -> None: + super().__init__(tag, value, None, props) + + def to_html(self): + if self.value is None: + raise ValueError("Invalid HTML: no value") + if self.tag is None: + return self.value + props = self.props_to_html() + return f"<{self.tag}{props}>{self.value}" + + def __repr__(self): + return f"LeafNode({self.tag}, {self.value}, {self.props})" + + +class ParentNode(HTMLNode): + def __init__(self, tag=None, children=None, props=None) -> None: + super().__init__(tag, None, children, props) + + def to_html(self): + if self.tag is None: + raise ValueError("No tag specified") + if self.children is None: + raise ValueError("No children specified") + + html = f"<{self.tag}{self.props_to_html()}>" + + for child in self.children: + html+=child.to_html() + + html += f"" + + return html \ No newline at end of file diff --git a/src/test_htmlnode.py b/src/test_htmlnode.py new file mode 100644 index 0000000..21eb358 --- /dev/null +++ b/src/test_htmlnode.py @@ -0,0 +1,72 @@ +import unittest +from htmlnode import LeafNode, ParentNode, HTMLNode + + +class TestHTMLNode(unittest.TestCase): + def test_to_html_props(self): + node = HTMLNode( + "div", + "Hello, world!", + None, + {"class": "greeting", "href": "https://boot.dev"}, + ) + self.assertEqual( + node.props_to_html(), + ' class="greeting" href="https://boot.dev"', + ) + + def test_to_html_no_children(self): + node = LeafNode("p", "Hello, world!") + self.assertEqual(node.to_html(), "

Hello, world!

") + + def test_to_html_no_tag(self): + node = LeafNode(None, "Hello, world!") + self.assertEqual(node.to_html(), "Hello, world!") + + def test_to_html_with_children(self): + child_node = LeafNode("span", "child") + parent_node = ParentNode("div", [child_node]) + self.assertEqual(parent_node.to_html(), "
child
") + + def test_to_html_with_grandchildren(self): + grandchild_node = LeafNode("b", "grandchild") + child_node = ParentNode("span", [grandchild_node]) + parent_node = ParentNode("div", [child_node]) + self.assertEqual( + parent_node.to_html(), + "
grandchild
", + ) + + def test_to_html_many_children(self): + node = ParentNode( + "p", + [ + LeafNode("b", "Bold text"), + LeafNode(None, "Normal text"), + LeafNode("i", "italic text"), + LeafNode(None, "Normal text"), + ], + ) + self.assertEqual( + node.to_html(), + "

Bold textNormal textitalic textNormal text

", + ) + + def test_headings(self): + node = ParentNode( + "h2", + [ + LeafNode("b", "Bold text"), + LeafNode(None, "Normal text"), + LeafNode("i", "italic text"), + LeafNode(None, "Normal text"), + ], + ) + self.assertEqual( + node.to_html(), + "

Bold textNormal textitalic textNormal text

", + ) + + +if __name__ == "__main__": + unittest.main() \ No newline at end of file