chore: add more tests (#3282)

master
Kevin Wan 2 years ago committed by GitHub
parent d76a39ac26
commit fa33329a44
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -148,14 +148,17 @@ func (u *Unmarshaler) fillSlice(fieldType reflect.Type, value reflect.Value, map
return errValueNotSettable return errValueNotSettable
} }
baseType := fieldType.Elem()
dereffedBaseType := Deref(baseType)
dereffedBaseKind := dereffedBaseType.Kind()
refValue := reflect.ValueOf(mapValue) refValue := reflect.ValueOf(mapValue)
if refValue.Kind() != reflect.Slice {
return errTypeMismatch
}
if refValue.IsNil() { if refValue.IsNil() {
return nil return nil
} }
baseType := fieldType.Elem()
dereffedBaseType := Deref(baseType)
dereffedBaseKind := dereffedBaseType.Kind()
conv := reflect.MakeSlice(reflect.SliceOf(baseType), refValue.Len(), refValue.Cap()) conv := reflect.MakeSlice(reflect.SliceOf(baseType), refValue.Len(), refValue.Cap())
if refValue.Len() == 0 { if refValue.Len() == 0 {
value.Set(conv) value.Set(conv)

@ -306,30 +306,61 @@ func TestUnmarshalIntPtr(t *testing.T) {
} }
func TestUnmarshalIntSliceOfPtr(t *testing.T) { func TestUnmarshalIntSliceOfPtr(t *testing.T) {
type inner struct { t.Run("int slice", func(t *testing.T) {
Ints []*int `key:"ints"` type inner struct {
Intps []**int `key:"intps"` Ints []*int `key:"ints"`
} Intps []**int `key:"intps"`
m := map[string]any{ }
"ints": []int{1, 2, 3}, m := map[string]any{
"intps": []int{1, 2, 3, 4}, "ints": []int{1, 2, 3},
} "intps": []int{1, 2, 3, 4},
}
var in inner var in inner
if assert.NoError(t, UnmarshalKey(m, &in)) { if assert.NoError(t, UnmarshalKey(m, &in)) {
assert.NotEmpty(t, in.Ints) assert.NotEmpty(t, in.Ints)
var ints []int var ints []int
for _, i := range in.Ints { for _, i := range in.Ints {
ints = append(ints, *i) ints = append(ints, *i)
}
assert.EqualValues(t, []int{1, 2, 3}, ints)
var intps []int
for _, i := range in.Intps {
intps = append(intps, **i)
}
assert.EqualValues(t, []int{1, 2, 3, 4}, intps)
} }
assert.EqualValues(t, []int{1, 2, 3}, ints) })
var intps []int t.Run("int slice with error", func(t *testing.T) {
for _, i := range in.Intps { type inner struct {
intps = append(intps, **i) Ints []*int `key:"ints"`
Intps []**int `key:"intps"`
} }
assert.EqualValues(t, []int{1, 2, 3, 4}, intps) m := map[string]any{
} "ints": []any{1, 2, "a"},
"intps": []int{1, 2, 3, 4},
}
var in inner
assert.Error(t, UnmarshalKey(m, &in))
})
t.Run("int slice with nil", func(t *testing.T) {
type inner struct {
Ints []int `key:"ints"`
}
m := map[string]any{
"ints": []any{nil},
}
var in inner
if assert.NoError(t, UnmarshalKey(m, &in)) {
assert.Empty(t, in.Ints)
}
})
} }
func TestUnmarshalIntWithDefault(t *testing.T) { func TestUnmarshalIntWithDefault(t *testing.T) {
@ -373,6 +404,42 @@ func TestUnmarshalIntWithString(t *testing.T) {
} }
}) })
t.Run("int wrong range", func(t *testing.T) {
type inner struct {
Int int64 `key:"int,string,range=[2:3]"`
Intp *int64 `key:"intp,range=[2:3]"`
Intpp **int64 `key:"intpp,range=[2:3]"`
}
m := map[string]any{
"int": json.Number("1"),
"intp": json.Number("2"),
"intpp": json.Number("3"),
}
var in inner
assert.ErrorIs(t, UnmarshalKey(m, &in), errNumberRange)
})
t.Run("int with wrong type", func(t *testing.T) {
type (
myString string
inner struct {
Int int64 `key:"int,string"`
Intp *int64 `key:"intp,string"`
Intpp **int64 `key:"intpp,string"`
}
)
m := map[string]any{
"int": myString("1"),
"intp": myString("2"),
"intpp": myString("3"),
}
var in inner
assert.Error(t, UnmarshalKey(m, &in))
})
t.Run("int with ptr", func(t *testing.T) { t.Run("int with ptr", func(t *testing.T) {
type inner struct { type inner struct {
Int *int64 `key:"int"` Int *int64 `key:"int"`
@ -387,6 +454,54 @@ func TestUnmarshalIntWithString(t *testing.T) {
} }
}) })
t.Run("int with invalid value", func(t *testing.T) {
type inner struct {
Int int64 `key:"int"`
}
m := map[string]any{
"int": json.Number("a"),
}
var in inner
assert.Error(t, UnmarshalKey(m, &in))
})
t.Run("uint with invalid value", func(t *testing.T) {
type inner struct {
Int uint64 `key:"int"`
}
m := map[string]any{
"int": json.Number("a"),
}
var in inner
assert.Error(t, UnmarshalKey(m, &in))
})
t.Run("float with invalid value", func(t *testing.T) {
type inner struct {
Value float64 `key:"float"`
}
m := map[string]any{
"float": json.Number("a"),
}
var in inner
assert.Error(t, UnmarshalKey(m, &in))
})
t.Run("float with invalid value", func(t *testing.T) {
type inner struct {
Value string `key:"value"`
}
m := map[string]any{
"value": json.Number("a"),
}
var in inner
assert.Error(t, UnmarshalKey(m, &in))
})
t.Run("int with ptr of ptr", func(t *testing.T) { t.Run("int with ptr of ptr", func(t *testing.T) {
type inner struct { type inner struct {
Int **int64 `key:"int"` Int **int64 `key:"int"`
@ -491,14 +606,25 @@ func TestUnmarshalBoolSliceEmpty(t *testing.T) {
} }
func TestUnmarshalBoolSliceWithDefault(t *testing.T) { func TestUnmarshalBoolSliceWithDefault(t *testing.T) {
type inner struct { t.Run("slice with default", func(t *testing.T) {
Bools []bool `key:"bools,default=[true,false]"` type inner struct {
} Bools []bool `key:"bools,default=[true,false]"`
}
var in inner var in inner
if assert.NoError(t, UnmarshalKey(nil, &in)) { if assert.NoError(t, UnmarshalKey(nil, &in)) {
assert.ElementsMatch(t, []bool{true, false}, in.Bools) assert.ElementsMatch(t, []bool{true, false}, in.Bools)
} }
})
t.Run("slice with default error", func(t *testing.T) {
type inner struct {
Bools []bool `key:"bools,default=[true,fal]"`
}
var in inner
assert.Error(t, UnmarshalKey(nil, &in))
})
} }
func TestUnmarshalIntSliceWithDefault(t *testing.T) { func TestUnmarshalIntSliceWithDefault(t *testing.T) {
@ -726,19 +852,45 @@ func TestUnmarshalStringWithMissing(t *testing.T) {
} }
func TestUnmarshalStringSliceFromString(t *testing.T) { func TestUnmarshalStringSliceFromString(t *testing.T) {
var v struct { t.Run("slice from string", func(t *testing.T) {
Names []string `key:"names"` var v struct {
} Names []string `key:"names"`
m := map[string]any{ }
"names": `["first", "second"]`, m := map[string]any{
} "names": `["first", "second"]`,
}
ast := assert.New(t) ast := assert.New(t)
if ast.NoError(UnmarshalKey(m, &v)) { if ast.NoError(UnmarshalKey(m, &v)) {
ast.Equal(2, len(v.Names)) ast.Equal(2, len(v.Names))
ast.Equal("first", v.Names[0]) ast.Equal("first", v.Names[0])
ast.Equal("second", v.Names[1]) ast.Equal("second", v.Names[1])
} }
})
t.Run("slice from string with slice error", func(t *testing.T) {
var v struct {
Names []int `key:"names"`
}
m := map[string]any{
"names": `["first", 1]`,
}
assert.Error(t, UnmarshalKey(m, &v))
})
t.Run("slice from string with error", func(t *testing.T) {
type myString string
var v struct {
Names []string `key:"names"`
}
m := map[string]any{
"names": myString("not a slice"),
}
assert.Error(t, UnmarshalKey(m, &v))
})
} }
func TestUnmarshalIntSliceFromString(t *testing.T) { func TestUnmarshalIntSliceFromString(t *testing.T) {
@ -800,19 +952,32 @@ func (c CustomStringer) String() string {
} }
func TestUnmarshalStringMapFromStringer(t *testing.T) { func TestUnmarshalStringMapFromStringer(t *testing.T) {
var v struct { t.Run("CustomStringer", func(t *testing.T) {
Sort map[string]string `key:"sort"` var v struct {
} Sort map[string]string `key:"sort"`
m := map[string]any{ }
"sort": CustomStringer(`"value":"ascend","emptyStr":""`), m := map[string]any{
} "sort": CustomStringer(`"value":"ascend","emptyStr":""`),
}
ast := assert.New(t) ast := assert.New(t)
if ast.NoError(UnmarshalKey(m, &v)) { if ast.NoError(UnmarshalKey(m, &v)) {
ast.Equal(2, len(v.Sort)) ast.Equal(2, len(v.Sort))
ast.Equal("ascend", v.Sort["value"]) ast.Equal("ascend", v.Sort["value"])
ast.Equal("", v.Sort["emptyStr"]) ast.Equal("", v.Sort["emptyStr"])
} }
})
t.Run("CustomStringer incorrect", func(t *testing.T) {
var v struct {
Sort map[string]string `key:"sort"`
}
m := map[string]any{
"sort": CustomStringer(`"value"`),
}
assert.Error(t, UnmarshalKey(m, &v))
})
} }
func TestUnmarshalStringMapFromUnsupportedType(t *testing.T) { func TestUnmarshalStringMapFromUnsupportedType(t *testing.T) {
@ -906,48 +1071,83 @@ func TestUnmarshalStringSliceMapFromString(t *testing.T) {
} }
func TestUnmarshalStruct(t *testing.T) { func TestUnmarshalStruct(t *testing.T) {
type address struct { t.Run("struct", func(t *testing.T) {
City string `key:"city"` type address struct {
ZipCode int `key:"zipcode,string"` City string `key:"city"`
DefaultString string `key:"defaultstring,default=hello"` ZipCode int `key:"zipcode,string"`
Optional string `key:",optional"` DefaultString string `key:"defaultstring,default=hello"`
} Optional string `key:",optional"`
type inner struct { }
Name string `key:"name"` type inner struct {
Address address `key:"address"` Name string `key:"name"`
AddressP *address `key:"addressp"` Address address `key:"address"`
AddressPP **address `key:"addresspp"` AddressP *address `key:"addressp"`
} AddressPP **address `key:"addresspp"`
m := map[string]any{ }
"name": "kevin", m := map[string]any{
"address": map[string]any{ "name": "kevin",
"city": "shanghai", "address": map[string]any{
"zipcode": "200000", "city": "shanghai",
}, "zipcode": "200000",
"addressp": map[string]any{ },
"city": "beijing", "addressp": map[string]any{
"zipcode": "300000", "city": "beijing",
}, "zipcode": "300000",
"addresspp": map[string]any{ },
"city": "guangzhou", "addresspp": map[string]any{
"zipcode": "400000", "city": "guangzhou",
}, "zipcode": "400000",
} },
}
var in inner var in inner
ast := assert.New(t) ast := assert.New(t)
if ast.NoError(UnmarshalKey(m, &in)) { if ast.NoError(UnmarshalKey(m, &in)) {
ast.Equal("kevin", in.Name) ast.Equal("kevin", in.Name)
ast.Equal("shanghai", in.Address.City) ast.Equal("shanghai", in.Address.City)
ast.Equal(200000, in.Address.ZipCode) ast.Equal(200000, in.Address.ZipCode)
ast.Equal("hello", in.AddressP.DefaultString) ast.Equal("hello", in.AddressP.DefaultString)
ast.Equal("beijing", in.AddressP.City) ast.Equal("beijing", in.AddressP.City)
ast.Equal(300000, in.AddressP.ZipCode) ast.Equal(300000, in.AddressP.ZipCode)
ast.Equal("hello", in.AddressP.DefaultString) ast.Equal("hello", in.AddressP.DefaultString)
ast.Equal("guangzhou", (*in.AddressPP).City) ast.Equal("guangzhou", (*in.AddressPP).City)
ast.Equal(400000, (*in.AddressPP).ZipCode) ast.Equal(400000, (*in.AddressPP).ZipCode)
ast.Equal("hello", (*in.AddressPP).DefaultString) ast.Equal("hello", (*in.AddressPP).DefaultString)
} }
})
t.Run("struct with error", func(t *testing.T) {
type address struct {
City string `key:"city"`
ZipCode int `key:"zipcode,string"`
DefaultString string `key:"defaultstring,default=hello"`
Optional string `key:",optional"`
}
type inner struct {
Name string `key:"name"`
Address address `key:"address"`
AddressP *address `key:"addressp"`
AddressPP **address `key:"addresspp"`
}
m := map[string]any{
"name": "kevin",
"address": map[string]any{
"city": "shanghai",
"zipcode": "200000",
},
"addressp": map[string]any{
"city": "beijing",
"zipcode": "300000",
},
"addresspp": map[string]any{
"city": "guangzhou",
"zipcode": "a",
},
}
var in inner
assert.Error(t, UnmarshalKey(m, &in))
})
} }
func TestUnmarshalStructOptionalDepends(t *testing.T) { func TestUnmarshalStructOptionalDepends(t *testing.T) {
@ -1086,21 +1286,44 @@ func TestUnmarshalStructOptionalDependsNot(t *testing.T) {
} }
func TestUnmarshalStructOptionalDependsNotErrorDetails(t *testing.T) { func TestUnmarshalStructOptionalDependsNotErrorDetails(t *testing.T) {
type address struct { t.Run("mutal optionals", func(t *testing.T) {
Optional string `key:",optional"` type address struct {
OptionalDepends string `key:",optional=!Optional"` Optional string `key:",optional"`
} OptionalDepends string `key:",optional=!Optional"`
type inner struct { }
Name string `key:"name"` type inner struct {
Address address `key:"address"` Name string `key:"name"`
} Address address `key:"address"`
}
m := map[string]any{ m := map[string]any{
"name": "kevin", "name": "kevin",
} }
var in inner var in inner
assert.Error(t, UnmarshalKey(m, &in)) assert.Error(t, UnmarshalKey(m, &in))
})
t.Run("with default", func(t *testing.T) {
type address struct {
Optional string `key:",optional"`
OptionalDepends string `key:",default=value,optional"`
}
type inner struct {
Name string `key:"name"`
Address address `key:"address"`
}
m := map[string]any{
"name": "kevin",
}
var in inner
if assert.NoError(t, UnmarshalKey(m, &in)) {
assert.Equal(t, "kevin", in.Name)
assert.Equal(t, "value", in.Address.OptionalDepends)
}
})
} }
func TestUnmarshalStructOptionalDependsNotNested(t *testing.T) { func TestUnmarshalStructOptionalDependsNotNested(t *testing.T) {
@ -1440,16 +1663,48 @@ func TestUnmarshalMapOfInt(t *testing.T) {
} }
} }
func TestUnmarshalMapOfStructError(t *testing.T) { func TestUnmarshalMapOfStruct(t *testing.T) {
m := map[string]any{ t.Run("map of struct with error", func(t *testing.T) {
"Ids": map[string]any{"first": "second"}, m := map[string]any{
} "Ids": map[string]any{"first": "second"},
var v struct {
Ids map[string]struct {
Name string
} }
} var v struct {
assert.Error(t, UnmarshalKey(m, &v)) Ids map[string]struct {
Name string
}
}
assert.Error(t, UnmarshalKey(m, &v))
})
t.Run("map of struct", func(t *testing.T) {
m := map[string]any{
"Ids": map[string]any{
"foo": map[string]any{"Name": "foo"},
},
}
var v struct {
Ids map[string]struct {
Name string
}
}
if assert.NoError(t, UnmarshalKey(m, &v)) {
assert.Equal(t, "foo", v.Ids["foo"].Name)
}
})
t.Run("map of struct error", func(t *testing.T) {
m := map[string]any{
"Ids": map[string]any{
"foo": map[string]any{"name": "foo"},
},
}
var v struct {
Ids map[string]struct {
Name string
}
}
assert.Error(t, UnmarshalKey(m, &v))
})
} }
func TestUnmarshalSlice(t *testing.T) { func TestUnmarshalSlice(t *testing.T) {
@ -1492,26 +1747,46 @@ func TestUnmarshalSlice(t *testing.T) {
} }
func TestUnmarshalSliceOfStruct(t *testing.T) { func TestUnmarshalSliceOfStruct(t *testing.T) {
m := map[string]any{ t.Run("slice of struct", func(t *testing.T) {
"Ids": []map[string]any{ m := map[string]any{
{ "Ids": []map[string]any{
"First": 1, {
"Second": 2, "First": 1,
"Second": 2,
},
}, },
},
}
var v struct {
Ids []struct {
First int
Second int
} }
} var v struct {
ast := assert.New(t) Ids []struct {
if ast.NoError(UnmarshalKey(m, &v)) { First int
ast.Equal(1, len(v.Ids)) Second int
ast.Equal(1, v.Ids[0].First) }
ast.Equal(2, v.Ids[0].Second) }
} ast := assert.New(t)
if ast.NoError(UnmarshalKey(m, &v)) {
ast.Equal(1, len(v.Ids))
ast.Equal(1, v.Ids[0].First)
ast.Equal(2, v.Ids[0].Second)
}
})
t.Run("slice of struct", func(t *testing.T) {
m := map[string]any{
"Ids": []map[string]any{
{
"First": "a",
"Second": 2,
},
},
}
var v struct {
Ids []struct {
First int
Second int
}
}
assert.Error(t, UnmarshalKey(m, &v))
})
} }
func TestUnmarshalWithStringOptionsCorrect(t *testing.T) { func TestUnmarshalWithStringOptionsCorrect(t *testing.T) {
@ -3122,21 +3397,57 @@ func TestUnmarshalRangeError(t *testing.T) {
} }
func TestUnmarshalNestedMap(t *testing.T) { func TestUnmarshalNestedMap(t *testing.T) {
var c struct { t.Run("nested map", func(t *testing.T) {
Anything map[string]map[string]string `json:"anything"` var c struct {
} Anything map[string]map[string]string `json:"anything"`
m := map[string]any{ }
"anything": map[string]map[string]any{ m := map[string]any{
"inner": { "anything": map[string]map[string]any{
"id": "1", "inner": {
"name": "any", "id": "1",
"name": "any",
},
}, },
}, }
}
if assert.NoError(t, NewUnmarshaler("json").Unmarshal(m, &c)) { if assert.NoError(t, NewUnmarshaler("json").Unmarshal(m, &c)) {
assert.Equal(t, "1", c.Anything["inner"]["id"]) assert.Equal(t, "1", c.Anything["inner"]["id"])
} }
})
t.Run("nested map with slice element", func(t *testing.T) {
var c struct {
Anything map[string][]string `json:"anything"`
}
m := map[string]any{
"anything": map[string][]any{
"inner": {
"id",
"name",
},
},
}
if assert.NoError(t, NewUnmarshaler("json").Unmarshal(m, &c)) {
assert.Equal(t, []string{"id", "name"}, c.Anything["inner"])
}
})
t.Run("nested map with slice element error", func(t *testing.T) {
var c struct {
Anything map[string][]string `json:"anything"`
}
m := map[string]any{
"anything": map[string][]any{
"inner": {
"id",
1,
},
},
}
assert.Error(t, NewUnmarshaler("json").Unmarshal(m, &c))
})
} }
func TestUnmarshalNestedMapMismatch(t *testing.T) { func TestUnmarshalNestedMapMismatch(t *testing.T) {
@ -3810,15 +4121,27 @@ func TestUnmarshal_EnvWithOptionsWrongValueString(t *testing.T) {
} }
func TestUnmarshalJsonReaderMultiArray(t *testing.T) { func TestUnmarshalJsonReaderMultiArray(t *testing.T) {
var res struct { t.Run("reader multi array", func(t *testing.T) {
A string `json:"a"` var res struct {
B [][]string `json:"b"` A string `json:"a"`
} B [][]string `json:"b"`
payload := `{"a": "133", "b": [["add", "cccd"], ["eeee"]]}` }
reader := strings.NewReader(payload) payload := `{"a": "133", "b": [["add", "cccd"], ["eeee"]]}`
if assert.NoError(t, UnmarshalJsonReader(reader, &res)) { reader := strings.NewReader(payload)
assert.Equal(t, 2, len(res.B)) if assert.NoError(t, UnmarshalJsonReader(reader, &res)) {
} assert.Equal(t, 2, len(res.B))
}
})
t.Run("reader multi array with error", func(t *testing.T) {
var res struct {
A string `json:"a"`
B [][]string `json:"b"`
}
payload := `{"a": "133", "b": ["eeee"]}`
reader := strings.NewReader(payload)
assert.Error(t, UnmarshalJsonReader(reader, &res))
})
} }
func TestUnmarshalJsonReaderPtrMultiArrayString(t *testing.T) { func TestUnmarshalJsonReaderPtrMultiArrayString(t *testing.T) {
@ -4059,12 +4382,24 @@ func TestUnmarshalJsonReaderWithTypeMismatchBool(t *testing.T) {
assert.Equal(t, errTypeMismatch, UnmarshalJsonReader(strings.NewReader(body), &req)) assert.Equal(t, errTypeMismatch, UnmarshalJsonReader(strings.NewReader(body), &req))
} }
func TestUnmarshalJsonReaderWithTypeMismatchString(t *testing.T) { func TestUnmarshalJsonReaderWithTypeString(t *testing.T) {
var req struct { t.Run("string type", func(t *testing.T) {
Params map[string]string `json:"params"` var req struct {
} Params map[string]string `json:"params"`
body := `{"params":{"a":{"a":123}}}` }
assert.Equal(t, errTypeMismatch, UnmarshalJsonReader(strings.NewReader(body), &req)) body := `{"params":{"a":"b"}}`
if assert.NoError(t, UnmarshalJsonReader(strings.NewReader(body), &req)) {
assert.Equal(t, "b", req.Params["a"])
}
})
t.Run("string type mismatch", func(t *testing.T) {
var req struct {
Params map[string]string `json:"params"`
}
body := `{"params":{"a":{"a":123}}}`
assert.Equal(t, errTypeMismatch, UnmarshalJsonReader(strings.NewReader(body), &req))
})
} }
func TestUnmarshalJsonReaderWithMismatchType(t *testing.T) { func TestUnmarshalJsonReaderWithMismatchType(t *testing.T) {
@ -4077,43 +4412,95 @@ func TestUnmarshalJsonReaderWithMismatchType(t *testing.T) {
assert.Equal(t, errTypeMismatch, UnmarshalJsonReader(strings.NewReader(body), &req)) assert.Equal(t, errTypeMismatch, UnmarshalJsonReader(strings.NewReader(body), &req))
} }
func TestUnmarshalJsonReaderWithMismatchTypeBool(t *testing.T) { func TestUnmarshalJsonReaderWithTypeBool(t *testing.T) {
type Req struct { t.Run("bool type", func(t *testing.T) {
Params map[string]bool `json:"params"` type Req struct {
} Params map[string]bool `json:"params"`
}
tests := []struct { tests := []struct {
name string name string
input string input string
}{ expect bool
{ }{
name: "int", {
input: `{"params":{"a":123}}`, name: "int",
}, input: `{"params":{"a":1}}`,
{ expect: true,
name: "int", },
input: `{"params":{"a":"123"}}`, {
}, name: "int",
} input: `{"params":{"a":0}}`,
expect: false,
},
}
for _, test := range tests { for _, test := range tests {
test := test test := test
t.Run(test.name, func(t *testing.T) { t.Run(test.name, func(t *testing.T) {
var req Req var req Req
assert.Equal(t, errTypeMismatch, UnmarshalJsonReader(strings.NewReader(test.input), &req)) if assert.NoError(t, UnmarshalJsonReader(strings.NewReader(test.input), &req)) {
}) assert.Equal(t, test.expect, req.Params["a"])
} }
})
}
})
t.Run("bool type mismatch", func(t *testing.T) {
type Req struct {
Params map[string]bool `json:"params"`
}
tests := []struct {
name string
input string
}{
{
name: "int",
input: `{"params":{"a":123}}`,
},
{
name: "int",
input: `{"params":{"a":"123"}}`,
},
}
for _, test := range tests {
test := test
t.Run(test.name, func(t *testing.T) {
var req Req
assert.Equal(t, errTypeMismatch, UnmarshalJsonReader(strings.NewReader(test.input), &req))
})
}
})
} }
func TestUnmarshalJsonReaderWithMismatchTypeBoolMap(t *testing.T) { func TestUnmarshalJsonReaderWithTypeBoolMap(t *testing.T) {
var req struct { t.Run("bool map", func(t *testing.T) {
Params map[string]string `json:"params"` var req struct {
} Params map[string]bool `json:"params"`
assert.Equal(t, errTypeMismatch, UnmarshalJsonMap(map[string]any{ }
"params": map[string]any{ if assert.NoError(t, UnmarshalJsonMap(map[string]any{
"a": true, "params": map[string]any{
}, "a": true,
}, &req)) },
}, &req)) {
assert.Equal(t, map[string]bool{
"a": true,
}, req.Params)
}
})
t.Run("bool map with error", func(t *testing.T) {
var req struct {
Params map[string]string `json:"params"`
}
assert.Equal(t, errTypeMismatch, UnmarshalJsonMap(map[string]any{
"params": map[string]any{
"a": true,
},
}, &req))
})
} }
func TestUnmarshalJsonBytesSliceOfMaps(t *testing.T) { func TestUnmarshalJsonBytesSliceOfMaps(t *testing.T) {
@ -4446,6 +4833,55 @@ func Test_UnmarshalMap(t *testing.T) {
var customer Customer var customer Customer
assert.ErrorIs(t, UnmarshalKey(input, &customer), errTypeMismatch) assert.ErrorIs(t, UnmarshalKey(input, &customer), errTypeMismatch)
}) })
t.Run("map from string", func(t *testing.T) {
type Customer struct {
Names map[string]string `key:"names,string"`
}
input := map[string]any{
"names": `{"name": "Tom"}`,
}
var customer Customer
assert.NoError(t, UnmarshalKey(input, &customer))
assert.Equal(t, "Tom", customer.Names["name"])
})
t.Run("map from string with error", func(t *testing.T) {
type Customer struct {
Names map[string]any `key:"names,string"`
}
input := map[string]any{
"names": `"name"`,
}
var customer Customer
assert.Error(t, UnmarshalKey(input, &customer))
})
}
// func TestUnmarshalWithFillPrimitives(t *testing.T) {
// t.Run("fill primitives", func(t *testing.T) {
// type St struct {
// A int `key:"a,string,range=[5,10]"`
// }
// var st St
// err := UnmarshalKey(map[string]any{
// "a": "1",
// }, &st)
// assert.ErrorIs(t, err, errNumberRange)
// })
// }
func TestUnmarshaler_Unmarshal(t *testing.T) {
t.Run("not struct", func(t *testing.T) {
var i int
unmarshaler := NewUnmarshaler(jsonTagKey)
err := unmarshaler.UnmarshalValuer(nil, &i)
assert.Error(t, err)
})
} }
func TestGetValueWithChainedKeys(t *testing.T) { func TestGetValueWithChainedKeys(t *testing.T) {

Loading…
Cancel
Save