mapstructure icon indicating copy to clipboard operation
mapstructure copied to clipboard

StringToSliceHookFunc() bug when decoding to []byte fields

Open knadh opened this issue 2 years ago • 0 comments

package main

import (
	"log"

	"github.com/mitchellh/mapstructure"
)

func main() {
	o := struct {
		String []byte `json:"bytes"`
	}{}

	cfg := &mapstructure.DecoderConfig{
		DecodeHook: mapstructure.ComposeDecodeHookFunc(
			mapstructure.StringToSliceHookFunc(","),
		),
		Metadata:         nil,
		Result:           &o,
		WeaklyTypedInput: true,
		TagName:          "json",
	}

	decoder, err := mapstructure.NewDecoder(cfg)
	if err != nil {
		log.Fatal(err)
	}

	mp := map[string]interface{}{
		"bytes": "foo",
	}
	if err := decoder.Decode(mp); err != nil {
		log.Fatal(err)
	}

}

Produces:

2023/04/12 22:03:00 1 error(s) decoding:

* cannot parse 'bytes[0]' as uint: strconv.ParseUint: parsing "foo": invalid syntax
exit status 1

This hook func should only apply when the target field is a slice of strings. However, there is no way to figure that it's a slice of strings (and only that it's a slice) from reflect.kind. Thus, unmarshalling a string to []byte fails when this hook is used. Unsure what can be done here.

https://github.com/mitchellh/mapstructure/blob/bf980b35cac4dfd34e05254ee5aba086504c3f96/decode_hooks.go#L107

knadh avatar Apr 12 '23 16:04 knadh