mirror of
https://github.com/json-iterator/go.git
synced 2025-04-20 11:28:49 +02:00
fix #313 support json marshaller type as map key
This commit is contained in:
parent
5916df66b3
commit
05d041de10
@ -1,13 +1,13 @@
|
|||||||
package test
|
package test
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"bytes"
|
||||||
"github.com/json-iterator/go"
|
"github.com/json-iterator/go"
|
||||||
"github.com/stretchr/testify/require"
|
"github.com/stretchr/testify/require"
|
||||||
"strconv"
|
"strconv"
|
||||||
"testing"
|
"testing"
|
||||||
"time"
|
"time"
|
||||||
"unsafe"
|
"unsafe"
|
||||||
"bytes"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
func Test_customize_type_decoder(t *testing.T) {
|
func Test_customize_type_decoder(t *testing.T) {
|
||||||
|
@ -64,14 +64,26 @@ func decoderOfMapKey(ctx *ctx, typ reflect2.Type) ValDecoder {
|
|||||||
return &numericMapKeyDecoder{decoderOfType(ctx, typ)}
|
return &numericMapKeyDecoder{decoderOfType(ctx, typ)}
|
||||||
default:
|
default:
|
||||||
ptrType := reflect2.PtrTo(typ)
|
ptrType := reflect2.PtrTo(typ)
|
||||||
if ptrType.Implements(textMarshalerType) {
|
if ptrType.Implements(unmarshalerType) {
|
||||||
|
return &referenceDecoder{
|
||||||
|
&unmarshalerDecoder{
|
||||||
|
valType: ptrType,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if typ.Implements(unmarshalerType) {
|
||||||
|
return &unmarshalerDecoder{
|
||||||
|
valType: typ,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if ptrType.Implements(textUnmarshalerType) {
|
||||||
return &referenceDecoder{
|
return &referenceDecoder{
|
||||||
&textUnmarshalerDecoder{
|
&textUnmarshalerDecoder{
|
||||||
valType: ptrType,
|
valType: ptrType,
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if typ.Implements(textMarshalerType) {
|
if typ.Implements(textUnmarshalerType) {
|
||||||
return &textUnmarshalerDecoder{
|
return &textUnmarshalerDecoder{
|
||||||
valType: typ,
|
valType: typ,
|
||||||
}
|
}
|
||||||
|
@ -2,7 +2,9 @@ package test
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
|
"fmt"
|
||||||
"math/big"
|
"math/big"
|
||||||
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
@ -27,6 +29,8 @@ func init() {
|
|||||||
nilMap,
|
nilMap,
|
||||||
&nilMap,
|
&nilMap,
|
||||||
map[string]*json.RawMessage{"hello": pRawMessage(json.RawMessage("[]"))},
|
map[string]*json.RawMessage{"hello": pRawMessage(json.RawMessage("[]"))},
|
||||||
|
map[Date]bool{{}: true},
|
||||||
|
map[Date2]bool{{}: true},
|
||||||
)
|
)
|
||||||
unmarshalCases = append(unmarshalCases, unmarshalCase{
|
unmarshalCases = append(unmarshalCases, unmarshalCase{
|
||||||
ptr: (*map[string]string)(nil),
|
ptr: (*map[string]string)(nil),
|
||||||
@ -37,6 +41,20 @@ func init() {
|
|||||||
}, unmarshalCase{
|
}, unmarshalCase{
|
||||||
ptr: (*map[string]*json.RawMessage)(nil),
|
ptr: (*map[string]*json.RawMessage)(nil),
|
||||||
input: "{\"test\":[{\"key\":\"value\"}]}",
|
input: "{\"test\":[{\"key\":\"value\"}]}",
|
||||||
|
}, unmarshalCase{
|
||||||
|
ptr: (*map[Date]bool)(nil),
|
||||||
|
input: `{
|
||||||
|
"2018-12-12": true,
|
||||||
|
"2018-12-13": true,
|
||||||
|
"2018-12-14": true
|
||||||
|
}`,
|
||||||
|
}, unmarshalCase{
|
||||||
|
ptr: (*map[Date2]bool)(nil),
|
||||||
|
input: `{
|
||||||
|
"2018-12-12": true,
|
||||||
|
"2018-12-13": true,
|
||||||
|
"2018-12-14": true
|
||||||
|
}`,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -49,3 +67,51 @@ type MyString string
|
|||||||
func (ms MyString) Hello() string {
|
func (ms MyString) Hello() string {
|
||||||
return string(ms)
|
return string(ms)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type Date struct {
|
||||||
|
time.Time
|
||||||
|
}
|
||||||
|
|
||||||
|
func (d *Date) UnmarshalJSON(b []byte) error {
|
||||||
|
dateStr := string(b) // something like `"2017-08-20"`
|
||||||
|
|
||||||
|
if dateStr == "null" {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
t, err := time.Parse(`"2006-01-02"`, dateStr)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("cant parse date: %#v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
d.Time = t
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (d *Date) MarshalJSON() ([]byte, error) {
|
||||||
|
return []byte(d.Time.Format("2006-01-02")), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
type Date2 struct {
|
||||||
|
time.Time
|
||||||
|
}
|
||||||
|
|
||||||
|
func (d Date2) UnmarshalJSON(b []byte) error {
|
||||||
|
dateStr := string(b) // something like `"2017-08-20"`
|
||||||
|
|
||||||
|
if dateStr == "null" {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
t, err := time.Parse(`"2006-01-02"`, dateStr)
|
||||||
|
if err != nil {
|
||||||
|
return fmt.Errorf("cant parse date: %#v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
d.Time = t
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (d Date2) MarshalJSON() ([]byte, error) {
|
||||||
|
return []byte(d.Time.Format("2006-01-02")), nil
|
||||||
|
}
|
||||||
|
@ -7,12 +7,12 @@ import (
|
|||||||
func init() {
|
func init() {
|
||||||
marshalCases = append(marshalCases,
|
marshalCases = append(marshalCases,
|
||||||
json.RawMessage("{}"),
|
json.RawMessage("{}"),
|
||||||
selectedMarshalCase{struct {
|
struct {
|
||||||
Env string `json:"env"`
|
Env string `json:"env"`
|
||||||
Extra json.RawMessage `json:"extra,omitempty"`
|
Extra json.RawMessage `json:"extra,omitempty"`
|
||||||
}{
|
}{
|
||||||
Env: "jfdk",
|
Env: "jfdk",
|
||||||
}},
|
},
|
||||||
)
|
)
|
||||||
unmarshalCases = append(unmarshalCases, unmarshalCase{
|
unmarshalCases = append(unmarshalCases, unmarshalCase{
|
||||||
ptr: (*json.RawMessage)(nil),
|
ptr: (*json.RawMessage)(nil),
|
||||||
|
Loading…
x
Reference in New Issue
Block a user