1package mapstructure
2
3import (
4	"encoding/json"
5	"io"
6	"reflect"
7	"sort"
8	"strings"
9	"testing"
10)
11
12type Basic struct {
13	Vstring     string
14	Vint        int
15	Vint8       int8
16	Vint16      int16
17	Vint32      int32
18	Vint64      int64
19	Vuint       uint
20	Vbool       bool
21	Vfloat      float64
22	Vextra      string
23	vsilent     bool
24	Vdata       interface{}
25	VjsonInt    int
26	VjsonUint   uint
27	VjsonFloat  float64
28	VjsonNumber json.Number
29}
30
31type BasicPointer struct {
32	Vstring     *string
33	Vint        *int
34	Vuint       *uint
35	Vbool       *bool
36	Vfloat      *float64
37	Vextra      *string
38	vsilent     *bool
39	Vdata       *interface{}
40	VjsonInt    *int
41	VjsonFloat  *float64
42	VjsonNumber *json.Number
43}
44
45type BasicSquash struct {
46	Test Basic `mapstructure:",squash"`
47}
48
49type Embedded struct {
50	Basic
51	Vunique string
52}
53
54type EmbeddedPointer struct {
55	*Basic
56	Vunique string
57}
58
59type EmbeddedSquash struct {
60	Basic   `mapstructure:",squash"`
61	Vunique string
62}
63
64type EmbeddedPointerSquash struct {
65	*Basic  `mapstructure:",squash"`
66	Vunique string
67}
68
69type EmbeddedAndNamed struct {
70	Basic
71	Named   Basic
72	Vunique string
73}
74
75type SliceAlias []string
76
77type EmbeddedSlice struct {
78	SliceAlias `mapstructure:"slice_alias"`
79	Vunique    string
80}
81
82type ArrayAlias [2]string
83
84type EmbeddedArray struct {
85	ArrayAlias `mapstructure:"array_alias"`
86	Vunique    string
87}
88
89type SquashOnNonStructType struct {
90	InvalidSquashType int `mapstructure:",squash"`
91}
92
93type Map struct {
94	Vfoo   string
95	Vother map[string]string
96}
97
98type MapOfStruct struct {
99	Value map[string]Basic
100}
101
102type Nested struct {
103	Vfoo string
104	Vbar Basic
105}
106
107type NestedPointer struct {
108	Vfoo string
109	Vbar *Basic
110}
111
112type NilInterface struct {
113	W io.Writer
114}
115
116type NilPointer struct {
117	Value *string
118}
119
120type Slice struct {
121	Vfoo string
122	Vbar []string
123}
124
125type SliceOfAlias struct {
126	Vfoo string
127	Vbar SliceAlias
128}
129
130type SliceOfStruct struct {
131	Value []Basic
132}
133
134type SlicePointer struct {
135	Vbar *[]string
136}
137
138type Array struct {
139	Vfoo string
140	Vbar [2]string
141}
142
143type ArrayOfStruct struct {
144	Value [2]Basic
145}
146
147type Func struct {
148	Foo func() string
149}
150
151type Tagged struct {
152	Extra string `mapstructure:"bar,what,what"`
153	Value string `mapstructure:"foo"`
154}
155
156type Remainder struct {
157	A     string
158	Extra map[string]interface{} `mapstructure:",remain"`
159}
160
161type StructWithOmitEmpty struct {
162	VisibleStringField string                 `mapstructure:"visible-string"`
163	OmitStringField    string                 `mapstructure:"omittable-string,omitempty"`
164	VisibleIntField    int                    `mapstructure:"visible-int"`
165	OmitIntField       int                    `mapstructure:"omittable-int,omitempty"`
166	VisibleFloatField  float64                `mapstructure:"visible-float"`
167	OmitFloatField     float64                `mapstructure:"omittable-float,omitempty"`
168	VisibleSliceField  []interface{}          `mapstructure:"visible-slice"`
169	OmitSliceField     []interface{}          `mapstructure:"omittable-slice,omitempty"`
170	VisibleMapField    map[string]interface{} `mapstructure:"visible-map"`
171	OmitMapField       map[string]interface{} `mapstructure:"omittable-map,omitempty"`
172	NestedField        *Nested                `mapstructure:"visible-nested"`
173	OmitNestedField    *Nested                `mapstructure:"omittable-nested,omitempty"`
174}
175
176type TypeConversionResult struct {
177	IntToFloat         float32
178	IntToUint          uint
179	IntToBool          bool
180	IntToString        string
181	UintToInt          int
182	UintToFloat        float32
183	UintToBool         bool
184	UintToString       string
185	BoolToInt          int
186	BoolToUint         uint
187	BoolToFloat        float32
188	BoolToString       string
189	FloatToInt         int
190	FloatToUint        uint
191	FloatToBool        bool
192	FloatToString      string
193	SliceUint8ToString string
194	StringToSliceUint8 []byte
195	ArrayUint8ToString string
196	StringToInt        int
197	StringToUint       uint
198	StringToBool       bool
199	StringToFloat      float32
200	StringToStrSlice   []string
201	StringToIntSlice   []int
202	StringToStrArray   [1]string
203	StringToIntArray   [1]int
204	SliceToMap         map[string]interface{}
205	MapToSlice         []interface{}
206	ArrayToMap         map[string]interface{}
207	MapToArray         [1]interface{}
208}
209
210func TestBasicTypes(t *testing.T) {
211	t.Parallel()
212
213	input := map[string]interface{}{
214		"vstring":     "foo",
215		"vint":        42,
216		"vint8":       42,
217		"vint16":      42,
218		"vint32":      42,
219		"vint64":      42,
220		"Vuint":       42,
221		"vbool":       true,
222		"Vfloat":      42.42,
223		"vsilent":     true,
224		"vdata":       42,
225		"vjsonInt":    json.Number("1234"),
226		"vjsonUint":   json.Number("1234"),
227		"vjsonFloat":  json.Number("1234.5"),
228		"vjsonNumber": json.Number("1234.5"),
229	}
230
231	var result Basic
232	err := Decode(input, &result)
233	if err != nil {
234		t.Errorf("got an err: %s", err.Error())
235		t.FailNow()
236	}
237
238	if result.Vstring != "foo" {
239		t.Errorf("vstring value should be 'foo': %#v", result.Vstring)
240	}
241
242	if result.Vint != 42 {
243		t.Errorf("vint value should be 42: %#v", result.Vint)
244	}
245	if result.Vint8 != 42 {
246		t.Errorf("vint8 value should be 42: %#v", result.Vint)
247	}
248	if result.Vint16 != 42 {
249		t.Errorf("vint16 value should be 42: %#v", result.Vint)
250	}
251	if result.Vint32 != 42 {
252		t.Errorf("vint32 value should be 42: %#v", result.Vint)
253	}
254	if result.Vint64 != 42 {
255		t.Errorf("vint64 value should be 42: %#v", result.Vint)
256	}
257
258	if result.Vuint != 42 {
259		t.Errorf("vuint value should be 42: %#v", result.Vuint)
260	}
261
262	if result.Vbool != true {
263		t.Errorf("vbool value should be true: %#v", result.Vbool)
264	}
265
266	if result.Vfloat != 42.42 {
267		t.Errorf("vfloat value should be 42.42: %#v", result.Vfloat)
268	}
269
270	if result.Vextra != "" {
271		t.Errorf("vextra value should be empty: %#v", result.Vextra)
272	}
273
274	if result.vsilent != false {
275		t.Error("vsilent should not be set, it is unexported")
276	}
277
278	if result.Vdata != 42 {
279		t.Error("vdata should be valid")
280	}
281
282	if result.VjsonInt != 1234 {
283		t.Errorf("vjsonint value should be 1234: %#v", result.VjsonInt)
284	}
285
286	if result.VjsonUint != 1234 {
287		t.Errorf("vjsonuint value should be 1234: %#v", result.VjsonUint)
288	}
289
290	if result.VjsonFloat != 1234.5 {
291		t.Errorf("vjsonfloat value should be 1234.5: %#v", result.VjsonFloat)
292	}
293
294	if !reflect.DeepEqual(result.VjsonNumber, json.Number("1234.5")) {
295		t.Errorf("vjsonnumber value should be '1234.5': %T, %#v", result.VjsonNumber, result.VjsonNumber)
296	}
297}
298
299func TestBasic_IntWithFloat(t *testing.T) {
300	t.Parallel()
301
302	input := map[string]interface{}{
303		"vint": float64(42),
304	}
305
306	var result Basic
307	err := Decode(input, &result)
308	if err != nil {
309		t.Fatalf("got an err: %s", err)
310	}
311}
312
313func TestBasic_Merge(t *testing.T) {
314	t.Parallel()
315
316	input := map[string]interface{}{
317		"vint": 42,
318	}
319
320	var result Basic
321	result.Vuint = 100
322	err := Decode(input, &result)
323	if err != nil {
324		t.Fatalf("got an err: %s", err)
325	}
326
327	expected := Basic{
328		Vint:  42,
329		Vuint: 100,
330	}
331	if !reflect.DeepEqual(result, expected) {
332		t.Fatalf("bad: %#v", result)
333	}
334}
335
336// Test for issue #46.
337func TestBasic_Struct(t *testing.T) {
338	t.Parallel()
339
340	input := map[string]interface{}{
341		"vdata": map[string]interface{}{
342			"vstring": "foo",
343		},
344	}
345
346	var result, inner Basic
347	result.Vdata = &inner
348	err := Decode(input, &result)
349	if err != nil {
350		t.Fatalf("got an err: %s", err)
351	}
352	expected := Basic{
353		Vdata: &Basic{
354			Vstring: "foo",
355		},
356	}
357	if !reflect.DeepEqual(result, expected) {
358		t.Fatalf("bad: %#v", result)
359	}
360}
361
362func TestBasic_interfaceStruct(t *testing.T) {
363	t.Parallel()
364
365	input := map[string]interface{}{
366		"vstring": "foo",
367	}
368
369	var iface interface{} = &Basic{}
370	err := Decode(input, &iface)
371	if err != nil {
372		t.Fatalf("got an err: %s", err)
373	}
374
375	expected := &Basic{
376		Vstring: "foo",
377	}
378	if !reflect.DeepEqual(iface, expected) {
379		t.Fatalf("bad: %#v", iface)
380	}
381}
382
383// Issue 187
384func TestBasic_interfaceStructNonPtr(t *testing.T) {
385	t.Parallel()
386
387	input := map[string]interface{}{
388		"vstring": "foo",
389	}
390
391	var iface interface{} = Basic{}
392	err := Decode(input, &iface)
393	if err != nil {
394		t.Fatalf("got an err: %s", err)
395	}
396
397	expected := Basic{
398		Vstring: "foo",
399	}
400	if !reflect.DeepEqual(iface, expected) {
401		t.Fatalf("bad: %#v", iface)
402	}
403}
404
405func TestDecode_BasicSquash(t *testing.T) {
406	t.Parallel()
407
408	input := map[string]interface{}{
409		"vstring": "foo",
410	}
411
412	var result BasicSquash
413	err := Decode(input, &result)
414	if err != nil {
415		t.Fatalf("got an err: %s", err.Error())
416	}
417
418	if result.Test.Vstring != "foo" {
419		t.Errorf("vstring value should be 'foo': %#v", result.Test.Vstring)
420	}
421}
422
423func TestDecodeFrom_BasicSquash(t *testing.T) {
424	t.Parallel()
425
426	var v interface{}
427	var ok bool
428
429	input := BasicSquash{
430		Test: Basic{
431			Vstring: "foo",
432		},
433	}
434
435	var result map[string]interface{}
436	err := Decode(input, &result)
437	if err != nil {
438		t.Fatalf("got an err: %s", err.Error())
439	}
440
441	if _, ok = result["Test"]; ok {
442		t.Error("test should not be present in map")
443	}
444
445	v, ok = result["Vstring"]
446	if !ok {
447		t.Error("vstring should be present in map")
448	} else if !reflect.DeepEqual(v, "foo") {
449		t.Errorf("vstring value should be 'foo': %#v", v)
450	}
451}
452
453func TestDecode_Embedded(t *testing.T) {
454	t.Parallel()
455
456	input := map[string]interface{}{
457		"vstring": "foo",
458		"Basic": map[string]interface{}{
459			"vstring": "innerfoo",
460		},
461		"vunique": "bar",
462	}
463
464	var result Embedded
465	err := Decode(input, &result)
466	if err != nil {
467		t.Fatalf("got an err: %s", err.Error())
468	}
469
470	if result.Vstring != "innerfoo" {
471		t.Errorf("vstring value should be 'innerfoo': %#v", result.Vstring)
472	}
473
474	if result.Vunique != "bar" {
475		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
476	}
477}
478
479func TestDecode_EmbeddedPointer(t *testing.T) {
480	t.Parallel()
481
482	input := map[string]interface{}{
483		"vstring": "foo",
484		"Basic": map[string]interface{}{
485			"vstring": "innerfoo",
486		},
487		"vunique": "bar",
488	}
489
490	var result EmbeddedPointer
491	err := Decode(input, &result)
492	if err != nil {
493		t.Fatalf("err: %s", err)
494	}
495
496	expected := EmbeddedPointer{
497		Basic: &Basic{
498			Vstring: "innerfoo",
499		},
500		Vunique: "bar",
501	}
502	if !reflect.DeepEqual(result, expected) {
503		t.Fatalf("bad: %#v", result)
504	}
505}
506
507func TestDecode_EmbeddedSlice(t *testing.T) {
508	t.Parallel()
509
510	input := map[string]interface{}{
511		"slice_alias": []string{"foo", "bar"},
512		"vunique":     "bar",
513	}
514
515	var result EmbeddedSlice
516	err := Decode(input, &result)
517	if err != nil {
518		t.Fatalf("got an err: %s", err.Error())
519	}
520
521	if !reflect.DeepEqual(result.SliceAlias, SliceAlias([]string{"foo", "bar"})) {
522		t.Errorf("slice value: %#v", result.SliceAlias)
523	}
524
525	if result.Vunique != "bar" {
526		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
527	}
528}
529
530func TestDecode_EmbeddedArray(t *testing.T) {
531	t.Parallel()
532
533	input := map[string]interface{}{
534		"array_alias": [2]string{"foo", "bar"},
535		"vunique":     "bar",
536	}
537
538	var result EmbeddedArray
539	err := Decode(input, &result)
540	if err != nil {
541		t.Fatalf("got an err: %s", err.Error())
542	}
543
544	if !reflect.DeepEqual(result.ArrayAlias, ArrayAlias([2]string{"foo", "bar"})) {
545		t.Errorf("array value: %#v", result.ArrayAlias)
546	}
547
548	if result.Vunique != "bar" {
549		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
550	}
551}
552
553func TestDecode_EmbeddedNoSquash(t *testing.T) {
554	t.Parallel()
555
556	input := map[string]interface{}{
557		"vstring": "foo",
558		"vunique": "bar",
559	}
560
561	var result Embedded
562	err := Decode(input, &result)
563	if err != nil {
564		t.Fatalf("got an err: %s", err.Error())
565	}
566
567	if result.Vstring != "" {
568		t.Errorf("vstring value should be empty: %#v", result.Vstring)
569	}
570
571	if result.Vunique != "bar" {
572		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
573	}
574}
575
576func TestDecode_EmbeddedPointerNoSquash(t *testing.T) {
577	t.Parallel()
578
579	input := map[string]interface{}{
580		"vstring": "foo",
581		"vunique": "bar",
582	}
583
584	result := EmbeddedPointer{
585		Basic: &Basic{},
586	}
587
588	err := Decode(input, &result)
589	if err != nil {
590		t.Fatalf("err: %s", err)
591	}
592
593	if result.Vstring != "" {
594		t.Errorf("vstring value should be empty: %#v", result.Vstring)
595	}
596
597	if result.Vunique != "bar" {
598		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
599	}
600}
601
602func TestDecode_EmbeddedSquash(t *testing.T) {
603	t.Parallel()
604
605	input := map[string]interface{}{
606		"vstring": "foo",
607		"vunique": "bar",
608	}
609
610	var result EmbeddedSquash
611	err := Decode(input, &result)
612	if err != nil {
613		t.Fatalf("got an err: %s", err.Error())
614	}
615
616	if result.Vstring != "foo" {
617		t.Errorf("vstring value should be 'foo': %#v", result.Vstring)
618	}
619
620	if result.Vunique != "bar" {
621		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
622	}
623}
624
625func TestDecodeFrom_EmbeddedSquash(t *testing.T) {
626	t.Parallel()
627
628	var v interface{}
629	var ok bool
630
631	input := EmbeddedSquash{
632		Basic: Basic{
633			Vstring: "foo",
634		},
635		Vunique: "bar",
636	}
637
638	var result map[string]interface{}
639	err := Decode(input, &result)
640	if err != nil {
641		t.Fatalf("got an err: %s", err.Error())
642	}
643
644	if _, ok = result["Basic"]; ok {
645		t.Error("basic should not be present in map")
646	}
647
648	v, ok = result["Vstring"]
649	if !ok {
650		t.Error("vstring should be present in map")
651	} else if !reflect.DeepEqual(v, "foo") {
652		t.Errorf("vstring value should be 'foo': %#v", v)
653	}
654
655	v, ok = result["Vunique"]
656	if !ok {
657		t.Error("vunique should be present in map")
658	} else if !reflect.DeepEqual(v, "bar") {
659		t.Errorf("vunique value should be 'bar': %#v", v)
660	}
661}
662
663func TestDecode_EmbeddedPointerSquash_FromStructToMap(t *testing.T) {
664	t.Parallel()
665
666	input := EmbeddedPointerSquash{
667		Basic: &Basic{
668			Vstring: "foo",
669		},
670		Vunique: "bar",
671	}
672
673	var result map[string]interface{}
674	err := Decode(input, &result)
675	if err != nil {
676		t.Fatalf("got an err: %s", err.Error())
677	}
678
679	if result["Vstring"] != "foo" {
680		t.Errorf("vstring value should be 'foo': %#v", result["Vstring"])
681	}
682
683	if result["Vunique"] != "bar" {
684		t.Errorf("vunique value should be 'bar': %#v", result["Vunique"])
685	}
686}
687
688func TestDecode_EmbeddedPointerSquash_FromMapToStruct(t *testing.T) {
689	t.Parallel()
690
691	input := map[string]interface{}{
692		"Vstring": "foo",
693		"Vunique": "bar",
694	}
695
696	result := EmbeddedPointerSquash{
697		Basic: &Basic{},
698	}
699	err := Decode(input, &result)
700	if err != nil {
701		t.Fatalf("got an err: %s", err.Error())
702	}
703
704	if result.Vstring != "foo" {
705		t.Errorf("vstring value should be 'foo': %#v", result.Vstring)
706	}
707
708	if result.Vunique != "bar" {
709		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
710	}
711}
712
713func TestDecode_EmbeddedSquashConfig(t *testing.T) {
714	t.Parallel()
715
716	input := map[string]interface{}{
717		"vstring": "foo",
718		"vunique": "bar",
719		"Named": map[string]interface{}{
720			"vstring": "baz",
721		},
722	}
723
724	var result EmbeddedAndNamed
725	config := &DecoderConfig{
726		Squash: true,
727		Result: &result,
728	}
729
730	decoder, err := NewDecoder(config)
731	if err != nil {
732		t.Fatalf("err: %s", err)
733	}
734
735	err = decoder.Decode(input)
736	if err != nil {
737		t.Fatalf("got an err: %s", err)
738	}
739
740	if result.Vstring != "foo" {
741		t.Errorf("vstring value should be 'foo': %#v", result.Vstring)
742	}
743
744	if result.Vunique != "bar" {
745		t.Errorf("vunique value should be 'bar': %#v", result.Vunique)
746	}
747
748	if result.Named.Vstring != "baz" {
749		t.Errorf("Named.vstring value should be 'baz': %#v", result.Named.Vstring)
750	}
751}
752
753func TestDecodeFrom_EmbeddedSquashConfig(t *testing.T) {
754	t.Parallel()
755
756	input := EmbeddedAndNamed{
757		Basic:   Basic{Vstring: "foo"},
758		Named:   Basic{Vstring: "baz"},
759		Vunique: "bar",
760	}
761
762	result := map[string]interface{}{}
763	config := &DecoderConfig{
764		Squash: true,
765		Result: &result,
766	}
767	decoder, err := NewDecoder(config)
768	if err != nil {
769		t.Fatalf("got an err: %s", err.Error())
770	}
771
772	err = decoder.Decode(input)
773	if err != nil {
774		t.Fatalf("got an err: %s", err.Error())
775	}
776
777	if _, ok := result["Basic"]; ok {
778		t.Error("basic should not be present in map")
779	}
780
781	v, ok := result["Vstring"]
782	if !ok {
783		t.Error("vstring should be present in map")
784	} else if !reflect.DeepEqual(v, "foo") {
785		t.Errorf("vstring value should be 'foo': %#v", v)
786	}
787
788	v, ok = result["Vunique"]
789	if !ok {
790		t.Error("vunique should be present in map")
791	} else if !reflect.DeepEqual(v, "bar") {
792		t.Errorf("vunique value should be 'bar': %#v", v)
793	}
794
795	v, ok = result["Named"]
796	if !ok {
797		t.Error("Named should be present in map")
798	} else {
799		named := v.(map[string]interface{})
800		v, ok := named["Vstring"]
801		if !ok {
802			t.Error("Named: vstring should be present in map")
803		} else if !reflect.DeepEqual(v, "baz") {
804			t.Errorf("Named: vstring should be 'baz': %#v", v)
805		}
806	}
807}
808
809func TestDecode_SquashOnNonStructType(t *testing.T) {
810	t.Parallel()
811
812	input := map[string]interface{}{
813		"InvalidSquashType": 42,
814	}
815
816	var result SquashOnNonStructType
817	err := Decode(input, &result)
818	if err == nil {
819		t.Fatal("unexpected success decoding invalid squash field type")
820	} else if !strings.Contains(err.Error(), "unsupported type for squash") {
821		t.Fatalf("unexpected error message for invalid squash field type: %s", err)
822	}
823}
824
825func TestDecode_DecodeHook(t *testing.T) {
826	t.Parallel()
827
828	input := map[string]interface{}{
829		"vint": "WHAT",
830	}
831
832	decodeHook := func(from reflect.Kind, to reflect.Kind, v interface{}) (interface{}, error) {
833		if from == reflect.String && to != reflect.String {
834			return 5, nil
835		}
836
837		return v, nil
838	}
839
840	var result Basic
841	config := &DecoderConfig{
842		DecodeHook: decodeHook,
843		Result:     &result,
844	}
845
846	decoder, err := NewDecoder(config)
847	if err != nil {
848		t.Fatalf("err: %s", err)
849	}
850
851	err = decoder.Decode(input)
852	if err != nil {
853		t.Fatalf("got an err: %s", err)
854	}
855
856	if result.Vint != 5 {
857		t.Errorf("vint should be 5: %#v", result.Vint)
858	}
859}
860
861func TestDecode_DecodeHookType(t *testing.T) {
862	t.Parallel()
863
864	input := map[string]interface{}{
865		"vint": "WHAT",
866	}
867
868	decodeHook := func(from reflect.Type, to reflect.Type, v interface{}) (interface{}, error) {
869		if from.Kind() == reflect.String &&
870			to.Kind() != reflect.String {
871			return 5, nil
872		}
873
874		return v, nil
875	}
876
877	var result Basic
878	config := &DecoderConfig{
879		DecodeHook: decodeHook,
880		Result:     &result,
881	}
882
883	decoder, err := NewDecoder(config)
884	if err != nil {
885		t.Fatalf("err: %s", err)
886	}
887
888	err = decoder.Decode(input)
889	if err != nil {
890		t.Fatalf("got an err: %s", err)
891	}
892
893	if result.Vint != 5 {
894		t.Errorf("vint should be 5: %#v", result.Vint)
895	}
896}
897
898func TestDecode_Nil(t *testing.T) {
899	t.Parallel()
900
901	var input interface{}
902	result := Basic{
903		Vstring: "foo",
904	}
905
906	err := Decode(input, &result)
907	if err != nil {
908		t.Fatalf("err: %s", err)
909	}
910
911	if result.Vstring != "foo" {
912		t.Fatalf("bad: %#v", result.Vstring)
913	}
914}
915
916func TestDecode_NilInterfaceHook(t *testing.T) {
917	t.Parallel()
918
919	input := map[string]interface{}{
920		"w": "",
921	}
922
923	decodeHook := func(f, t reflect.Type, v interface{}) (interface{}, error) {
924		if t.String() == "io.Writer" {
925			return nil, nil
926		}
927
928		return v, nil
929	}
930
931	var result NilInterface
932	config := &DecoderConfig{
933		DecodeHook: decodeHook,
934		Result:     &result,
935	}
936
937	decoder, err := NewDecoder(config)
938	if err != nil {
939		t.Fatalf("err: %s", err)
940	}
941
942	err = decoder.Decode(input)
943	if err != nil {
944		t.Fatalf("got an err: %s", err)
945	}
946
947	if result.W != nil {
948		t.Errorf("W should be nil: %#v", result.W)
949	}
950}
951
952func TestDecode_NilPointerHook(t *testing.T) {
953	t.Parallel()
954
955	input := map[string]interface{}{
956		"value": "",
957	}
958
959	decodeHook := func(f, t reflect.Type, v interface{}) (interface{}, error) {
960		if typed, ok := v.(string); ok {
961			if typed == "" {
962				return nil, nil
963			}
964		}
965		return v, nil
966	}
967
968	var result NilPointer
969	config := &DecoderConfig{
970		DecodeHook: decodeHook,
971		Result:     &result,
972	}
973
974	decoder, err := NewDecoder(config)
975	if err != nil {
976		t.Fatalf("err: %s", err)
977	}
978
979	err = decoder.Decode(input)
980	if err != nil {
981		t.Fatalf("got an err: %s", err)
982	}
983
984	if result.Value != nil {
985		t.Errorf("W should be nil: %#v", result.Value)
986	}
987}
988
989func TestDecode_FuncHook(t *testing.T) {
990	t.Parallel()
991
992	input := map[string]interface{}{
993		"foo": "baz",
994	}
995
996	decodeHook := func(f, t reflect.Type, v interface{}) (interface{}, error) {
997		if t.Kind() != reflect.Func {
998			return v, nil
999		}
1000		val := v.(string)
1001		return func() string { return val }, nil
1002	}
1003
1004	var result Func
1005	config := &DecoderConfig{
1006		DecodeHook: decodeHook,
1007		Result:     &result,
1008	}
1009
1010	decoder, err := NewDecoder(config)
1011	if err != nil {
1012		t.Fatalf("err: %s", err)
1013	}
1014
1015	err = decoder.Decode(input)
1016	if err != nil {
1017		t.Fatalf("got an err: %s", err)
1018	}
1019
1020	if result.Foo() != "baz" {
1021		t.Errorf("Foo call result should be 'baz': %s", result.Foo())
1022	}
1023}
1024
1025func TestDecode_NonStruct(t *testing.T) {
1026	t.Parallel()
1027
1028	input := map[string]interface{}{
1029		"foo": "bar",
1030		"bar": "baz",
1031	}
1032
1033	var result map[string]string
1034	err := Decode(input, &result)
1035	if err != nil {
1036		t.Fatalf("err: %s", err)
1037	}
1038
1039	if result["foo"] != "bar" {
1040		t.Fatal("foo is not bar")
1041	}
1042}
1043
1044func TestDecode_StructMatch(t *testing.T) {
1045	t.Parallel()
1046
1047	input := map[string]interface{}{
1048		"vbar": Basic{
1049			Vstring: "foo",
1050		},
1051	}
1052
1053	var result Nested
1054	err := Decode(input, &result)
1055	if err != nil {
1056		t.Fatalf("got an err: %s", err.Error())
1057	}
1058
1059	if result.Vbar.Vstring != "foo" {
1060		t.Errorf("bad: %#v", result)
1061	}
1062}
1063
1064func TestDecode_TypeConversion(t *testing.T) {
1065	input := map[string]interface{}{
1066		"IntToFloat":         42,
1067		"IntToUint":          42,
1068		"IntToBool":          1,
1069		"IntToString":        42,
1070		"UintToInt":          42,
1071		"UintToFloat":        42,
1072		"UintToBool":         42,
1073		"UintToString":       42,
1074		"BoolToInt":          true,
1075		"BoolToUint":         true,
1076		"BoolToFloat":        true,
1077		"BoolToString":       true,
1078		"FloatToInt":         42.42,
1079		"FloatToUint":        42.42,
1080		"FloatToBool":        42.42,
1081		"FloatToString":      42.42,
1082		"SliceUint8ToString": []uint8("foo"),
1083		"StringToSliceUint8": "foo",
1084		"ArrayUint8ToString": [3]uint8{'f', 'o', 'o'},
1085		"StringToInt":        "42",
1086		"StringToUint":       "42",
1087		"StringToBool":       "1",
1088		"StringToFloat":      "42.42",
1089		"StringToStrSlice":   "A",
1090		"StringToIntSlice":   "42",
1091		"StringToStrArray":   "A",
1092		"StringToIntArray":   "42",
1093		"SliceToMap":         []interface{}{},
1094		"MapToSlice":         map[string]interface{}{},
1095		"ArrayToMap":         []interface{}{},
1096		"MapToArray":         map[string]interface{}{},
1097	}
1098
1099	expectedResultStrict := TypeConversionResult{
1100		IntToFloat:  42.0,
1101		IntToUint:   42,
1102		UintToInt:   42,
1103		UintToFloat: 42,
1104		BoolToInt:   0,
1105		BoolToUint:  0,
1106		BoolToFloat: 0,
1107		FloatToInt:  42,
1108		FloatToUint: 42,
1109	}
1110
1111	expectedResultWeak := TypeConversionResult{
1112		IntToFloat:         42.0,
1113		IntToUint:          42,
1114		IntToBool:          true,
1115		IntToString:        "42",
1116		UintToInt:          42,
1117		UintToFloat:        42,
1118		UintToBool:         true,
1119		UintToString:       "42",
1120		BoolToInt:          1,
1121		BoolToUint:         1,
1122		BoolToFloat:        1,
1123		BoolToString:       "1",
1124		FloatToInt:         42,
1125		FloatToUint:        42,
1126		FloatToBool:        true,
1127		FloatToString:      "42.42",
1128		SliceUint8ToString: "foo",
1129		StringToSliceUint8: []byte("foo"),
1130		ArrayUint8ToString: "foo",
1131		StringToInt:        42,
1132		StringToUint:       42,
1133		StringToBool:       true,
1134		StringToFloat:      42.42,
1135		StringToStrSlice:   []string{"A"},
1136		StringToIntSlice:   []int{42},
1137		StringToStrArray:   [1]string{"A"},
1138		StringToIntArray:   [1]int{42},
1139		SliceToMap:         map[string]interface{}{},
1140		MapToSlice:         []interface{}{},
1141		ArrayToMap:         map[string]interface{}{},
1142		MapToArray:         [1]interface{}{},
1143	}
1144
1145	// Test strict type conversion
1146	var resultStrict TypeConversionResult
1147	err := Decode(input, &resultStrict)
1148	if err == nil {
1149		t.Errorf("should return an error")
1150	}
1151	if !reflect.DeepEqual(resultStrict, expectedResultStrict) {
1152		t.Errorf("expected %v, got: %v", expectedResultStrict, resultStrict)
1153	}
1154
1155	// Test weak type conversion
1156	var decoder *Decoder
1157	var resultWeak TypeConversionResult
1158
1159	config := &DecoderConfig{
1160		WeaklyTypedInput: true,
1161		Result:           &resultWeak,
1162	}
1163
1164	decoder, err = NewDecoder(config)
1165	if err != nil {
1166		t.Fatalf("err: %s", err)
1167	}
1168
1169	err = decoder.Decode(input)
1170	if err != nil {
1171		t.Fatalf("got an err: %s", err)
1172	}
1173
1174	if !reflect.DeepEqual(resultWeak, expectedResultWeak) {
1175		t.Errorf("expected \n%#v, got: \n%#v", expectedResultWeak, resultWeak)
1176	}
1177}
1178
1179func TestDecoder_ErrorUnused(t *testing.T) {
1180	t.Parallel()
1181
1182	input := map[string]interface{}{
1183		"vstring": "hello",
1184		"foo":     "bar",
1185	}
1186
1187	var result Basic
1188	config := &DecoderConfig{
1189		ErrorUnused: true,
1190		Result:      &result,
1191	}
1192
1193	decoder, err := NewDecoder(config)
1194	if err != nil {
1195		t.Fatalf("err: %s", err)
1196	}
1197
1198	err = decoder.Decode(input)
1199	if err == nil {
1200		t.Fatal("expected error")
1201	}
1202}
1203
1204func TestDecoder_ErrorUnused_NotSetable(t *testing.T) {
1205	t.Parallel()
1206
1207	// lowercase vsilent is unexported and cannot be set
1208	input := map[string]interface{}{
1209		"vsilent": "false",
1210	}
1211
1212	var result Basic
1213	config := &DecoderConfig{
1214		ErrorUnused: true,
1215		Result:      &result,
1216	}
1217
1218	decoder, err := NewDecoder(config)
1219	if err != nil {
1220		t.Fatalf("err: %s", err)
1221	}
1222
1223	err = decoder.Decode(input)
1224	if err == nil {
1225		t.Fatal("expected error")
1226	}
1227}
1228
1229func TestMap(t *testing.T) {
1230	t.Parallel()
1231
1232	input := map[string]interface{}{
1233		"vfoo": "foo",
1234		"vother": map[interface{}]interface{}{
1235			"foo": "foo",
1236			"bar": "bar",
1237		},
1238	}
1239
1240	var result Map
1241	err := Decode(input, &result)
1242	if err != nil {
1243		t.Fatalf("got an error: %s", err)
1244	}
1245
1246	if result.Vfoo != "foo" {
1247		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
1248	}
1249
1250	if result.Vother == nil {
1251		t.Fatal("vother should not be nil")
1252	}
1253
1254	if len(result.Vother) != 2 {
1255		t.Error("vother should have two items")
1256	}
1257
1258	if result.Vother["foo"] != "foo" {
1259		t.Errorf("'foo' key should be foo, got: %#v", result.Vother["foo"])
1260	}
1261
1262	if result.Vother["bar"] != "bar" {
1263		t.Errorf("'bar' key should be bar, got: %#v", result.Vother["bar"])
1264	}
1265}
1266
1267func TestMapMerge(t *testing.T) {
1268	t.Parallel()
1269
1270	input := map[string]interface{}{
1271		"vfoo": "foo",
1272		"vother": map[interface{}]interface{}{
1273			"foo": "foo",
1274			"bar": "bar",
1275		},
1276	}
1277
1278	var result Map
1279	result.Vother = map[string]string{"hello": "world"}
1280	err := Decode(input, &result)
1281	if err != nil {
1282		t.Fatalf("got an error: %s", err)
1283	}
1284
1285	if result.Vfoo != "foo" {
1286		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
1287	}
1288
1289	expected := map[string]string{
1290		"foo":   "foo",
1291		"bar":   "bar",
1292		"hello": "world",
1293	}
1294	if !reflect.DeepEqual(result.Vother, expected) {
1295		t.Errorf("bad: %#v", result.Vother)
1296	}
1297}
1298
1299func TestMapOfStruct(t *testing.T) {
1300	t.Parallel()
1301
1302	input := map[string]interface{}{
1303		"value": map[string]interface{}{
1304			"foo": map[string]string{"vstring": "one"},
1305			"bar": map[string]string{"vstring": "two"},
1306		},
1307	}
1308
1309	var result MapOfStruct
1310	err := Decode(input, &result)
1311	if err != nil {
1312		t.Fatalf("got an err: %s", err)
1313	}
1314
1315	if result.Value == nil {
1316		t.Fatal("value should not be nil")
1317	}
1318
1319	if len(result.Value) != 2 {
1320		t.Error("value should have two items")
1321	}
1322
1323	if result.Value["foo"].Vstring != "one" {
1324		t.Errorf("foo value should be 'one', got: %s", result.Value["foo"].Vstring)
1325	}
1326
1327	if result.Value["bar"].Vstring != "two" {
1328		t.Errorf("bar value should be 'two', got: %s", result.Value["bar"].Vstring)
1329	}
1330}
1331
1332func TestNestedType(t *testing.T) {
1333	t.Parallel()
1334
1335	input := map[string]interface{}{
1336		"vfoo": "foo",
1337		"vbar": map[string]interface{}{
1338			"vstring": "foo",
1339			"vint":    42,
1340			"vbool":   true,
1341		},
1342	}
1343
1344	var result Nested
1345	err := Decode(input, &result)
1346	if err != nil {
1347		t.Fatalf("got an err: %s", err.Error())
1348	}
1349
1350	if result.Vfoo != "foo" {
1351		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
1352	}
1353
1354	if result.Vbar.Vstring != "foo" {
1355		t.Errorf("vstring value should be 'foo': %#v", result.Vbar.Vstring)
1356	}
1357
1358	if result.Vbar.Vint != 42 {
1359		t.Errorf("vint value should be 42: %#v", result.Vbar.Vint)
1360	}
1361
1362	if result.Vbar.Vbool != true {
1363		t.Errorf("vbool value should be true: %#v", result.Vbar.Vbool)
1364	}
1365
1366	if result.Vbar.Vextra != "" {
1367		t.Errorf("vextra value should be empty: %#v", result.Vbar.Vextra)
1368	}
1369}
1370
1371func TestNestedTypePointer(t *testing.T) {
1372	t.Parallel()
1373
1374	input := map[string]interface{}{
1375		"vfoo": "foo",
1376		"vbar": &map[string]interface{}{
1377			"vstring": "foo",
1378			"vint":    42,
1379			"vbool":   true,
1380		},
1381	}
1382
1383	var result NestedPointer
1384	err := Decode(input, &result)
1385	if err != nil {
1386		t.Fatalf("got an err: %s", err.Error())
1387	}
1388
1389	if result.Vfoo != "foo" {
1390		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
1391	}
1392
1393	if result.Vbar.Vstring != "foo" {
1394		t.Errorf("vstring value should be 'foo': %#v", result.Vbar.Vstring)
1395	}
1396
1397	if result.Vbar.Vint != 42 {
1398		t.Errorf("vint value should be 42: %#v", result.Vbar.Vint)
1399	}
1400
1401	if result.Vbar.Vbool != true {
1402		t.Errorf("vbool value should be true: %#v", result.Vbar.Vbool)
1403	}
1404
1405	if result.Vbar.Vextra != "" {
1406		t.Errorf("vextra value should be empty: %#v", result.Vbar.Vextra)
1407	}
1408}
1409
1410// Test for issue #46.
1411func TestNestedTypeInterface(t *testing.T) {
1412	t.Parallel()
1413
1414	input := map[string]interface{}{
1415		"vfoo": "foo",
1416		"vbar": &map[string]interface{}{
1417			"vstring": "foo",
1418			"vint":    42,
1419			"vbool":   true,
1420
1421			"vdata": map[string]interface{}{
1422				"vstring": "bar",
1423			},
1424		},
1425	}
1426
1427	var result NestedPointer
1428	result.Vbar = new(Basic)
1429	result.Vbar.Vdata = new(Basic)
1430	err := Decode(input, &result)
1431	if err != nil {
1432		t.Fatalf("got an err: %s", err.Error())
1433	}
1434
1435	if result.Vfoo != "foo" {
1436		t.Errorf("vfoo value should be 'foo': %#v", result.Vfoo)
1437	}
1438
1439	if result.Vbar.Vstring != "foo" {
1440		t.Errorf("vstring value should be 'foo': %#v", result.Vbar.Vstring)
1441	}
1442
1443	if result.Vbar.Vint != 42 {
1444		t.Errorf("vint value should be 42: %#v", result.Vbar.Vint)
1445	}
1446
1447	if result.Vbar.Vbool != true {
1448		t.Errorf("vbool value should be true: %#v", result.Vbar.Vbool)
1449	}
1450
1451	if result.Vbar.Vextra != "" {
1452		t.Errorf("vextra value should be empty: %#v", result.Vbar.Vextra)
1453	}
1454
1455	if result.Vbar.Vdata.(*Basic).Vstring != "bar" {
1456		t.Errorf("vstring value should be 'bar': %#v", result.Vbar.Vdata.(*Basic).Vstring)
1457	}
1458}
1459
1460func TestSlice(t *testing.T) {
1461	t.Parallel()
1462
1463	inputStringSlice := map[string]interface{}{
1464		"vfoo": "foo",
1465		"vbar": []string{"foo", "bar", "baz"},
1466	}
1467
1468	inputStringSlicePointer := map[string]interface{}{
1469		"vfoo": "foo",
1470		"vbar": &[]string{"foo", "bar", "baz"},
1471	}
1472
1473	outputStringSlice := &Slice{
1474		"foo",
1475		[]string{"foo", "bar", "baz"},
1476	}
1477
1478	testSliceInput(t, inputStringSlice, outputStringSlice)
1479	testSliceInput(t, inputStringSlicePointer, outputStringSlice)
1480}
1481
1482func TestInvalidSlice(t *testing.T) {
1483	t.Parallel()
1484
1485	input := map[string]interface{}{
1486		"vfoo": "foo",
1487		"vbar": 42,
1488	}
1489
1490	result := Slice{}
1491	err := Decode(input, &result)
1492	if err == nil {
1493		t.Errorf("expected failure")
1494	}
1495}
1496
1497func TestSliceOfStruct(t *testing.T) {
1498	t.Parallel()
1499
1500	input := map[string]interface{}{
1501		"value": []map[string]interface{}{
1502			{"vstring": "one"},
1503			{"vstring": "two"},
1504		},
1505	}
1506
1507	var result SliceOfStruct
1508	err := Decode(input, &result)
1509	if err != nil {
1510		t.Fatalf("got unexpected error: %s", err)
1511	}
1512
1513	if len(result.Value) != 2 {
1514		t.Fatalf("expected two values, got %d", len(result.Value))
1515	}
1516
1517	if result.Value[0].Vstring != "one" {
1518		t.Errorf("first value should be 'one', got: %s", result.Value[0].Vstring)
1519	}
1520
1521	if result.Value[1].Vstring != "two" {
1522		t.Errorf("second value should be 'two', got: %s", result.Value[1].Vstring)
1523	}
1524}
1525
1526func TestSliceCornerCases(t *testing.T) {
1527	t.Parallel()
1528
1529	// Input with a map with zero values
1530	input := map[string]interface{}{}
1531	var resultWeak []Basic
1532
1533	err := WeakDecode(input, &resultWeak)
1534	if err != nil {
1535		t.Fatalf("got unexpected error: %s", err)
1536	}
1537
1538	if len(resultWeak) != 0 {
1539		t.Errorf("length should be 0")
1540	}
1541	// Input with more values
1542	input = map[string]interface{}{
1543		"Vstring": "foo",
1544	}
1545
1546	resultWeak = nil
1547	err = WeakDecode(input, &resultWeak)
1548	if err != nil {
1549		t.Fatalf("got unexpected error: %s", err)
1550	}
1551
1552	if resultWeak[0].Vstring != "foo" {
1553		t.Errorf("value does not match")
1554	}
1555}
1556
1557func TestSliceToMap(t *testing.T) {
1558	t.Parallel()
1559
1560	input := []map[string]interface{}{
1561		{
1562			"foo": "bar",
1563		},
1564		{
1565			"bar": "baz",
1566		},
1567	}
1568
1569	var result map[string]interface{}
1570	err := WeakDecode(input, &result)
1571	if err != nil {
1572		t.Fatalf("got an error: %s", err)
1573	}
1574
1575	expected := map[string]interface{}{
1576		"foo": "bar",
1577		"bar": "baz",
1578	}
1579	if !reflect.DeepEqual(result, expected) {
1580		t.Errorf("bad: %#v", result)
1581	}
1582}
1583
1584func TestArray(t *testing.T) {
1585	t.Parallel()
1586
1587	inputStringArray := map[string]interface{}{
1588		"vfoo": "foo",
1589		"vbar": [2]string{"foo", "bar"},
1590	}
1591
1592	inputStringArrayPointer := map[string]interface{}{
1593		"vfoo": "foo",
1594		"vbar": &[2]string{"foo", "bar"},
1595	}
1596
1597	outputStringArray := &Array{
1598		"foo",
1599		[2]string{"foo", "bar"},
1600	}
1601
1602	testArrayInput(t, inputStringArray, outputStringArray)
1603	testArrayInput(t, inputStringArrayPointer, outputStringArray)
1604}
1605
1606func TestInvalidArray(t *testing.T) {
1607	t.Parallel()
1608
1609	input := map[string]interface{}{
1610		"vfoo": "foo",
1611		"vbar": 42,
1612	}
1613
1614	result := Array{}
1615	err := Decode(input, &result)
1616	if err == nil {
1617		t.Errorf("expected failure")
1618	}
1619}
1620
1621func TestArrayOfStruct(t *testing.T) {
1622	t.Parallel()
1623
1624	input := map[string]interface{}{
1625		"value": []map[string]interface{}{
1626			{"vstring": "one"},
1627			{"vstring": "two"},
1628		},
1629	}
1630
1631	var result ArrayOfStruct
1632	err := Decode(input, &result)
1633	if err != nil {
1634		t.Fatalf("got unexpected error: %s", err)
1635	}
1636
1637	if len(result.Value) != 2 {
1638		t.Fatalf("expected two values, got %d", len(result.Value))
1639	}
1640
1641	if result.Value[0].Vstring != "one" {
1642		t.Errorf("first value should be 'one', got: %s", result.Value[0].Vstring)
1643	}
1644
1645	if result.Value[1].Vstring != "two" {
1646		t.Errorf("second value should be 'two', got: %s", result.Value[1].Vstring)
1647	}
1648}
1649
1650func TestArrayToMap(t *testing.T) {
1651	t.Parallel()
1652
1653	input := []map[string]interface{}{
1654		{
1655			"foo": "bar",
1656		},
1657		{
1658			"bar": "baz",
1659		},
1660	}
1661
1662	var result map[string]interface{}
1663	err := WeakDecode(input, &result)
1664	if err != nil {
1665		t.Fatalf("got an error: %s", err)
1666	}
1667
1668	expected := map[string]interface{}{
1669		"foo": "bar",
1670		"bar": "baz",
1671	}
1672	if !reflect.DeepEqual(result, expected) {
1673		t.Errorf("bad: %#v", result)
1674	}
1675}
1676
1677func TestDecodeTable(t *testing.T) {
1678	t.Parallel()
1679
1680	// We need to make new types so that we don't get the short-circuit
1681	// copy functionality. We want to test the deep copying functionality.
1682	type BasicCopy Basic
1683	type NestedPointerCopy NestedPointer
1684	type MapCopy Map
1685
1686	tests := []struct {
1687		name    string
1688		in      interface{}
1689		target  interface{}
1690		out     interface{}
1691		wantErr bool
1692	}{
1693		{
1694			"basic struct input",
1695			&Basic{
1696				Vstring: "vstring",
1697				Vint:    2,
1698				Vint8:   2,
1699				Vint16:  2,
1700				Vint32:  2,
1701				Vint64:  2,
1702				Vuint:   3,
1703				Vbool:   true,
1704				Vfloat:  4.56,
1705				Vextra:  "vextra",
1706				vsilent: true,
1707				Vdata:   []byte("data"),
1708			},
1709			&map[string]interface{}{},
1710			&map[string]interface{}{
1711				"Vstring":     "vstring",
1712				"Vint":        2,
1713				"Vint8":       int8(2),
1714				"Vint16":      int16(2),
1715				"Vint32":      int32(2),
1716				"Vint64":      int64(2),
1717				"Vuint":       uint(3),
1718				"Vbool":       true,
1719				"Vfloat":      4.56,
1720				"Vextra":      "vextra",
1721				"Vdata":       []byte("data"),
1722				"VjsonInt":    0,
1723				"VjsonUint":   uint(0),
1724				"VjsonFloat":  0.0,
1725				"VjsonNumber": json.Number(""),
1726			},
1727			false,
1728		},
1729		{
1730			"embedded struct input",
1731			&Embedded{
1732				Vunique: "vunique",
1733				Basic: Basic{
1734					Vstring: "vstring",
1735					Vint:    2,
1736					Vint8:   2,
1737					Vint16:  2,
1738					Vint32:  2,
1739					Vint64:  2,
1740					Vuint:   3,
1741					Vbool:   true,
1742					Vfloat:  4.56,
1743					Vextra:  "vextra",
1744					vsilent: true,
1745					Vdata:   []byte("data"),
1746				},
1747			},
1748			&map[string]interface{}{},
1749			&map[string]interface{}{
1750				"Vunique": "vunique",
1751				"Basic": map[string]interface{}{
1752					"Vstring":     "vstring",
1753					"Vint":        2,
1754					"Vint8":       int8(2),
1755					"Vint16":      int16(2),
1756					"Vint32":      int32(2),
1757					"Vint64":      int64(2),
1758					"Vuint":       uint(3),
1759					"Vbool":       true,
1760					"Vfloat":      4.56,
1761					"Vextra":      "vextra",
1762					"Vdata":       []byte("data"),
1763					"VjsonInt":    0,
1764					"VjsonUint":   uint(0),
1765					"VjsonFloat":  0.0,
1766					"VjsonNumber": json.Number(""),
1767				},
1768			},
1769			false,
1770		},
1771		{
1772			"struct => struct",
1773			&Basic{
1774				Vstring: "vstring",
1775				Vint:    2,
1776				Vuint:   3,
1777				Vbool:   true,
1778				Vfloat:  4.56,
1779				Vextra:  "vextra",
1780				Vdata:   []byte("data"),
1781				vsilent: true,
1782			},
1783			&BasicCopy{},
1784			&BasicCopy{
1785				Vstring: "vstring",
1786				Vint:    2,
1787				Vuint:   3,
1788				Vbool:   true,
1789				Vfloat:  4.56,
1790				Vextra:  "vextra",
1791				Vdata:   []byte("data"),
1792			},
1793			false,
1794		},
1795		{
1796			"struct => struct with pointers",
1797			&NestedPointer{
1798				Vfoo: "hello",
1799				Vbar: nil,
1800			},
1801			&NestedPointerCopy{},
1802			&NestedPointerCopy{
1803				Vfoo: "hello",
1804			},
1805			false,
1806		},
1807		{
1808			"basic pointer to non-pointer",
1809			&BasicPointer{
1810				Vstring: stringPtr("vstring"),
1811				Vint:    intPtr(2),
1812				Vuint:   uintPtr(3),
1813				Vbool:   boolPtr(true),
1814				Vfloat:  floatPtr(4.56),
1815				Vdata:   interfacePtr([]byte("data")),
1816			},
1817			&Basic{},
1818			&Basic{
1819				Vstring: "vstring",
1820				Vint:    2,
1821				Vuint:   3,
1822				Vbool:   true,
1823				Vfloat:  4.56,
1824				Vdata:   []byte("data"),
1825			},
1826			false,
1827		},
1828		{
1829			"slice non-pointer to pointer",
1830			&Slice{},
1831			&SlicePointer{},
1832			&SlicePointer{},
1833			false,
1834		},
1835		{
1836			"slice non-pointer to pointer, zero field",
1837			&Slice{},
1838			&SlicePointer{
1839				Vbar: &[]string{"yo"},
1840			},
1841			&SlicePointer{},
1842			false,
1843		},
1844		{
1845			"slice to slice alias",
1846			&Slice{},
1847			&SliceOfAlias{},
1848			&SliceOfAlias{},
1849			false,
1850		},
1851		{
1852			"nil map to map",
1853			&Map{},
1854			&MapCopy{},
1855			&MapCopy{},
1856			false,
1857		},
1858		{
1859			"nil map to non-empty map",
1860			&Map{},
1861			&MapCopy{Vother: map[string]string{"foo": "bar"}},
1862			&MapCopy{},
1863			false,
1864		},
1865
1866		{
1867			"slice input - should error",
1868			[]string{"foo", "bar"},
1869			&map[string]interface{}{},
1870			&map[string]interface{}{},
1871			true,
1872		},
1873		{
1874			"struct with slice property",
1875			&Slice{
1876				Vfoo: "vfoo",
1877				Vbar: []string{"foo", "bar"},
1878			},
1879			&map[string]interface{}{},
1880			&map[string]interface{}{
1881				"Vfoo": "vfoo",
1882				"Vbar": []string{"foo", "bar"},
1883			},
1884			false,
1885		},
1886		{
1887			"struct with empty slice",
1888			&map[string]interface{}{
1889				"Vbar": []string{},
1890			},
1891			&Slice{},
1892			&Slice{
1893				Vbar: []string{},
1894			},
1895			false,
1896		},
1897		{
1898			"struct with slice of struct property",
1899			&SliceOfStruct{
1900				Value: []Basic{
1901					Basic{
1902						Vstring: "vstring",
1903						Vint:    2,
1904						Vuint:   3,
1905						Vbool:   true,
1906						Vfloat:  4.56,
1907						Vextra:  "vextra",
1908						vsilent: true,
1909						Vdata:   []byte("data"),
1910					},
1911				},
1912			},
1913			&map[string]interface{}{},
1914			&map[string]interface{}{
1915				"Value": []Basic{
1916					Basic{
1917						Vstring: "vstring",
1918						Vint:    2,
1919						Vuint:   3,
1920						Vbool:   true,
1921						Vfloat:  4.56,
1922						Vextra:  "vextra",
1923						vsilent: true,
1924						Vdata:   []byte("data"),
1925					},
1926				},
1927			},
1928			false,
1929		},
1930		{
1931			"struct with map property",
1932			&Map{
1933				Vfoo:   "vfoo",
1934				Vother: map[string]string{"vother": "vother"},
1935			},
1936			&map[string]interface{}{},
1937			&map[string]interface{}{
1938				"Vfoo": "vfoo",
1939				"Vother": map[string]string{
1940					"vother": "vother",
1941				}},
1942			false,
1943		},
1944		{
1945			"tagged struct",
1946			&Tagged{
1947				Extra: "extra",
1948				Value: "value",
1949			},
1950			&map[string]string{},
1951			&map[string]string{
1952				"bar": "extra",
1953				"foo": "value",
1954			},
1955			false,
1956		},
1957		{
1958			"omit tag struct",
1959			&struct {
1960				Value string `mapstructure:"value"`
1961				Omit  string `mapstructure:"-"`
1962			}{
1963				Value: "value",
1964				Omit:  "omit",
1965			},
1966			&map[string]string{},
1967			&map[string]string{
1968				"value": "value",
1969			},
1970			false,
1971		},
1972		{
1973			"decode to wrong map type",
1974			&struct {
1975				Value string
1976			}{
1977				Value: "string",
1978			},
1979			&map[string]int{},
1980			&map[string]int{},
1981			true,
1982		},
1983		{
1984			"remainder",
1985			map[string]interface{}{
1986				"A": "hello",
1987				"B": "goodbye",
1988				"C": "yo",
1989			},
1990			&Remainder{},
1991			&Remainder{
1992				A: "hello",
1993				Extra: map[string]interface{}{
1994					"B": "goodbye",
1995					"C": "yo",
1996				},
1997			},
1998			false,
1999		},
2000		{
2001			"remainder with no extra",
2002			map[string]interface{}{
2003				"A": "hello",
2004			},
2005			&Remainder{},
2006			&Remainder{
2007				A:     "hello",
2008				Extra: nil,
2009			},
2010			false,
2011		},
2012		{
2013			"struct with omitempty tag return non-empty values",
2014			&struct {
2015				VisibleField interface{} `mapstructure:"visible"`
2016				OmitField    interface{} `mapstructure:"omittable,omitempty"`
2017			}{
2018				VisibleField: nil,
2019				OmitField:    "string",
2020			},
2021			&map[string]interface{}{},
2022			&map[string]interface{}{"visible": nil, "omittable": "string"},
2023			false,
2024		},
2025		{
2026			"struct with omitempty tag ignore empty values",
2027			&struct {
2028				VisibleField interface{} `mapstructure:"visible"`
2029				OmitField    interface{} `mapstructure:"omittable,omitempty"`
2030			}{
2031				VisibleField: nil,
2032				OmitField:    nil,
2033			},
2034			&map[string]interface{}{},
2035			&map[string]interface{}{"visible": nil},
2036			false,
2037		},
2038	}
2039
2040	for _, tt := range tests {
2041		t.Run(tt.name, func(t *testing.T) {
2042			if err := Decode(tt.in, tt.target); (err != nil) != tt.wantErr {
2043				t.Fatalf("%q: TestMapOutputForStructuredInputs() unexpected error: %s", tt.name, err)
2044			}
2045
2046			if !reflect.DeepEqual(tt.out, tt.target) {
2047				t.Fatalf("%q: TestMapOutputForStructuredInputs() expected: %#v, got: %#v", tt.name, tt.out, tt.target)
2048			}
2049		})
2050	}
2051}
2052
2053func TestInvalidType(t *testing.T) {
2054	t.Parallel()
2055
2056	input := map[string]interface{}{
2057		"vstring": 42,
2058	}
2059
2060	var result Basic
2061	err := Decode(input, &result)
2062	if err == nil {
2063		t.Fatal("error should exist")
2064	}
2065
2066	derr, ok := err.(*Error)
2067	if !ok {
2068		t.Fatalf("error should be kind of Error, instead: %#v", err)
2069	}
2070
2071	if derr.Errors[0] !=
2072		"'Vstring' expected type 'string', got unconvertible type 'int', value: '42'" {
2073		t.Errorf("got unexpected error: %s", err)
2074	}
2075
2076	inputNegIntUint := map[string]interface{}{
2077		"vuint": -42,
2078	}
2079
2080	err = Decode(inputNegIntUint, &result)
2081	if err == nil {
2082		t.Fatal("error should exist")
2083	}
2084
2085	derr, ok = err.(*Error)
2086	if !ok {
2087		t.Fatalf("error should be kind of Error, instead: %#v", err)
2088	}
2089
2090	if derr.Errors[0] != "cannot parse 'Vuint', -42 overflows uint" {
2091		t.Errorf("got unexpected error: %s", err)
2092	}
2093
2094	inputNegFloatUint := map[string]interface{}{
2095		"vuint": -42.0,
2096	}
2097
2098	err = Decode(inputNegFloatUint, &result)
2099	if err == nil {
2100		t.Fatal("error should exist")
2101	}
2102
2103	derr, ok = err.(*Error)
2104	if !ok {
2105		t.Fatalf("error should be kind of Error, instead: %#v", err)
2106	}
2107
2108	if derr.Errors[0] != "cannot parse 'Vuint', -42.000000 overflows uint" {
2109		t.Errorf("got unexpected error: %s", err)
2110	}
2111}
2112
2113func TestDecodeMetadata(t *testing.T) {
2114	t.Parallel()
2115
2116	input := map[string]interface{}{
2117		"vfoo": "foo",
2118		"vbar": map[string]interface{}{
2119			"vstring": "foo",
2120			"Vuint":   42,
2121			"vsilent": "false",
2122			"foo":     "bar",
2123		},
2124		"bar": "nil",
2125	}
2126
2127	var md Metadata
2128	var result Nested
2129
2130	err := DecodeMetadata(input, &result, &md)
2131	if err != nil {
2132		t.Fatalf("err: %s", err.Error())
2133	}
2134
2135	expectedKeys := []string{"Vbar", "Vbar.Vstring", "Vbar.Vuint", "Vfoo"}
2136	sort.Strings(md.Keys)
2137	if !reflect.DeepEqual(md.Keys, expectedKeys) {
2138		t.Fatalf("bad keys: %#v", md.Keys)
2139	}
2140
2141	expectedUnused := []string{"Vbar.foo", "Vbar.vsilent", "bar"}
2142	sort.Strings(md.Unused)
2143	if !reflect.DeepEqual(md.Unused, expectedUnused) {
2144		t.Fatalf("bad unused: %#v", md.Unused)
2145	}
2146}
2147
2148func TestMetadata(t *testing.T) {
2149	t.Parallel()
2150
2151	type testResult struct {
2152		Vfoo string
2153		Vbar BasicPointer
2154	}
2155
2156	input := map[string]interface{}{
2157		"vfoo": "foo",
2158		"vbar": map[string]interface{}{
2159			"vstring": "foo",
2160			"Vuint":   42,
2161			"vsilent": "false",
2162			"foo":     "bar",
2163		},
2164		"bar": "nil",
2165	}
2166
2167	var md Metadata
2168	var result testResult
2169	config := &DecoderConfig{
2170		Metadata: &md,
2171		Result:   &result,
2172	}
2173
2174	decoder, err := NewDecoder(config)
2175	if err != nil {
2176		t.Fatalf("err: %s", err)
2177	}
2178
2179	err = decoder.Decode(input)
2180	if err != nil {
2181		t.Fatalf("err: %s", err.Error())
2182	}
2183
2184	expectedKeys := []string{"Vbar", "Vbar.Vstring", "Vbar.Vuint", "Vfoo"}
2185	sort.Strings(md.Keys)
2186	if !reflect.DeepEqual(md.Keys, expectedKeys) {
2187		t.Fatalf("bad keys: %#v", md.Keys)
2188	}
2189
2190	expectedUnused := []string{"Vbar.foo", "Vbar.vsilent", "bar"}
2191	sort.Strings(md.Unused)
2192	if !reflect.DeepEqual(md.Unused, expectedUnused) {
2193		t.Fatalf("bad unused: %#v", md.Unused)
2194	}
2195}
2196
2197func TestMetadata_Embedded(t *testing.T) {
2198	t.Parallel()
2199
2200	input := map[string]interface{}{
2201		"vstring": "foo",
2202		"vunique": "bar",
2203	}
2204
2205	var md Metadata
2206	var result EmbeddedSquash
2207	config := &DecoderConfig{
2208		Metadata: &md,
2209		Result:   &result,
2210	}
2211
2212	decoder, err := NewDecoder(config)
2213	if err != nil {
2214		t.Fatalf("err: %s", err)
2215	}
2216
2217	err = decoder.Decode(input)
2218	if err != nil {
2219		t.Fatalf("err: %s", err.Error())
2220	}
2221
2222	expectedKeys := []string{"Vstring", "Vunique"}
2223
2224	sort.Strings(md.Keys)
2225	if !reflect.DeepEqual(md.Keys, expectedKeys) {
2226		t.Fatalf("bad keys: %#v", md.Keys)
2227	}
2228
2229	expectedUnused := []string{}
2230	if !reflect.DeepEqual(md.Unused, expectedUnused) {
2231		t.Fatalf("bad unused: %#v", md.Unused)
2232	}
2233}
2234
2235func TestNonPtrValue(t *testing.T) {
2236	t.Parallel()
2237
2238	err := Decode(map[string]interface{}{}, Basic{})
2239	if err == nil {
2240		t.Fatal("error should exist")
2241	}
2242
2243	if err.Error() != "result must be a pointer" {
2244		t.Errorf("got unexpected error: %s", err)
2245	}
2246}
2247
2248func TestTagged(t *testing.T) {
2249	t.Parallel()
2250
2251	input := map[string]interface{}{
2252		"foo": "bar",
2253		"bar": "value",
2254	}
2255
2256	var result Tagged
2257	err := Decode(input, &result)
2258	if err != nil {
2259		t.Fatalf("unexpected error: %s", err)
2260	}
2261
2262	if result.Value != "bar" {
2263		t.Errorf("value should be 'bar', got: %#v", result.Value)
2264	}
2265
2266	if result.Extra != "value" {
2267		t.Errorf("extra should be 'value', got: %#v", result.Extra)
2268	}
2269}
2270
2271func TestWeakDecode(t *testing.T) {
2272	t.Parallel()
2273
2274	input := map[string]interface{}{
2275		"foo": "4",
2276		"bar": "value",
2277	}
2278
2279	var result struct {
2280		Foo int
2281		Bar string
2282	}
2283
2284	if err := WeakDecode(input, &result); err != nil {
2285		t.Fatalf("err: %s", err)
2286	}
2287	if result.Foo != 4 {
2288		t.Fatalf("bad: %#v", result)
2289	}
2290	if result.Bar != "value" {
2291		t.Fatalf("bad: %#v", result)
2292	}
2293}
2294
2295func TestWeakDecodeMetadata(t *testing.T) {
2296	t.Parallel()
2297
2298	input := map[string]interface{}{
2299		"foo":        "4",
2300		"bar":        "value",
2301		"unused":     "value",
2302		"unexported": "value",
2303	}
2304
2305	var md Metadata
2306	var result struct {
2307		Foo        int
2308		Bar        string
2309		unexported string
2310	}
2311
2312	if err := WeakDecodeMetadata(input, &result, &md); err != nil {
2313		t.Fatalf("err: %s", err)
2314	}
2315	if result.Foo != 4 {
2316		t.Fatalf("bad: %#v", result)
2317	}
2318	if result.Bar != "value" {
2319		t.Fatalf("bad: %#v", result)
2320	}
2321
2322	expectedKeys := []string{"Bar", "Foo"}
2323	sort.Strings(md.Keys)
2324	if !reflect.DeepEqual(md.Keys, expectedKeys) {
2325		t.Fatalf("bad keys: %#v", md.Keys)
2326	}
2327
2328	expectedUnused := []string{"unexported", "unused"}
2329	sort.Strings(md.Unused)
2330	if !reflect.DeepEqual(md.Unused, expectedUnused) {
2331		t.Fatalf("bad unused: %#v", md.Unused)
2332	}
2333}
2334
2335func TestDecode_StructTaggedWithOmitempty_OmitEmptyValues(t *testing.T) {
2336	t.Parallel()
2337
2338	input := &StructWithOmitEmpty{}
2339
2340	var emptySlice []interface{}
2341	var emptyMap map[string]interface{}
2342	var emptyNested *Nested
2343	expected := &map[string]interface{}{
2344		"visible-string": "",
2345		"visible-int":    0,
2346		"visible-float":  0.0,
2347		"visible-slice":  emptySlice,
2348		"visible-map":    emptyMap,
2349		"visible-nested": emptyNested,
2350	}
2351
2352	actual := &map[string]interface{}{}
2353	Decode(input, actual)
2354
2355	if !reflect.DeepEqual(actual, expected) {
2356		t.Fatalf("Decode() expected: %#v, got: %#v", expected, actual)
2357	}
2358}
2359
2360func TestDecode_StructTaggedWithOmitempty_KeepNonEmptyValues(t *testing.T) {
2361	t.Parallel()
2362
2363	input := &StructWithOmitEmpty{
2364		VisibleStringField: "",
2365		OmitStringField:    "string",
2366		VisibleIntField:    0,
2367		OmitIntField:       1,
2368		VisibleFloatField:  0.0,
2369		OmitFloatField:     1.0,
2370		VisibleSliceField:  nil,
2371		OmitSliceField:     []interface{}{1},
2372		VisibleMapField:    nil,
2373		OmitMapField:       map[string]interface{}{"k": "v"},
2374		NestedField:        nil,
2375		OmitNestedField:    &Nested{},
2376	}
2377
2378	var emptySlice []interface{}
2379	var emptyMap map[string]interface{}
2380	var emptyNested *Nested
2381	expected := &map[string]interface{}{
2382		"visible-string":   "",
2383		"omittable-string": "string",
2384		"visible-int":      0,
2385		"omittable-int":    1,
2386		"visible-float":    0.0,
2387		"omittable-float":  1.0,
2388		"visible-slice":    emptySlice,
2389		"omittable-slice":  []interface{}{1},
2390		"visible-map":      emptyMap,
2391		"omittable-map":    map[string]interface{}{"k": "v"},
2392		"visible-nested":   emptyNested,
2393		"omittable-nested": map[string]interface{}{
2394			"Vbar": map[string]interface{}{
2395				"Vbool":       false,
2396				"Vdata":       interface{}(nil),
2397				"Vextra":      "",
2398				"Vfloat":      float64(0),
2399				"Vint":        0,
2400				"Vint16":      int16(0),
2401				"Vint32":      int32(0),
2402				"Vint64":      int64(0),
2403				"Vint8":       int8(0),
2404				"VjsonFloat":  float64(0),
2405				"VjsonInt":    0,
2406				"VjsonNumber": json.Number(""),
2407				"VjsonUint":   uint(0),
2408				"Vstring":     "",
2409				"Vuint":       uint(0),
2410			},
2411			"Vfoo": "",
2412		},
2413	}
2414
2415	actual := &map[string]interface{}{}
2416	Decode(input, actual)
2417
2418	if !reflect.DeepEqual(actual, expected) {
2419		t.Fatalf("Decode() expected: %#v, got: %#v", expected, actual)
2420	}
2421}
2422
2423func TestDecode_mapToStruct(t *testing.T) {
2424	type Target struct {
2425		String    string
2426		StringPtr *string
2427	}
2428
2429	expected := Target{
2430		String: "hello",
2431	}
2432
2433	var target Target
2434	err := Decode(map[string]interface{}{
2435		"string":    "hello",
2436		"StringPtr": "goodbye",
2437	}, &target)
2438	if err != nil {
2439		t.Fatalf("got error: %s", err)
2440	}
2441
2442	// Pointers fail reflect test so do those manually
2443	if target.StringPtr == nil || *target.StringPtr != "goodbye" {
2444		t.Fatalf("bad: %#v", target)
2445	}
2446	target.StringPtr = nil
2447
2448	if !reflect.DeepEqual(target, expected) {
2449		t.Fatalf("bad: %#v", target)
2450	}
2451}
2452
2453func testSliceInput(t *testing.T, input map[string]interface{}, expected *Slice) {
2454	var result Slice
2455	err := Decode(input, &result)
2456	if err != nil {
2457		t.Fatalf("got error: %s", err)
2458	}
2459
2460	if result.Vfoo != expected.Vfoo {
2461		t.Errorf("Vfoo expected '%s', got '%s'", expected.Vfoo, result.Vfoo)
2462	}
2463
2464	if result.Vbar == nil {
2465		t.Fatalf("Vbar a slice, got '%#v'", result.Vbar)
2466	}
2467
2468	if len(result.Vbar) != len(expected.Vbar) {
2469		t.Errorf("Vbar length should be %d, got %d", len(expected.Vbar), len(result.Vbar))
2470	}
2471
2472	for i, v := range result.Vbar {
2473		if v != expected.Vbar[i] {
2474			t.Errorf(
2475				"Vbar[%d] should be '%#v', got '%#v'",
2476				i, expected.Vbar[i], v)
2477		}
2478	}
2479}
2480
2481func testArrayInput(t *testing.T, input map[string]interface{}, expected *Array) {
2482	var result Array
2483	err := Decode(input, &result)
2484	if err != nil {
2485		t.Fatalf("got error: %s", err)
2486	}
2487
2488	if result.Vfoo != expected.Vfoo {
2489		t.Errorf("Vfoo expected '%s', got '%s'", expected.Vfoo, result.Vfoo)
2490	}
2491
2492	if result.Vbar == [2]string{} {
2493		t.Fatalf("Vbar a slice, got '%#v'", result.Vbar)
2494	}
2495
2496	if len(result.Vbar) != len(expected.Vbar) {
2497		t.Errorf("Vbar length should be %d, got %d", len(expected.Vbar), len(result.Vbar))
2498	}
2499
2500	for i, v := range result.Vbar {
2501		if v != expected.Vbar[i] {
2502			t.Errorf(
2503				"Vbar[%d] should be '%#v', got '%#v'",
2504				i, expected.Vbar[i], v)
2505		}
2506	}
2507}
2508
2509func stringPtr(v string) *string              { return &v }
2510func intPtr(v int) *int                       { return &v }
2511func uintPtr(v uint) *uint                    { return &v }
2512func boolPtr(v bool) *bool                    { return &v }
2513func floatPtr(v float64) *float64             { return &v }
2514func interfacePtr(v interface{}) *interface{} { return &v }
2515