parent
0d97e820e4
commit
3d0c541f69
@ -0,0 +1,192 @@
|
|||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// Project atila
|
||||||
|
// Active Thing (activething.com) git.activething.com/go
|
||||||
|
//
|
||||||
|
// File name f.go
|
||||||
|
// Created by DEV
|
||||||
|
// Modified 29/01/2024
|
||||||
|
//
|
||||||
|
// Copyright 2024 activething.com
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
|
||||||
|
package packs
|
||||||
|
|
||||||
|
import (
|
||||||
|
"strings"
|
||||||
|
"time"
|
||||||
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
|
||||||
|
FlagOmitEmpty Flags = 1 << iota
|
||||||
|
FlagQuote
|
||||||
|
FlagScapeHTML
|
||||||
|
|
||||||
|
FlagBinary64 Flags = 0b0000100000000000
|
||||||
|
FlagBinary32 Flags = 0b0000010000000000
|
||||||
|
|
||||||
|
FlagDateRFC822 Flags = 0b0001000000000000
|
||||||
|
FlagDateUnix Flags = 0b0010000000000000
|
||||||
|
FlagDateANSIC Flags = 0b0100000000000000
|
||||||
|
FlagDateRFC850 Flags = 0b1000000000000000
|
||||||
|
|
||||||
|
binMask = 0b0000110000000000
|
||||||
|
dateMask = 0b1111000000000000
|
||||||
|
flagMaskBin Flags = 0b1111001111111111
|
||||||
|
flagMaskDate Flags = 0b0000111111111111
|
||||||
|
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
type Flags uint16
|
||||||
|
|
||||||
|
|
||||||
|
func (f Flags) OmitEmpty () bool {
|
||||||
|
return f&FlagOmitEmpty != 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (f Flags) Quote () bool {
|
||||||
|
return f&FlagQuote != 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (f Flags) EscapeHTML () bool {
|
||||||
|
return f&FlagScapeHTML != 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (f Flags) Binary () bool {
|
||||||
|
return f&(FlagBinary64|FlagBinary32) != 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (f Flags) Bin64 () bool {
|
||||||
|
return f&FlagBinary64 != 0
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func (f Flags) Bin32 () bool {
|
||||||
|
return f&FlagBinary32 != 0
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func (f Flags) SetWithName(flag string) Flags {
|
||||||
|
switch strings.ToLower(flag) {
|
||||||
|
case "o","omitempty": return f | FlagOmitEmpty
|
||||||
|
case "q","quote" : return f | FlagQuote
|
||||||
|
case "h","html" : return f | FlagScapeHTML
|
||||||
|
|
||||||
|
// formato binario
|
||||||
|
case "b64","bin64" : return (f & flagMaskBin) | FlagBinary64
|
||||||
|
case "b32","bin32" : return (f & flagMaskBin) | FlagBinary32
|
||||||
|
|
||||||
|
// formatos de fechas
|
||||||
|
case "unix" : return (f & flagMaskDate) | FlagDateUnix
|
||||||
|
case "rfc822" : return (f & flagMaskDate) | FlagDateRFC822
|
||||||
|
case "ansic" : return (f & flagMaskDate) | FlagDateANSIC
|
||||||
|
case "rfc850" : return (f & flagMaskDate) | FlagDateRFC850
|
||||||
|
case "rfc822z": return f & flagMaskDate
|
||||||
|
|
||||||
|
default: return f
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func (f Flags) SetWithNames(flags ... string) Flags {
|
||||||
|
nf := f
|
||||||
|
for _,n := range flags {
|
||||||
|
switch strings.ToLower(n) {
|
||||||
|
case "o","omitempty": nf |= FlagOmitEmpty
|
||||||
|
case "q","quote" : nf |= FlagQuote
|
||||||
|
case "h","html" : nf |= FlagScapeHTML
|
||||||
|
|
||||||
|
// formatos binarios
|
||||||
|
case "b32","bin32" : nf = (nf & flagMaskBin) | FlagBinary32
|
||||||
|
case "b64","bin64" : nf = (nf & flagMaskBin) | FlagBinary64
|
||||||
|
|
||||||
|
// formatos de fechas
|
||||||
|
case "unix" : nf = (nf & flagMaskDate) | FlagDateUnix
|
||||||
|
case "rfc822" : nf = (nf & flagMaskDate) | FlagDateRFC822
|
||||||
|
case "ansic" : nf = (nf & flagMaskDate) | FlagDateANSIC
|
||||||
|
case "rfc850" : nf = (nf & flagMaskDate) | FlagDateRFC850
|
||||||
|
case "rfc822z": nf &= flagMaskDate
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return nf
|
||||||
|
}
|
||||||
|
|
||||||
|
func (f Flags) SetWithString (flags string) Flags {
|
||||||
|
if len(flags) == 0 {
|
||||||
|
return f
|
||||||
|
}
|
||||||
|
nf := f
|
||||||
|
for flags != "" {
|
||||||
|
var op string
|
||||||
|
op,flags,_ = strings.Cut(flags,",")
|
||||||
|
nf |= f.SetWithName(op)
|
||||||
|
}
|
||||||
|
return nf
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func (f Flags) Names () string {
|
||||||
|
var ls []string
|
||||||
|
if f&FlagOmitEmpty != 0 { ls = append(ls,"omitempty")}
|
||||||
|
if f&FlagQuote != 0 { ls = append(ls,"quote")}
|
||||||
|
if f&FlagScapeHTML != 0 { ls = append(ls,"html")}
|
||||||
|
|
||||||
|
if f&flagMaskBin != 0 {
|
||||||
|
ls = append(ls,f.binName())
|
||||||
|
}
|
||||||
|
if f&dateMask != 0 {
|
||||||
|
ls = append(ls,f.dateName())
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(ls) > 0 {
|
||||||
|
return strings.Join(ls,",")
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
func (f Flags) binName () string {
|
||||||
|
switch f & binMask {
|
||||||
|
case FlagBinary64 : return "b64"
|
||||||
|
case FlagBinary32 : return "b32"
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func (f Flags) dateName() string {
|
||||||
|
switch f & dateMask {
|
||||||
|
case FlagDateUnix : return "unix"
|
||||||
|
case FlagDateRFC822: return "rfc822"
|
||||||
|
case FlagDateANSIC : return "ansic"
|
||||||
|
case FlagDateRFC850: return "rfc8550"
|
||||||
|
default: return time.RFC822Z
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func (f Flags) DateFormat () string {
|
||||||
|
switch f & dateMask {
|
||||||
|
case FlagDateUnix : return time.UnixDate
|
||||||
|
case FlagDateRFC822: return time.RFC822
|
||||||
|
case FlagDateANSIC : return time.ANSIC
|
||||||
|
case FlagDateRFC850: return time.RFC850
|
||||||
|
default: return time.RFC822Z
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -0,0 +1,41 @@
|
|||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// Project atila
|
||||||
|
// Active Thing (activething.com) git.activething.com/go
|
||||||
|
//
|
||||||
|
// File name json_char_atts.go
|
||||||
|
// Created by DEV
|
||||||
|
// Modified 18/01/2024
|
||||||
|
//
|
||||||
|
// Copyright 2024 activething.com
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
|
||||||
|
package pjson
|
||||||
|
|
||||||
|
const (
|
||||||
|
jsonCharAttUnsafe jsonCharAtt = 1 << iota
|
||||||
|
jsonCharAttHtmlUnsafe
|
||||||
|
|
||||||
|
jsonCharAttAllUnsafe = jsonCharAttUnsafe | jsonCharAttHtmlUnsafe
|
||||||
|
)
|
||||||
|
|
||||||
|
type jsonCharAtt uint8
|
||||||
|
|
||||||
|
func (a jsonCharAtt) isUnsafe() bool {
|
||||||
|
return a&jsonCharAttUnsafe != 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (a jsonCharAtt) isHtmlUnsafe() bool {
|
||||||
|
return a&jsonCharAttHtmlUnsafe != 0
|
||||||
|
}
|
||||||
@ -0,0 +1,168 @@
|
|||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// Project atila
|
||||||
|
// Active Thing (activething.com) git.activething.com/go
|
||||||
|
//
|
||||||
|
// File name gogo.go
|
||||||
|
// Created by DEV
|
||||||
|
// Modified 23/01/2024
|
||||||
|
//
|
||||||
|
// Copyright 2024 activething.com
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
|
||||||
|
package pjson
|
||||||
|
|
||||||
|
import (
|
||||||
|
"activething.com/go/gogo/packs"
|
||||||
|
"encoding"
|
||||||
|
"encoding/json"
|
||||||
|
"math"
|
||||||
|
"reflect"
|
||||||
|
"strconv"
|
||||||
|
"sync"
|
||||||
|
"unicode/utf8"
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
const startDetectingCyclesAfter = 100
|
||||||
|
|
||||||
|
|
||||||
|
var (
|
||||||
|
G = struct {
|
||||||
|
hex string
|
||||||
|
jsonChars [utf8.RuneSelf]jsonCharAtt
|
||||||
|
|
||||||
|
nullValue []byte
|
||||||
|
zeroValue []byte
|
||||||
|
trueValue []byte
|
||||||
|
falseValue []byte
|
||||||
|
|
||||||
|
floatNaN []byte
|
||||||
|
floatInfPos []byte
|
||||||
|
floatInfNeg []byte
|
||||||
|
|
||||||
|
|
||||||
|
packersCache sync.Map
|
||||||
|
keyersCache sync.Map
|
||||||
|
|
||||||
|
jsonMarshalerType reflect.Type
|
||||||
|
textMarshalerType reflect.Type
|
||||||
|
packMarshalerType reflect.Type
|
||||||
|
|
||||||
|
}{
|
||||||
|
|
||||||
|
hex: "0123456789abcdef",
|
||||||
|
jsonChars: initJSONChars(),
|
||||||
|
|
||||||
|
nullValue: []byte{'n', 'u', 'l', 'l'},
|
||||||
|
zeroValue: []byte{'0'},
|
||||||
|
trueValue: []byte{'"','t', 'r', 'u', 'e','"'},
|
||||||
|
falseValue: []byte{'"','f', 'a', 'l', 's', 'e','"'},
|
||||||
|
|
||||||
|
floatNaN: []byte{'"', 'N', 'a', 'N', '"'},
|
||||||
|
floatInfPos: []byte{'"', 'I', 'n', 'f', '"'},
|
||||||
|
floatInfNeg: []byte{'"', '-', 'I', 'n', 'f', '"'},
|
||||||
|
|
||||||
|
|
||||||
|
jsonMarshalerType: reflect.TypeOf((*json.Marshaler)(nil)).Elem(),
|
||||||
|
textMarshalerType: reflect.TypeOf((*encoding.TextMarshaler)(nil)).Elem(),
|
||||||
|
packMarshalerType: reflect.TypeOf((*packs.Packer)(nil)).Elem(),
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
func initJSONChars() [utf8.RuneSelf]jsonCharAtt {
|
||||||
|
var tb = [utf8.RuneSelf]jsonCharAtt{
|
||||||
|
'"': jsonCharAttAllUnsafe,
|
||||||
|
'&': jsonCharAttHtmlUnsafe,
|
||||||
|
'<': jsonCharAttHtmlUnsafe,
|
||||||
|
'>': jsonCharAttHtmlUnsafe,
|
||||||
|
'\\': jsonCharAttAllUnsafe,
|
||||||
|
}
|
||||||
|
for i := 0; i <= 31; i++ {
|
||||||
|
tb[i] = jsonCharAttAllUnsafe
|
||||||
|
}
|
||||||
|
return tb
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func stringifyKey(buffer []byte, value any) []byte {
|
||||||
|
if value == nil {
|
||||||
|
return G.nullValue
|
||||||
|
}
|
||||||
|
|
||||||
|
if st,is := value.(string); is {
|
||||||
|
return append(buffer[:0],st...)
|
||||||
|
}
|
||||||
|
|
||||||
|
if tm,is := value.(encoding.TextMarshaler); is {
|
||||||
|
if bf,er := tm.MarshalText(); er == nil {
|
||||||
|
return append(buffer[:0],bf...)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
switch tp := value.(type) {
|
||||||
|
case bool:
|
||||||
|
if tp {
|
||||||
|
return G.trueValue
|
||||||
|
}
|
||||||
|
return G.falseValue
|
||||||
|
|
||||||
|
case int : return strconv.AppendInt (buffer[:0],int64(tp), 10)
|
||||||
|
case int8 : return strconv.AppendInt (buffer[:0],int64(tp), 10)
|
||||||
|
case int16 : return strconv.AppendInt (buffer[:0],int64(tp), 10)
|
||||||
|
case int32 : return strconv.AppendInt (buffer[:0],int64(tp), 10)
|
||||||
|
case int64 : return strconv.AppendInt (buffer[:0],tp, 10)
|
||||||
|
|
||||||
|
case uint : return strconv.AppendUint(buffer[:0],uint64(tp), 10)
|
||||||
|
case uint8 : return strconv.AppendUint(buffer[:0],uint64(tp), 10)
|
||||||
|
case uint16 : return strconv.AppendUint(buffer[:0],uint64(tp), 10)
|
||||||
|
case uint32 : return strconv.AppendUint(buffer[:0],uint64(tp), 10)
|
||||||
|
case uint64 : return strconv.AppendUint(buffer[:0],tp, 10)
|
||||||
|
|
||||||
|
case float32: return stringifyFloat(buffer[:0],float64(tp),32)
|
||||||
|
case float64: return stringifyFloat(buffer[:0],tp,64)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func stringifyFloat (buffer []byte, f float64, bits int) []byte {
|
||||||
|
if math.IsInf(f, 0) || math.IsNaN(f) {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
abs := math.Abs(f)
|
||||||
|
fmt := byte('f')
|
||||||
|
|
||||||
|
if abs != 0 {
|
||||||
|
if bits == 64 && (abs < 1e-6 || abs >= 1e21) || bits == 32 && (float32(abs) < 1e-6 || float32(abs) >= 1e21) {
|
||||||
|
fmt = 'e'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
buffer = strconv.AppendFloat(buffer[:0], f, fmt, -1, int(bits))
|
||||||
|
if fmt == 'e' {
|
||||||
|
// clean up e-09 to e-9
|
||||||
|
n := len(buffer)
|
||||||
|
if n >= 4 && buffer[n-4] == 'e' && buffer[n-3] == '-' && buffer[n-2] == '0' {
|
||||||
|
buffer[n-2] = buffer[n-1]
|
||||||
|
buffer = buffer[:n-1]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return buffer
|
||||||
|
}
|
||||||
|
|
||||||
@ -0,0 +1,401 @@
|
|||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// Project atila
|
||||||
|
// Active Thing (activething.com) git.activething.com/go
|
||||||
|
//
|
||||||
|
// File name packer.go
|
||||||
|
// Created by DEV
|
||||||
|
// Modified 05/02/2024
|
||||||
|
//
|
||||||
|
// Copyright 2024 activething.com
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
|
||||||
|
package pjson
|
||||||
|
|
||||||
|
import (
|
||||||
|
"activething.com/go/gogo/core/opts"
|
||||||
|
"activething.com/go/gogo/packs"
|
||||||
|
"encoding/base32"
|
||||||
|
"encoding/base64"
|
||||||
|
"encoding/json"
|
||||||
|
"math"
|
||||||
|
"reflect"
|
||||||
|
"strconv"
|
||||||
|
"time"
|
||||||
|
"unicode/utf8"
|
||||||
|
)
|
||||||
|
|
||||||
|
type (
|
||||||
|
|
||||||
|
|
||||||
|
Packer struct {
|
||||||
|
state *packs.State
|
||||||
|
Options
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
func NewPacker (options opts.OptionFnc[Packer]) *Packer {
|
||||||
|
return opts.Apply[Packer](&Packer {
|
||||||
|
state : packs.NewState(),
|
||||||
|
}, options)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) Pack (value any, flags packs.Flags) ([]byte,error) {
|
||||||
|
if p.state.Error != nil {
|
||||||
|
return nil,packs.G.ErrInvalidState.WithCause(p.state.Error)
|
||||||
|
}
|
||||||
|
|
||||||
|
p.PackAny(value,flags)
|
||||||
|
if p.state.Error != nil {
|
||||||
|
return nil,p.state.Error
|
||||||
|
}
|
||||||
|
return p.state.Bytes(),nil
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackAny (value any, flags packs.Flags) {
|
||||||
|
if p.state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(p.state.Error))
|
||||||
|
}
|
||||||
|
if value == nil {
|
||||||
|
p.state.W(G.nullValue)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
switch v := value.(type) {
|
||||||
|
case packs.Builder:
|
||||||
|
p.state.SetError(v.Build(p))
|
||||||
|
|
||||||
|
case json.Marshaler:
|
||||||
|
d,e := v.MarshalJSON()
|
||||||
|
if e != nil {
|
||||||
|
p.state.SetError(e)
|
||||||
|
} else {
|
||||||
|
p.state.W(d)
|
||||||
|
}
|
||||||
|
|
||||||
|
case reflect.Value:
|
||||||
|
rPackAny(p.state,v,flags)
|
||||||
|
|
||||||
|
default:
|
||||||
|
rPackAny(p.state,reflect.ValueOf(value), flags)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackRaw (value []byte, flags packs.Flags) {
|
||||||
|
if p.state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(p.state.Error))
|
||||||
|
}
|
||||||
|
if value == nil {
|
||||||
|
p.state.W(G.nullValue)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if len(value) == 0 {
|
||||||
|
p.state.Write2Byte('"','"')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
p.state.W(value)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackBinary (value []byte, flags packs.Flags) { packBinary(p.state,value,flags) }
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackString (value string, flags packs.Flags) { packString (p.state,value,flags) }
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackBool (value bool, flags packs.Flags) { packBool(p.state,value,flags) }
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackInt8 (value int8 , flags packs.Flags) { packInt(p.state,int64(value),flags) }
|
||||||
|
func (p *Packer) PackInt16 (value int16, flags packs.Flags) { packInt(p.state,int64(value),flags) }
|
||||||
|
func (p *Packer) PackInt32 (value int32, flags packs.Flags) { packInt(p.state,int64(value),flags) }
|
||||||
|
func (p *Packer) PackInt64 (value int64, flags packs.Flags) { packInt(p.state,value,flags)}
|
||||||
|
|
||||||
|
func (p *Packer) PackUInt8 (value uint8 , flags packs.Flags) { packUInt(p.state,uint64(value),flags) }
|
||||||
|
func (p *Packer) PackUInt16 (value uint16, flags packs.Flags) { packUInt(p.state,uint64(value),flags) }
|
||||||
|
func (p *Packer) PackUInt32 (value uint32, flags packs.Flags) { packUInt(p.state,uint64(value),flags) }
|
||||||
|
func (p *Packer) PackUInt64 (value uint64, flags packs.Flags) { packUInt(p.state, value,flags) }
|
||||||
|
|
||||||
|
func (p *Packer) PackFloat32 (value float32, flags packs.Flags) { packFloatString(p.state, float64(value), flags, 32) }
|
||||||
|
func (p *Packer) PackFloat64 (value float64, flags packs.Flags) { packFloatString(p.state, value, flags, 64) }
|
||||||
|
|
||||||
|
func (p *Packer) PackDate (value time.Time, flags packs.Flags) { PackDate(p.state,value,flags) }
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackList (builder func(packs.ListPacker, packs.Flags)) {}
|
||||||
|
func (p *Packer) PackMap (builder func(packs.MapPacker, packs.Flags)) {}
|
||||||
|
func (p *Packer) PackObject(builder func(packs.ObjectPacker, packs.Flags)) {}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func packString (state *packs.State, value string , flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(value) == 0 {
|
||||||
|
state.Write2Byte('"','"')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
state.WriteByte('"')
|
||||||
|
start := 0
|
||||||
|
for i := 0; i < len(value); {
|
||||||
|
if b := value[i]; b < utf8.RuneSelf {
|
||||||
|
if !G.jsonChars[b].isHtmlUnsafe() || (!flags.EscapeHTML() && !G.jsonChars[b].isUnsafe()) {
|
||||||
|
i++
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
if start < i {
|
||||||
|
state.WriteString(value[start:i])
|
||||||
|
}
|
||||||
|
state.WriteByte('\\')
|
||||||
|
switch b {
|
||||||
|
case '\\', '"': state.WriteByte(b)
|
||||||
|
case '\n': state.WriteByte('n')
|
||||||
|
case '\r': state.WriteByte('r')
|
||||||
|
case '\t': state.WriteByte('t')
|
||||||
|
default:
|
||||||
|
state.WriteString(`u00`)
|
||||||
|
state.Write2Byte(G.hex[b>>4], G.hex[b&0xF])
|
||||||
|
}
|
||||||
|
i++
|
||||||
|
start = i
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
c, size := utf8.DecodeRuneInString(value[i:])
|
||||||
|
if c == utf8.RuneError && size == 1 {
|
||||||
|
if start < i {
|
||||||
|
state.WriteString(value[start:i])
|
||||||
|
}
|
||||||
|
state.WriteString(`\ufffd`)
|
||||||
|
i += size
|
||||||
|
start = i
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
if c == '\u2028' || c == '\u2029' {
|
||||||
|
if start < i {
|
||||||
|
state.WriteString(value[start:i])
|
||||||
|
}
|
||||||
|
state.WriteString(`\u202`)
|
||||||
|
state.WriteByte(G.hex[c&0xF])
|
||||||
|
i += size
|
||||||
|
start = i
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
i += size
|
||||||
|
}
|
||||||
|
if start < len(value) {
|
||||||
|
state.WriteString(value[start:])
|
||||||
|
}
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func packBinary (state *packs.State, value []byte , flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
|
||||||
|
if value == nil {
|
||||||
|
_,_ = state.Write(G.nullValue)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if len(value) == 0 {
|
||||||
|
state.Write2Byte('"','"')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
state.WriteByte('"')
|
||||||
|
|
||||||
|
if flags.Bin64() {
|
||||||
|
packBinary64(state, value, 0)
|
||||||
|
} else if flags.Bin32() {
|
||||||
|
packBinary32(state, value, 0)
|
||||||
|
} else {
|
||||||
|
state.SetError(packs.G.ErrUnsupportedType)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if state.Error == nil {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func packBinary64 (state *packs.State, value []byte , _ packs.Flags) {
|
||||||
|
ln := base64.StdEncoding.EncodedLen(len(value))
|
||||||
|
if ln <= len(state.Temp) {
|
||||||
|
dst := state.Temp[:ln]
|
||||||
|
base64.StdEncoding.Encode(dst, value)
|
||||||
|
_,_= state.Write(dst)
|
||||||
|
} else if ln <= 1024 {
|
||||||
|
dst := make([]byte, ln)
|
||||||
|
base64.StdEncoding.Encode(dst, value)
|
||||||
|
_,_ = state.Write(dst)
|
||||||
|
} else {
|
||||||
|
ec := base64.NewEncoder(base64.StdEncoding, state)
|
||||||
|
_,_ = ec.Write(value)
|
||||||
|
state.SetError(ec.Close())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func packBinary32 (state *packs.State, value []byte , _ packs.Flags) {
|
||||||
|
ln := base32.StdEncoding.EncodedLen(len(value))
|
||||||
|
if ln <= len(state.Temp) {
|
||||||
|
dst := state.Temp[:ln]
|
||||||
|
base32.StdEncoding.Encode(dst, value)
|
||||||
|
_,_= state.Write(dst)
|
||||||
|
} else if ln <= 1024 {
|
||||||
|
dst := make([]byte, ln)
|
||||||
|
base32.StdEncoding.Encode(dst, value)
|
||||||
|
_,_ = state.Write(dst)
|
||||||
|
} else {
|
||||||
|
ec := base32.NewEncoder(base32.StdEncoding, state)
|
||||||
|
_,_ = ec.Write(value)
|
||||||
|
state.SetError(ec.Close())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func packBool (state *packs.State, value bool , flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
if flags.Quote() {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
if value {
|
||||||
|
state.W(G.trueValue)
|
||||||
|
} else {
|
||||||
|
state.W(G.falseValue)
|
||||||
|
}
|
||||||
|
if flags.Quote() {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func packInt (state *packs.State, value int64 , flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
|
||||||
|
if flags.Quote() {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
if value == 0 {
|
||||||
|
state.WriteByte('0')
|
||||||
|
} else {
|
||||||
|
state.WriteIntStr(value, 10)
|
||||||
|
}
|
||||||
|
if flags.Quote() {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func packUInt (state *packs.State, value uint64 , flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
q :=flags.Quote()
|
||||||
|
if q {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
if value == 0 {
|
||||||
|
state.WriteByte('0')
|
||||||
|
} else {
|
||||||
|
state.WriteUIntStr(value, 10)
|
||||||
|
}
|
||||||
|
if q {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func packFloat (state *packs.State, value float64, flags packs.Flags) {
|
||||||
|
packFloatString(state, value, flags, 64)
|
||||||
|
}
|
||||||
|
|
||||||
|
func packFloatString (state *packs.State, f float64, flags packs.Flags, bits int) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
|
||||||
|
if math.IsInf(f, 0) || math.IsNaN(f) {
|
||||||
|
state.SetError(packs.G.ErrInvalidValue)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
abs := math.Abs(f)
|
||||||
|
fmt := byte('f')
|
||||||
|
|
||||||
|
if abs != 0 {
|
||||||
|
if bits == 64 && (abs < 1e-6 || abs >= 1e21) || bits == 32 && (float32(abs) < 1e-6 || float32(abs) >= 1e21) {
|
||||||
|
fmt = 'e'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
bf := state.Temp[:0]
|
||||||
|
bf = strconv.AppendFloat(bf, f, fmt, -1, int(bits))
|
||||||
|
if fmt == 'e' {
|
||||||
|
// clean up e-09 to e-9
|
||||||
|
n := len(bf)
|
||||||
|
if n >= 4 && bf[n-4] == 'e' && bf[n-3] == '-' && bf[n-2] == '0' {
|
||||||
|
bf[n-2] = bf[n-1]
|
||||||
|
bf = bf[:n-1]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if flags.Quote() {
|
||||||
|
state.WriteByte('"')
|
||||||
|
state.W(bf)
|
||||||
|
state.WriteByte('"')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
state.W(bf)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func PackDate (state *packs.State, value time.Time, flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
state.WriteByte('"')
|
||||||
|
bf := state.Temp[:0]
|
||||||
|
bf = value.AppendFormat(bf,flags.DateFormat())
|
||||||
|
state.W(bf)
|
||||||
|
state.WriteByte('"')
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -0,0 +1,363 @@
|
|||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// Project atila
|
||||||
|
// Active Thing (activething.com) git.activething.com/go
|
||||||
|
//
|
||||||
|
// File name packer_value.go
|
||||||
|
// Created by DEV
|
||||||
|
// Modified 05/02/2024
|
||||||
|
//
|
||||||
|
// Copyright 2024 activething.com
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
// ------------------------------------------------------------------------
|
||||||
|
|
||||||
|
package pjson
|
||||||
|
|
||||||
|
import (
|
||||||
|
"activething.com/go/gogo/packs"
|
||||||
|
"encoding/base32"
|
||||||
|
"encoding/base64"
|
||||||
|
"encoding/json"
|
||||||
|
"math"
|
||||||
|
"reflect"
|
||||||
|
"strconv"
|
||||||
|
"time"
|
||||||
|
"unicode/utf8"
|
||||||
|
)
|
||||||
|
|
||||||
|
func (p *Packer) PackAny (value any, flags packs.Flags) {
|
||||||
|
if p.state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(p.state.Error))
|
||||||
|
}
|
||||||
|
if value == nil {
|
||||||
|
p.state.W(G.nullValue)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
switch v := value.(type) {
|
||||||
|
case packs.Builder:
|
||||||
|
p.state.SetError(v.Build(p))
|
||||||
|
|
||||||
|
case json.Marshaler:
|
||||||
|
d,e := v.MarshalJSON()
|
||||||
|
if e != nil {
|
||||||
|
p.state.SetError(e)
|
||||||
|
} else {
|
||||||
|
p.state.W(d)
|
||||||
|
}
|
||||||
|
|
||||||
|
case reflect.Value:
|
||||||
|
rPackAny(p.state,v,flags)
|
||||||
|
|
||||||
|
default:
|
||||||
|
rPackAny(p.state,reflect.ValueOf(value), flags)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackRaw (value []byte, flags packs.Flags) {
|
||||||
|
if p.state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(p.state.Error))
|
||||||
|
}
|
||||||
|
if value == nil {
|
||||||
|
p.state.W(G.nullValue)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if len(value) == 0 {
|
||||||
|
p.state.Write2Byte('"','"')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
p.state.W(value)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackBinary (value []byte, flags packs.Flags) { packBinary(p.state,value,flags) }
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackString (value string, flags packs.Flags) { packString (p.state,value,flags) }
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackBool (value bool, flags packs.Flags) { packBool(p.state,value,flags) }
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackInt8 (value int8 , flags packs.Flags) { packInt(p.state,int64(value),flags) }
|
||||||
|
func (p *Packer) PackInt16 (value int16, flags packs.Flags) { packInt(p.state,int64(value),flags) }
|
||||||
|
func (p *Packer) PackInt32 (value int32, flags packs.Flags) { packInt(p.state,int64(value),flags) }
|
||||||
|
func (p *Packer) PackInt64 (value int64, flags packs.Flags) { packInt(p.state,value,flags)}
|
||||||
|
|
||||||
|
func (p *Packer) PackUInt8 (value uint8 , flags packs.Flags) { packUInt(p.state,uint64(value),flags) }
|
||||||
|
func (p *Packer) PackUInt16 (value uint16, flags packs.Flags) { packUInt(p.state,uint64(value),flags) }
|
||||||
|
func (p *Packer) PackUInt32 (value uint32, flags packs.Flags) { packUInt(p.state,uint64(value),flags) }
|
||||||
|
func (p *Packer) PackUInt64 (value uint64, flags packs.Flags) { packUInt(p.state, value,flags) }
|
||||||
|
|
||||||
|
func (p *Packer) PackFloat32 (value float32, flags packs.Flags) { packFloatString(p.state, float64(value), flags, 32) }
|
||||||
|
func (p *Packer) PackFloat64 (value float64, flags packs.Flags) { packFloatString(p.state, value, flags, 64) }
|
||||||
|
|
||||||
|
func (p *Packer) PackDate (value time.Time, flags packs.Flags) { PackDate(p.state,value,flags) }
|
||||||
|
|
||||||
|
|
||||||
|
func (p *Packer) PackList (builder func(packs.ListPacker, packs.Flags)) {}
|
||||||
|
func (p *Packer) PackMap (builder func(packs.MapPacker, packs.Flags)) {}
|
||||||
|
func (p *Packer) PackObject(builder func(packs.ObjectPacker, packs.Flags)) {}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func packString (state *packs.State, value string , flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(value) == 0 {
|
||||||
|
state.Write2Byte('"','"')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
state.WriteByte('"')
|
||||||
|
start := 0
|
||||||
|
for i := 0; i < len(value); {
|
||||||
|
if b := value[i]; b < utf8.RuneSelf {
|
||||||
|
if !G.jsonChars[b].isHtmlUnsafe() || (!flags.EscapeHTML() && !G.jsonChars[b].isUnsafe()) {
|
||||||
|
i++
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
if start < i {
|
||||||
|
state.WriteString(value[start:i])
|
||||||
|
}
|
||||||
|
state.WriteByte('\\')
|
||||||
|
switch b {
|
||||||
|
case '\\', '"': state.WriteByte(b)
|
||||||
|
case '\n': state.WriteByte('n')
|
||||||
|
case '\r': state.WriteByte('r')
|
||||||
|
case '\t': state.WriteByte('t')
|
||||||
|
default:
|
||||||
|
state.WriteString(`u00`)
|
||||||
|
state.Write2Byte(G.hex[b>>4], G.hex[b&0xF])
|
||||||
|
}
|
||||||
|
i++
|
||||||
|
start = i
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
c, size := utf8.DecodeRuneInString(value[i:])
|
||||||
|
if c == utf8.RuneError && size == 1 {
|
||||||
|
if start < i {
|
||||||
|
state.WriteString(value[start:i])
|
||||||
|
}
|
||||||
|
state.WriteString(`\ufffd`)
|
||||||
|
i += size
|
||||||
|
start = i
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
if c == '\u2028' || c == '\u2029' {
|
||||||
|
if start < i {
|
||||||
|
state.WriteString(value[start:i])
|
||||||
|
}
|
||||||
|
state.WriteString(`\u202`)
|
||||||
|
state.WriteByte(G.hex[c&0xF])
|
||||||
|
i += size
|
||||||
|
start = i
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
i += size
|
||||||
|
}
|
||||||
|
if start < len(value) {
|
||||||
|
state.WriteString(value[start:])
|
||||||
|
}
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func packBinary (state *packs.State, value []byte , flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
|
||||||
|
if value == nil {
|
||||||
|
_,_ = state.Write(G.nullValue)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if len(value) == 0 {
|
||||||
|
state.Write2Byte('"','"')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
state.WriteByte('"')
|
||||||
|
|
||||||
|
if flags.Bin64() {
|
||||||
|
packBinary64(state, value, 0)
|
||||||
|
} else if flags.Bin32() {
|
||||||
|
packBinary32(state, value, 0)
|
||||||
|
} else {
|
||||||
|
state.SetError(packs.G.ErrUnsupportedType)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
if state.Error == nil {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func packBinary64 (state *packs.State, value []byte , _ packs.Flags) {
|
||||||
|
ln := base64.StdEncoding.EncodedLen(len(value))
|
||||||
|
if ln <= len(state.Temp) {
|
||||||
|
dst := state.Temp[:ln]
|
||||||
|
base64.StdEncoding.Encode(dst, value)
|
||||||
|
_,_= state.Write(dst)
|
||||||
|
} else if ln <= 1024 {
|
||||||
|
dst := make([]byte, ln)
|
||||||
|
base64.StdEncoding.Encode(dst, value)
|
||||||
|
_,_ = state.Write(dst)
|
||||||
|
} else {
|
||||||
|
ec := base64.NewEncoder(base64.StdEncoding, state)
|
||||||
|
_,_ = ec.Write(value)
|
||||||
|
state.SetError(ec.Close())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func packBinary32 (state *packs.State, value []byte , _ packs.Flags) {
|
||||||
|
ln := base32.StdEncoding.EncodedLen(len(value))
|
||||||
|
if ln <= len(state.Temp) {
|
||||||
|
dst := state.Temp[:ln]
|
||||||
|
base32.StdEncoding.Encode(dst, value)
|
||||||
|
_,_= state.Write(dst)
|
||||||
|
} else if ln <= 1024 {
|
||||||
|
dst := make([]byte, ln)
|
||||||
|
base32.StdEncoding.Encode(dst, value)
|
||||||
|
_,_ = state.Write(dst)
|
||||||
|
} else {
|
||||||
|
ec := base32.NewEncoder(base32.StdEncoding, state)
|
||||||
|
_,_ = ec.Write(value)
|
||||||
|
state.SetError(ec.Close())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
func packBool (state *packs.State, value bool , flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
if flags.Quote() {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
if value {
|
||||||
|
state.W(G.trueValue)
|
||||||
|
} else {
|
||||||
|
state.W(G.falseValue)
|
||||||
|
}
|
||||||
|
if flags.Quote() {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func packInt (state *packs.State, value int64 , flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
|
||||||
|
if flags.Quote() {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
if value == 0 {
|
||||||
|
state.WriteByte('0')
|
||||||
|
} else {
|
||||||
|
state.WriteIntStr(value, 10)
|
||||||
|
}
|
||||||
|
if flags.Quote() {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func packUInt (state *packs.State, value uint64 , flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
q :=flags.Quote()
|
||||||
|
if q {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
if value == 0 {
|
||||||
|
state.WriteByte('0')
|
||||||
|
} else {
|
||||||
|
state.WriteUIntStr(value, 10)
|
||||||
|
}
|
||||||
|
if q {
|
||||||
|
state.WriteByte('"')
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func packFloat (state *packs.State, value float64, flags packs.Flags) {
|
||||||
|
packFloatString(state, value, flags, 64)
|
||||||
|
}
|
||||||
|
|
||||||
|
func packFloatString (state *packs.State, f float64, flags packs.Flags, bits int) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
|
||||||
|
if math.IsInf(f, 0) || math.IsNaN(f) {
|
||||||
|
state.SetError(packs.G.ErrInvalidValue)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
abs := math.Abs(f)
|
||||||
|
fmt := byte('f')
|
||||||
|
|
||||||
|
if abs != 0 {
|
||||||
|
if bits == 64 && (abs < 1e-6 || abs >= 1e21) || bits == 32 && (float32(abs) < 1e-6 || float32(abs) >= 1e21) {
|
||||||
|
fmt = 'e'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
bf := state.Temp[:0]
|
||||||
|
bf = strconv.AppendFloat(bf, f, fmt, -1, int(bits))
|
||||||
|
if fmt == 'e' {
|
||||||
|
// clean up e-09 to e-9
|
||||||
|
n := len(bf)
|
||||||
|
if n >= 4 && bf[n-4] == 'e' && bf[n-3] == '-' && bf[n-2] == '0' {
|
||||||
|
bf[n-2] = bf[n-1]
|
||||||
|
bf = bf[:n-1]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if flags.Quote() {
|
||||||
|
state.WriteByte('"')
|
||||||
|
state.W(bf)
|
||||||
|
state.WriteByte('"')
|
||||||
|
return
|
||||||
|
}
|
||||||
|
state.W(bf)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
func PackDate (state *packs.State, value time.Time, flags packs.Flags) {
|
||||||
|
if state.Error != nil {
|
||||||
|
panic(packs.G.ErrInvalidState.WithCause(state.Error))
|
||||||
|
}
|
||||||
|
state.WriteByte('"')
|
||||||
|
bf := state.Temp[:0]
|
||||||
|
bf = value.AppendFormat(bf,flags.DateFormat())
|
||||||
|
state.W(bf)
|
||||||
|
state.WriteByte('"')
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
Loading…
Reference in new issue