diff options
Diffstat (limited to 'compat/json/compat.go')
-rw-r--r-- | compat/json/compat.go | 45 |
1 files changed, 42 insertions, 3 deletions
diff --git a/compat/json/compat.go b/compat/json/compat.go index 78a9d5f..b26914b 100644 --- a/compat/json/compat.go +++ b/compat/json/compat.go @@ -8,7 +8,9 @@ import ( "bufio" "bytes" "encoding/json" + "errors" "io" + "strconv" "git.lukeshu.com/go/lowmemjson" ) @@ -19,7 +21,7 @@ type ( RawMessage = json.RawMessage // low-level decode errors - SyntaxError = lowmemjson.SyntaxError + //SyntaxError = lowmemjson.DecodeSyntaxError // expose a field UnmarshalFieldError = json.UnmarshalFieldError UnmarshalTypeError = json.UnmarshalTypeError // lowmemjson.DecodeTypeError @@ -28,7 +30,7 @@ type ( // marshal errors InvalidUTF8Error = json.InvalidUTF8Error - MarshalerError = json.MarshalerError + MarshalerError = lowmemjson.EncodeMethodError // expose a field UnsupportedTypeError = json.UnsupportedTypeError UnsupportedValueError = json.UnsupportedValueError ) @@ -92,7 +94,7 @@ func Valid(data []byte) bool { } func Unmarshal(data []byte, ptr any) error { - return lowmemjson.Decode(bytes.NewReader(data), ptr) + return NewDecoder(bytes.NewReader(data)).Decode(ptr) } ///////////////////////////////////////////////////////////////////// @@ -113,6 +115,43 @@ func NewDecoder(r io.Reader) *Decoder { } } +func (dec *Decoder) Decode(ptr any) error { + err := dec.Decoder.Decode(ptr) + if derr, ok := err.(*lowmemjson.DecodeError); ok { + switch terr := derr.Err.(type) { + case *lowmemjson.DecodeSyntaxError: + err = &SyntaxError{ + msg: terr.Err.Error(), + Offset: terr.Offset, + } + case *lowmemjson.DecodeTypeError: + if typeErr, ok := terr.Err.(*json.UnmarshalTypeError); ok { + err = &UnmarshalTypeError{ + Value: typeErr.Value, + Type: typeErr.Type, + Offset: typeErr.Offset, + Struct: derr.FieldParent, + Field: derr.FieldName, + } + } else if _, isArgErr := terr.Err.(*lowmemjson.DecodeArgumentError); terr.Err != nil && + !isArgErr && + !errors.Is(terr.Err, strconv.ErrSyntax) && + !errors.Is(terr.Err, strconv.ErrRange) { + err = terr.Err + } else { + err = &UnmarshalTypeError{ + Value: terr.JSONType, + Type: terr.GoType, + Offset: terr.Offset, + Struct: derr.FieldParent, + Field: derr.FieldName, + } + } + } + } + return err +} + func (dec *Decoder) Buffered() io.Reader { dat, _ := dec.buf.Peek(dec.buf.Buffered()) return bytes.NewReader(dat) |