yuin / goldmark

:trophy: A markdown parser written in Go. Easy to extend, standard(CommonMark) compliant, well structured.
MIT License
3.74k stars 259 forks source link

make RenderAttributes() accept both []byte and string #448

Closed movsb closed 8 months ago

movsb commented 8 months ago

The problem:

Since the Value of an Attribute is defined as of type interface{}, I may think that it accepts all usual types (such as []byte, string, and even numbers).

The problem is that when I SetAttributeString(`target`, `_blank`) of a Link, the RenderAttributes function force the Value to be []byte, which results in runtime panic.

https://github.com/yuin/goldmark/blob/ce6424aa0e15504f675a0f224972d3c8d0c86654/renderer/html/html.go#L789

The solution:

I switch cased the type and rewritten the code as below:

        var value []byte
        switch typed := attr.Value.(type) {
        case []byte:
            value = typed
        case string:
            value = util.StringToReadOnlyBytes(typed)
        }
        _, _ = w.Write(util.EscapeHTML(value))

I cannot assume that people don't force the Value to be of type []byte, or that they already know that, and while SetAttributeString, use []byte. May god bless all those who switch case Node::AttributeString()'s return value.

yuin commented 8 months ago

goldmark is designed to be able to support various output formats by custom renderer implementations, so attribute values designed to be able to have any kind of values.

In HTML outputs, attribute values should be rendered as a string.