From 4bacac4d4879f7ec64e6d981a7875f3d0fb85af5 Mon Sep 17 00:00:00 2001 From: Stuart George Date: Mon, 20 Jan 2025 10:18:43 +0000 Subject: [PATCH] add void closer tags to allow either > or /> --- element.go | 48 ++++++++++++++++++++++-------------------------- element_test.go | 29 +++++++++++++++-------------- 2 files changed, 37 insertions(+), 40 deletions(-) diff --git a/element.go b/element.go index 590d69d..4965a4f 100644 --- a/element.go +++ b/element.go @@ -4,7 +4,6 @@ import ( "context" "github.com/a-h/templ" "io" - "slices" ) type ( @@ -30,21 +29,21 @@ const ( ) var ( - // VoidElements is a list of HTML void elements, these are all self-closing. - VoidElements = []string{ - "area", - "base", - "br", - "col", - "embed", - "hr", - "img", - "input", - "link", - "meta", - "source", - "track", - "wbr", + // VoidElements is a list of HTML void elements, these dont have children or content. + VoidElements = map[string]string{ + "area": ">", + "base": ">", + "br": ">", + "col": ">", + "embed": ">", + "hr": ">", + "img": ">", + "input": ">", + "link": ">", + "meta": ">", + "source": ">", + "track": ">", + "wbr": ">", } // NA is an empty set of attributes. NA = Attrs{} @@ -359,7 +358,11 @@ func (e *Element) AddChildren(children ...templ.Component) { // Render renders the Element to the writer. func (e *Element) Render(ctx context.Context, w io.Writer) error { - isVoid := slices.Contains(VoidElements, e.Tag) + closer := ">" + voidCloser, isVoid := VoidElements[e.Tag] + if isVoid { + closer = voidCloser + } if e.Tag != "" { if _, err := io.WriteString(w, "<"+e.Tag); err != nil { @@ -370,15 +373,8 @@ func (e *Element) Render(ctx context.Context, w io.Writer) error { return err } } - - if isVoid { - if _, err := io.WriteString(w, " />"); err != nil { - return err - } - } else { - if _, err := io.WriteString(w, ">"); err != nil { - return err - } + if _, err := io.WriteString(w, closer); err != nil { + return err } } diff --git a/element_test.go b/element_test.go index 2bedf5f..81f690f 100644 --- a/element_test.go +++ b/element_test.go @@ -97,24 +97,25 @@ func TestElementTags(t *testing.T) { // Test rendering a void Element's. func TestRenderVoidElements(t *testing.T) { + attr := Attrs{"foo": "bar"} tests := []struct { name string nodeFunc func() *Element expected string }{ - {"area", func() *Element { return &Element{Tag: "area"} }, ""}, - {"base", func() *Element { return &Element{Tag: "base"} }, ""}, - {"br", func() *Element { return &Element{Tag: "br"} }, "
"}, - {"col", func() *Element { return &Element{Tag: "col"} }, ""}, - {"embed", func() *Element { return &Element{Tag: "embed"} }, ""}, - {"hr", func() *Element { return &Element{Tag: "hr"} }, "
"}, - {"img", func() *Element { return &Element{Tag: "img"} }, ""}, - {"input", func() *Element { return &Element{Tag: "input"} }, ""}, - {"link", func() *Element { return &Element{Tag: "link"} }, ""}, - {"meta", func() *Element { return &Element{Tag: "meta"} }, ""}, - {"source", func() *Element { return &Element{Tag: "source"} }, ""}, - {"track", func() *Element { return &Element{Tag: "track"} }, ""}, - {"wbr", func() *Element { return &Element{Tag: "wbr"} }, ""}, + {"area", func() *Element { return &Element{Tag: "area", Attrs: attr} }, ``}, + {"base", func() *Element { return &Element{Tag: "base", Attrs: attr} }, ``}, + {"br", func() *Element { return &Element{Tag: "br"} }, `
`}, + {"col", func() *Element { return &Element{Tag: "col", Attrs: attr} }, ``}, + {"embed", func() *Element { return &Element{Tag: "embed", Attrs: attr} }, ``}, + {"hr", func() *Element { return &Element{Tag: "hr"} }, `
`}, + {"img", func() *Element { return &Element{Tag: "img", Attrs: attr} }, ``}, + {"input", func() *Element { return &Element{Tag: "input", Attrs: attr} }, ``}, + {"link", func() *Element { return &Element{Tag: "link", Attrs: attr} }, ``}, + {"meta", func() *Element { return &Element{Tag: "meta", Attrs: attr} }, ``}, + {"source", func() *Element { return &Element{Tag: "source", Attrs: attr} }, ``}, + {"track", func() *Element { return &Element{Tag: "track", Attrs: attr} }, ``}, + {"wbr", func() *Element { return &Element{Tag: "wbr", Attrs: attr} }, ``}, } for _, tt := range tests { @@ -142,7 +143,7 @@ func TestRenderBasicElement(t *testing.T) { // Test rendering an image tag with attributes. func TestRenderImgElement(t *testing.T) { node := Img(Attrs{"src": "image.png", "alt": "Test Image"}) - expected := `Test Image` + expected := `Test Image` output := renderElement(t, node) if output != expected {