pax_global_header00006660000000000000000000000064126432610640014516gustar00rootroot0000000000000052 comment=de1477059f3b5004ea4c6730b54fd418c8a68700 golang-gopkg-vmihailenco-msgpack.v2-2.4.7/000077500000000000000000000000001264326106400203515ustar00rootroot00000000000000golang-gopkg-vmihailenco-msgpack.v2-2.4.7/.travis.yml000066400000000000000000000005201264326106400224570ustar00rootroot00000000000000sudo: false language: go go: - 1.3 - 1.4 - 1.5 - tip matrix: allow_failures: - go: tip install: - go get gopkg.in/check.v1 - go get github.com/ugorji/go-msgpack - go get github.com/ugorji/go/codec - mkdir -p $HOME/gopath/src/gopkg.in/vmihailenco - ln -s `pwd` $HOME/gopath/src/gopkg.in/vmihailenco/msgpack.v2 golang-gopkg-vmihailenco-msgpack.v2-2.4.7/LICENSE000066400000000000000000000027231264326106400213620ustar00rootroot00000000000000Copyright (c) 2013 The msgpack for Go Authors. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. * Neither the name of Google Inc. nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. golang-gopkg-vmihailenco-msgpack.v2-2.4.7/Makefile000066400000000000000000000002331264326106400220070ustar00rootroot00000000000000all: go test gopkg.in/vmihailenco/msgpack.v2 -cpu=1 go test gopkg.in/vmihailenco/msgpack.v2 -cpu=2 go test gopkg.in/vmihailenco/msgpack.v2 -short -race golang-gopkg-vmihailenco-msgpack.v2-2.4.7/README.md000066400000000000000000000033751264326106400216400ustar00rootroot00000000000000# MessagePack encoding for Golang [![Build Status](https://travis-ci.org/vmihailenco/msgpack.svg)](https://travis-ci.org/vmihailenco/msgpack) Supports: - Primitives, arrays, maps, structs, time.Time and interface{}. - Appengine *datastore.Key and datastore.Cursor. - [CustomEncoder](http://godoc.org/gopkg.in/vmihailenco/msgpack.v2#example-CustomEncoder)/CustomDecoder interfaces for custom encoding. - [Extensions](http://godoc.org/gopkg.in/vmihailenco/msgpack.v2#example-RegisterExt) to encode type information. - Fields renaming, e.g. `msgpack:"my_field_name"`. - Structs inlining, e.g. `msgpack:",inline"`. - Omitempty flag, e.g. `msgpack:",omitempty"`. API docs: http://godoc.org/gopkg.in/vmihailenco/msgpack.v2. Examples: http://godoc.org/gopkg.in/vmihailenco/msgpack.v2#pkg-examples. ## Installation Install: go get gopkg.in/vmihailenco/msgpack.v2 ## Quickstart ```go func ExampleMarshal() { b, err := msgpack.Marshal(true) if err != nil { panic(err) } fmt.Printf("%#v\n", b) // Output: var out bool err = msgpack.Unmarshal([]byte{0xc3}, &out) if err != nil { panic(err) } fmt.Println(out) // Output: []byte{0xc3} // true } ``` ## Benchmark ``` BenchmarkStruct-4 200000 11515 ns/op 3296 B/op 27 allocs/op BenchmarkStructUgorjiGoMsgpack-4 100000 12234 ns/op 3840 B/op 70 allocs/op BenchmarkStructUgorjiGoCodec-4 100000 15251 ns/op 7474 B/op 29 allocs/op BenchmarkStructJSON-4 30000 50851 ns/op 8088 B/op 29 allocs/op BenchmarkStructGOB-4 20000 64993 ns/op 15609 B/op 299 allocs/op ``` ## Howto Please go through [examples](http://godoc.org/gopkg.in/vmihailenco/msgpack.v2#pkg-examples) to get an idea how to use this package. golang-gopkg-vmihailenco-msgpack.v2-2.4.7/appengine.go000066400000000000000000000025761264326106400226600ustar00rootroot00000000000000// +build appengine package msgpack import ( "reflect" ds "google.golang.org/appengine/datastore" ) var ( keyPtrType = reflect.TypeOf((*ds.Key)(nil)) cursorType = reflect.TypeOf((*ds.Cursor)(nil)).Elem() ) func init() { Register(keyPtrType, encodeDatastoreKeyValue, decodeDatastoreKeyValue) Register(cursorType, encodeDatastoreCursorValue, decodeDatastoreCursorValue) } func EncodeDatastoreKey(e *Encoder, key *ds.Key) error { if key == nil { return e.EncodeNil() } return e.EncodeString(key.Encode()) } func encodeDatastoreKeyValue(e *Encoder, v reflect.Value) error { key := v.Interface().(*ds.Key) return EncodeDatastoreKey(e, key) } func DecodeDatastoreKey(d *Decoder) (*ds.Key, error) { v, err := d.DecodeString() if err != nil { return nil, err } if v == "" { return nil, nil } return ds.DecodeKey(v) } func decodeDatastoreKeyValue(d *Decoder, v reflect.Value) error { key, err := DecodeDatastoreKey(d) if err != nil { return err } v.Set(reflect.ValueOf(key)) return nil } func encodeDatastoreCursorValue(e *Encoder, v reflect.Value) error { cursor := v.Interface().(ds.Cursor) return e.Encode(cursor.String()) } func decodeDatastoreCursorValue(d *Decoder, v reflect.Value) error { s, err := d.DecodeString() if err != nil { return err } cursor, err := ds.DecodeCursor(s) if err != nil { return err } v.Set(reflect.ValueOf(cursor)) return nil } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/codes/000077500000000000000000000000001264326106400214465ustar00rootroot00000000000000golang-gopkg-vmihailenco-msgpack.v2-2.4.7/codes/codes.go000066400000000000000000000021461264326106400230750ustar00rootroot00000000000000package codes const ( PosFixedNumHigh = 0x7f NegFixedNumLow = 0xe0 Nil = 0xc0 False = 0xc2 True = 0xc3 Float = 0xca Double = 0xcb Uint8 = 0xcc Uint16 = 0xcd Uint32 = 0xce Uint64 = 0xcf Int8 = 0xd0 Int16 = 0xd1 Int32 = 0xd2 Int64 = 0xd3 FixedStrLow = 0xa0 FixedStrHigh = 0xbf FixedStrMask = 0x1f Str8 = 0xd9 Str16 = 0xda Str32 = 0xdb Bin8 = 0xc4 Bin16 = 0xc5 Bin32 = 0xc6 FixedArrayLow = 0x90 FixedArrayHigh = 0x9f FixedArrayMask = 0xf Array16 = 0xdc Array32 = 0xdd FixedMapLow = 0x80 FixedMapHigh = 0x8f FixedMapMask = 0xf Map16 = 0xde Map32 = 0xdf FixExt1 = 0xd4 FixExt2 = 0xd5 FixExt4 = 0xd6 FixExt8 = 0xd7 FixExt16 = 0xd8 Ext8 = 0xc7 Ext16 = 0xc8 Ext32 = 0xc9 ) func IsFixedNum(c byte) bool { return c <= PosFixedNumHigh || c >= NegFixedNumLow } func IsFixedMap(c byte) bool { return c >= FixedMapLow && c <= FixedMapHigh } func IsFixedArray(c byte) bool { return c >= FixedArrayLow && c <= FixedArrayHigh } func IsFixedString(c byte) bool { return c >= FixedStrLow && c <= FixedStrHigh } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/decode.go000066400000000000000000000153041264326106400221260ustar00rootroot00000000000000package msgpack import ( "bufio" "bytes" "errors" "fmt" "io" "reflect" "time" "gopkg.in/vmihailenco/msgpack.v2/codes" ) type bufReader interface { Read([]byte) (int, error) ReadByte() (byte, error) UnreadByte() error } func Unmarshal(b []byte, v ...interface{}) error { if len(v) == 1 && v[0] != nil { unmarshaler, ok := v[0].(Unmarshaler) if ok { return unmarshaler.UnmarshalMsgpack(b) } } return NewDecoder(bytes.NewReader(b)).Decode(v...) } type Decoder struct { // TODO: add map len arg DecodeMapFunc func(*Decoder) (interface{}, error) r bufReader buf []byte } func NewDecoder(r io.Reader) *Decoder { br, ok := r.(bufReader) if !ok { br = bufio.NewReader(r) } return &Decoder{ DecodeMapFunc: decodeMap, r: br, buf: make([]byte, 64), } } func (d *Decoder) Decode(v ...interface{}) error { for _, vv := range v { if err := d.decode(vv); err != nil { return err } } return nil } func (d *Decoder) decode(dst interface{}) error { var err error switch v := dst.(type) { case *string: if v != nil { *v, err = d.DecodeString() return err } case *[]byte: if v != nil { *v, err = d.DecodeBytes() return err } case *int: if v != nil { *v, err = d.DecodeInt() return err } case *int8: if v != nil { *v, err = d.DecodeInt8() return err } case *int16: if v != nil { *v, err = d.DecodeInt16() return err } case *int32: if v != nil { *v, err = d.DecodeInt32() return err } case *int64: if v != nil { *v, err = d.DecodeInt64() return err } case *uint: if v != nil { *v, err = d.DecodeUint() return err } case *uint8: if v != nil { *v, err = d.DecodeUint8() return err } case *uint16: if v != nil { *v, err = d.DecodeUint16() return err } case *uint32: if v != nil { *v, err = d.DecodeUint32() return err } case *uint64: if v != nil { *v, err = d.DecodeUint64() return err } case *bool: if v != nil { *v, err = d.DecodeBool() return err } case *float32: if v != nil { *v, err = d.DecodeFloat32() return err } case *float64: if v != nil { *v, err = d.DecodeFloat64() return err } case *[]string: return d.decodeIntoStrings(v) case *map[string]string: return d.decodeIntoMapStringString(v) case *time.Duration: if v != nil { vv, err := d.DecodeInt64() *v = time.Duration(vv) return err } case *time.Time: if v != nil { *v, err = d.DecodeTime() return err } } v := reflect.ValueOf(dst) if !v.IsValid() { return errors.New("msgpack: Decode(nil)") } if v.Kind() != reflect.Ptr { return fmt.Errorf("msgpack: Decode(nonsettable %T)", dst) } return d.DecodeValue(v) } func (d *Decoder) DecodeValue(v reflect.Value) error { decode := getDecoder(v.Type()) return decode(d, v) } func (d *Decoder) DecodeNil() error { c, err := d.r.ReadByte() if err != nil { return err } if c != codes.Nil { return fmt.Errorf("msgpack: invalid code %x decoding nil", c) } return nil } func (d *Decoder) DecodeBool() (bool, error) { c, err := d.r.ReadByte() if err != nil { return false, err } return d.bool(c) } func (d *Decoder) bool(c byte) (bool, error) { if c == codes.False { return false, nil } if c == codes.True { return true, nil } return false, fmt.Errorf("msgpack: invalid code %x decoding bool", c) } func (d *Decoder) boolValue(value reflect.Value) error { v, err := d.DecodeBool() if err != nil { return err } value.SetBool(v) return nil } func (d *Decoder) interfaceValue(v reflect.Value) error { iface, err := d.DecodeInterface() if err != nil { return err } if iface != nil { v.Set(reflect.ValueOf(iface)) } return nil } // Decodes value into interface. Possible value types are: // - nil, // - int64, // - uint64, // - bool, // - float32 and float64, // - string, // - slices of any of the above, // - maps of any of the above. func (d *Decoder) DecodeInterface() (interface{}, error) { c, err := d.r.ReadByte() if err != nil { return nil, err } if codes.IsFixedNum(c) { if c >= 0 { return d.uint(c) } return d.int(c) } if codes.IsFixedMap(c) { d.r.UnreadByte() return d.DecodeMap() } if codes.IsFixedArray(c) { d.r.UnreadByte() return d.DecodeSlice() } if codes.IsFixedString(c) { return d.string(c) } switch c { case codes.Nil: return nil, nil case codes.False, codes.True: return d.bool(c) case codes.Float: return d.float32(c) case codes.Double: return d.float64(c) case codes.Uint8, codes.Uint16, codes.Uint32, codes.Uint64: return d.uint(c) case codes.Int8, codes.Int16, codes.Int32, codes.Int64: return d.int(c) case codes.Bin8, codes.Bin16, codes.Bin32: return d.bytes(c) case codes.Str8, codes.Str16, codes.Str32: return d.string(c) case codes.Array16, codes.Array32: d.r.UnreadByte() return d.DecodeSlice() case codes.Map16, codes.Map32: d.r.UnreadByte() return d.DecodeMap() case codes.FixExt1, codes.FixExt2, codes.FixExt4, codes.FixExt8, codes.FixExt16, codes.Ext8, codes.Ext16, codes.Ext32: return d.ext(c) } return 0, fmt.Errorf("msgpack: unknown code %x decoding interface{}", c) } // Skip skips next value. func (d *Decoder) Skip() error { c, err := d.r.ReadByte() if err != nil { return err } if codes.IsFixedNum(c) { return nil } else if codes.IsFixedMap(c) { return d.skipMap(c) } else if codes.IsFixedArray(c) { return d.skipSlice(c) } else if codes.IsFixedString(c) { return d.skipBytes(c) } switch c { case codes.Nil, codes.False, codes.True: return nil case codes.Uint8, codes.Int8: return d.skipN(1) case codes.Uint16, codes.Int16: return d.skipN(2) case codes.Uint32, codes.Int32, codes.Float: return d.skipN(4) case codes.Uint64, codes.Int64, codes.Double: return d.skipN(8) case codes.Bin8, codes.Bin16, codes.Bin32: return d.skipBytes(c) case codes.Str8, codes.Str16, codes.Str32: return d.skipBytes(c) case codes.Array16, codes.Array32: return d.skipSlice(c) case codes.Map16, codes.Map32: return d.skipMap(c) case codes.FixExt1, codes.FixExt2, codes.FixExt4, codes.FixExt8, codes.FixExt16, codes.Ext8, codes.Ext16, codes.Ext32: return d.skipExt(c) } return fmt.Errorf("msgpack: unknown code %x", c) } // peekCode returns the next Msgpack code. See // https://github.com/msgpack/msgpack/blob/master/spec.md#formats for details. func (d *Decoder) peekCode() (code byte, err error) { code, err = d.r.ReadByte() if err != nil { return 0, err } return code, d.r.UnreadByte() } func (d *Decoder) gotNilCode() bool { code, err := d.peekCode() return err == nil && code == codes.Nil } func (d *Decoder) readN(n int) ([]byte, error) { var b []byte if n <= cap(d.buf) { b = d.buf[:n] } else { b = make([]byte, n) } _, err := io.ReadFull(d.r, b) return b, err } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/decode_number.go000066400000000000000000000114001264326106400234670ustar00rootroot00000000000000package msgpack import ( "fmt" "math" "reflect" "gopkg.in/vmihailenco/msgpack.v2/codes" ) func (d *Decoder) skipN(n int) error { _, err := d.readN(n) return err } func (d *Decoder) uint8() (uint8, error) { c, err := d.r.ReadByte() if err != nil { return 0, err } return uint8(c), nil } func (d *Decoder) uint16() (uint16, error) { b, err := d.readN(2) if err != nil { return 0, err } return (uint16(b[0]) << 8) | uint16(b[1]), nil } func (d *Decoder) uint32() (uint32, error) { b, err := d.readN(4) if err != nil { return 0, err } n := (uint32(b[0]) << 24) | (uint32(b[1]) << 16) | (uint32(b[2]) << 8) | uint32(b[3]) return n, nil } func (d *Decoder) uint64() (uint64, error) { b, err := d.readN(8) if err != nil { return 0, err } n := (uint64(b[0]) << 56) | (uint64(b[1]) << 48) | (uint64(b[2]) << 40) | (uint64(b[3]) << 32) | (uint64(b[4]) << 24) | (uint64(b[5]) << 16) | (uint64(b[6]) << 8) | uint64(b[7]) return n, nil } func (d *Decoder) DecodeUint64() (uint64, error) { c, err := d.r.ReadByte() if err != nil { return 0, err } return d.uint(c) } func (d *Decoder) uint(c byte) (uint64, error) { if codes.IsFixedNum(c) { return uint64(int8(c)), nil } switch c { case codes.Uint8: n, err := d.uint8() return uint64(n), err case codes.Int8: n, err := d.uint8() return uint64(int8(n)), err case codes.Uint16: n, err := d.uint16() return uint64(n), err case codes.Int16: n, err := d.uint16() return uint64(int16(n)), err case codes.Uint32: n, err := d.uint32() return uint64(n), err case codes.Int32: n, err := d.uint32() return uint64(int32(n)), err case codes.Uint64, codes.Int64: return d.uint64() } return 0, fmt.Errorf("msgpack: invalid code %x decoding uint64", c) } func (d *Decoder) uint64Value(value reflect.Value) error { v, err := d.DecodeUint64() if err != nil { return err } value.SetUint(v) return nil } func (d *Decoder) DecodeInt64() (int64, error) { c, err := d.r.ReadByte() if err != nil { return 0, err } return d.int(c) } func (d *Decoder) int(c byte) (int64, error) { if codes.IsFixedNum(c) { return int64(int8(c)), nil } switch c { case codes.Uint8: n, err := d.uint8() return int64(n), err case codes.Int8: n, err := d.uint8() return int64(int8(n)), err case codes.Uint16: n, err := d.uint16() return int64(n), err case codes.Int16: n, err := d.uint16() return int64(int16(n)), err case codes.Uint32: n, err := d.uint32() return int64(n), err case codes.Int32: n, err := d.uint32() return int64(int32(n)), err case codes.Uint64, codes.Int64: n, err := d.uint64() return int64(n), err } return 0, fmt.Errorf("msgpack: invalid code %x decoding int64", c) } func (d *Decoder) int64Value(v reflect.Value) error { n, err := d.DecodeInt64() if err != nil { return err } v.SetInt(n) return nil } func (d *Decoder) DecodeFloat32() (float32, error) { c, err := d.r.ReadByte() if err != nil { return 0, err } return d.float32(c) } func (d *Decoder) float32(c byte) (float32, error) { if c != codes.Float { return 0, fmt.Errorf("msgpack: invalid code %x decoding float32", c) } b, err := d.uint32() if err != nil { return 0, err } return math.Float32frombits(b), nil } func (d *Decoder) float32Value(value reflect.Value) error { v, err := d.DecodeFloat32() if err != nil { return err } value.SetFloat(float64(v)) return nil } func (d *Decoder) DecodeFloat64() (float64, error) { c, err := d.r.ReadByte() if err != nil { return 0, err } return d.float64(c) } func (d *Decoder) float64(c byte) (float64, error) { if c == codes.Float { n, err := d.float32(c) return float64(n), err } if c != codes.Double { return 0, fmt.Errorf("msgpack: invalid code %x decoding float64", c) } b, err := d.uint64() if err != nil { return 0, err } return math.Float64frombits(b), nil } func (d *Decoder) float64Value(value reflect.Value) error { v, err := d.DecodeFloat64() if err != nil { return err } value.SetFloat(v) return nil } func (d *Decoder) DecodeUint() (uint, error) { n, err := d.DecodeUint64() return uint(n), err } func (d *Decoder) DecodeUint8() (uint8, error) { n, err := d.DecodeUint64() return uint8(n), err } func (d *Decoder) DecodeUint16() (uint16, error) { n, err := d.DecodeUint64() return uint16(n), err } func (d *Decoder) DecodeUint32() (uint32, error) { n, err := d.DecodeUint64() return uint32(n), err } func (d *Decoder) DecodeInt() (int, error) { n, err := d.DecodeInt64() return int(n), err } func (d *Decoder) DecodeInt8() (int8, error) { n, err := d.DecodeInt64() return int8(n), err } func (d *Decoder) DecodeInt16() (int16, error) { n, err := d.DecodeInt64() return int16(n), err } func (d *Decoder) DecodeInt32() (int32, error) { n, err := d.DecodeInt64() return int32(n), err } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/encode.go000066400000000000000000000050771264326106400221460ustar00rootroot00000000000000package msgpack import ( "bytes" "io" "reflect" "time" "gopkg.in/vmihailenco/msgpack.v2/codes" ) type writer interface { io.Writer WriteByte(byte) error WriteString(string) (int, error) } type byteWriter struct { io.Writer } func (w *byteWriter) WriteByte(b byte) error { n, err := w.Write([]byte{b}) if err != nil { return err } if n != 1 { return io.ErrShortWrite } return nil } func (w *byteWriter) WriteString(s string) (int, error) { return w.Write([]byte(s)) } func Marshal(v ...interface{}) ([]byte, error) { if len(v) == 1 { marshaler, ok := v[0].(Marshaler) if ok { return marshaler.MarshalMsgpack() } } buf := &bytes.Buffer{} err := NewEncoder(buf).Encode(v...) return buf.Bytes(), err } type Encoder struct { w writer buf []byte } func NewEncoder(w io.Writer) *Encoder { ww, ok := w.(writer) if !ok { ww = &byteWriter{Writer: w} } return &Encoder{ w: ww, buf: make([]byte, 9), } } func (e *Encoder) Encode(v ...interface{}) error { for _, vv := range v { if err := e.encode(vv); err != nil { return err } } return nil } func (e *Encoder) encode(iv interface{}) error { if iv == nil { return e.EncodeNil() } switch v := iv.(type) { case string: return e.EncodeString(v) case []byte: return e.EncodeBytes(v) case int: return e.EncodeInt64(int64(v)) case int64: return e.EncodeInt64(v) case uint: return e.EncodeUint64(uint64(v)) case uint64: return e.EncodeUint64(v) case bool: return e.EncodeBool(v) case float32: return e.EncodeFloat32(v) case float64: return e.EncodeFloat64(v) case []string: return e.encodeStringSlice(v) case map[string]string: return e.encodeMapStringString(v) case time.Duration: return e.EncodeInt64(int64(v)) case time.Time: return e.EncodeTime(v) case Marshaler: b, err := v.MarshalMsgpack() if err != nil { return err } _, err = e.w.Write(b) return err } return e.EncodeValue(reflect.ValueOf(iv)) } func (e *Encoder) EncodeValue(v reflect.Value) error { encode := getEncoder(v.Type()) return encode(e, v) } func (e *Encoder) EncodeNil() error { return e.w.WriteByte(codes.Nil) } func (e *Encoder) EncodeBool(value bool) error { if value { return e.w.WriteByte(codes.True) } return e.w.WriteByte(codes.False) } func (e *Encoder) write(b []byte) error { n, err := e.w.Write(b) if err != nil { return err } if n < len(b) { return io.ErrShortWrite } return nil } func (e *Encoder) writeString(s string) error { n, err := e.w.WriteString(s) if err != nil { return err } if n < len(s) { return io.ErrShortWrite } return nil } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/encode_number.go000066400000000000000000000047271264326106400235170ustar00rootroot00000000000000package msgpack import ( "math" "gopkg.in/vmihailenco/msgpack.v2/codes" ) func (e *Encoder) EncodeUint(v uint) error { return e.EncodeUint64(uint64(v)) } func (e *Encoder) EncodeUint8(v uint8) error { return e.EncodeUint64(uint64(v)) } func (e *Encoder) EncodeUint16(v uint16) error { return e.EncodeUint64(uint64(v)) } func (e *Encoder) EncodeUint32(v uint32) error { return e.EncodeUint64(uint64(v)) } func (e *Encoder) EncodeUint64(v uint64) error { if v <= math.MaxInt8 { return e.w.WriteByte(byte(v)) } if v <= math.MaxUint8 { return e.write1(codes.Uint8, v) } if v <= math.MaxUint16 { return e.write2(codes.Uint16, v) } if v <= math.MaxUint32 { return e.write4(codes.Uint32, v) } return e.write8(codes.Uint64, v) } func (e *Encoder) EncodeInt(v int) error { return e.EncodeInt64(int64(v)) } func (e *Encoder) EncodeInt8(v int8) error { return e.EncodeInt64(int64(v)) } func (e *Encoder) EncodeInt16(v int16) error { return e.EncodeInt64(int64(v)) } func (e *Encoder) EncodeInt32(v int32) error { return e.EncodeInt64(int64(v)) } func (e *Encoder) EncodeInt64(v int64) error { if v >= 0 { return e.EncodeUint64(uint64(v)) } if v >= -32 { return e.w.WriteByte(byte(v)) } if v >= math.MinInt8 { return e.write1(codes.Int8, uint64(v)) } if v >= math.MinInt16 { return e.write2(codes.Int16, uint64(v)) } if v >= math.MinInt32 { return e.write4(codes.Int32, uint64(v)) } return e.write8(codes.Int64, uint64(v)) } func (e *Encoder) EncodeFloat32(n float32) error { return e.write4(codes.Float, uint64(math.Float32bits(n))) } func (e *Encoder) EncodeFloat64(n float64) error { return e.write8(codes.Double, math.Float64bits(n)) } func (e *Encoder) write1(code byte, n uint64) error { e.buf = e.buf[:2] e.buf[0] = code e.buf[1] = byte(n) return e.write(e.buf) } func (e *Encoder) write2(code byte, n uint64) error { e.buf = e.buf[:3] e.buf[0] = code e.buf[1] = byte(n >> 8) e.buf[2] = byte(n) return e.write(e.buf) } func (e *Encoder) write4(code byte, n uint64) error { e.buf = e.buf[:5] e.buf[0] = code e.buf[1] = byte(n >> 24) e.buf[2] = byte(n >> 16) e.buf[3] = byte(n >> 8) e.buf[4] = byte(n) return e.write(e.buf) } func (e *Encoder) write8(code byte, n uint64) error { e.buf = e.buf[:9] e.buf[0] = code e.buf[1] = byte(n >> 56) e.buf[2] = byte(n >> 48) e.buf[3] = byte(n >> 40) e.buf[4] = byte(n >> 32) e.buf[5] = byte(n >> 24) e.buf[6] = byte(n >> 16) e.buf[7] = byte(n >> 8) e.buf[8] = byte(n) return e.write(e.buf) } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/example_CustomEncoder_test.go000066400000000000000000000013041264326106400262220ustar00rootroot00000000000000package msgpack_test import ( "fmt" "gopkg.in/vmihailenco/msgpack.v2" ) type customStruct struct { S string N int } var ( _ msgpack.CustomEncoder = &customStruct{} _ msgpack.CustomDecoder = &customStruct{} ) func (s *customStruct) EncodeMsgpack(enc *msgpack.Encoder) error { return enc.Encode(s.S, s.N) } func (s *customStruct) DecodeMsgpack(dec *msgpack.Decoder) error { return dec.Decode(&s.S, &s.N) } func ExampleCustomEncoder() { b, err := msgpack.Marshal(&customStruct{S: "hello", N: 42}) if err != nil { panic(err) } var v customStruct err = msgpack.Unmarshal(b, &v) if err != nil { panic(err) } fmt.Printf("%#v", v) // Output: msgpack_test.customStruct{S:"hello", N:42} } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/example_test.go000066400000000000000000000035171264326106400234000ustar00rootroot00000000000000package msgpack_test import ( "bytes" "fmt" "gopkg.in/vmihailenco/msgpack.v2" ) func ExampleMarshal() { b, err := msgpack.Marshal(true) if err != nil { panic(err) } fmt.Printf("%#v\n", b) // Output: var out bool err = msgpack.Unmarshal([]byte{0xc3}, &out) if err != nil { panic(err) } fmt.Println(out) // Output: []byte{0xc3} // true } type myStruct struct { S string } func ExampleRegisterExt() { msgpack.RegisterExt(1, myStruct{}) b, err := msgpack.Marshal(&myStruct{S: "string"}) if err != nil { panic(err) } var v interface{} err = msgpack.Unmarshal(b, &v) if err != nil { panic(err) } fmt.Printf("%#v", v) // Output: msgpack_test.myStruct{S:"string"} } func Example_mapStringInterface() { in := map[string]interface{}{"foo": 1, "hello": "world"} b, err := msgpack.Marshal(in) if err != nil { panic(err) } var out map[string]interface{} err = msgpack.Unmarshal(b, &out) if err != nil { panic(err) } fmt.Println("foo =", out["foo"]) fmt.Println("hello =", out["hello"]) // Output: // foo = 1 // hello = world } func Example_recursiveMapStringInterface() { buf := &bytes.Buffer{} enc := msgpack.NewEncoder(buf) in := map[string]interface{}{"foo": map[string]interface{}{"hello": "world"}} _ = enc.Encode(in) dec := msgpack.NewDecoder(buf) dec.DecodeMapFunc = func(d *msgpack.Decoder) (interface{}, error) { n, err := d.DecodeMapLen() if err != nil { return nil, err } m := make(map[string]interface{}, n) for i := 0; i < n; i++ { mk, err := d.DecodeString() if err != nil { return nil, err } mv, err := d.DecodeInterface() if err != nil { return nil, err } m[mk] = mv } return m, nil } out, err := dec.DecodeInterface() fmt.Printf("%v %#v\n", err, out) // Output: map[string]interface {}{"foo":map[string]interface {}{"hello":"world"}} } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/ext.go000066400000000000000000000054321264326106400215040ustar00rootroot00000000000000package msgpack import ( "bytes" "fmt" "reflect" "sync" "gopkg.in/vmihailenco/msgpack.v2/codes" ) var ( extTypes [128]reflect.Type ) var bufferPool = &sync.Pool{ New: func() interface{} { return &bytes.Buffer{} }, } func RegisterExt(id int8, value interface{}) { if extTypes[id] != nil { panic(fmt.Errorf("ext with id %d is already registered", id)) } extTypes[id] = reflect.TypeOf(value) } func extTypeId(typ reflect.Type) int8 { for id, t := range extTypes { if t == typ { return int8(id) } } return -1 } func makeExtEncoder(id int8, enc encoderFunc) encoderFunc { return func(e *Encoder, v reflect.Value) error { buf := bufferPool.Get().(*bytes.Buffer) defer bufferPool.Put(buf) buf.Reset() oldw := e.w e.w = buf err := enc(e, v) e.w = oldw if err != nil { return err } if err := e.encodeExtLen(buf.Len()); err != nil { return err } if err := e.w.WriteByte(byte(id)); err != nil { return err } return e.write(buf.Bytes()) } } func (e *Encoder) encodeExtLen(l int) error { if l == 1 { return e.w.WriteByte(codes.FixExt1) } if l == 2 { return e.w.WriteByte(codes.FixExt2) } if l == 4 { return e.w.WriteByte(codes.FixExt4) } if l == 8 { return e.w.WriteByte(codes.FixExt8) } if l == 16 { return e.w.WriteByte(codes.FixExt16) } if l < 256 { return e.write1(codes.Ext8, uint64(l)) } if l < 65536 { return e.write2(codes.Ext16, uint64(l)) } return e.write4(codes.Ext32, uint64(l)) } func (d *Decoder) decodeExtLen() (int, error) { c, err := d.r.ReadByte() if err != nil { return 0, err } return d.extLen(c) } func (d *Decoder) extLen(c byte) (int, error) { switch c { case codes.FixExt1: return 1, nil case codes.FixExt2: return 2, nil case codes.FixExt4: return 4, nil case codes.FixExt8: return 8, nil case codes.FixExt16: return 16, nil case codes.Ext8: n, err := d.uint8() return int(n), err case codes.Ext16: n, err := d.uint16() return int(n), err case codes.Ext32: n, err := d.uint32() return int(n), err default: return 0, fmt.Errorf("msgpack: invalid code %x decoding ext length", c) } } func (d *Decoder) decodeExt() (interface{}, error) { c, err := d.r.ReadByte() if err != nil { return 0, err } return d.ext(c) } func (d *Decoder) ext(c byte) (interface{}, error) { // TODO: use decoded length. _, err := d.extLen(c) if err != nil { return nil, err } extId, err := d.r.ReadByte() if err != nil { return nil, err } typ := extTypes[extId] if typ == nil { return nil, fmt.Errorf("msgpack: unregistered ext id %d", extId) } v := reflect.New(typ).Elem() if err := d.DecodeValue(v); err != nil { return nil, err } return v.Interface(), nil } func (d *Decoder) skipExt(c byte) error { n, err := d.extLen(c) if err != nil { return err } return d.skipN(n) } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/ext_test.go000066400000000000000000000024341264326106400225420ustar00rootroot00000000000000package msgpack_test import ( "testing" "gopkg.in/vmihailenco/msgpack.v2" "gopkg.in/vmihailenco/msgpack.v2/codes" ) func init() { msgpack.RegisterExt(127, extTest{}) } func TestRegisterExtPanic(t *testing.T) { defer func() { r := recover() if r == nil { t.Fatalf("panic expected") } got := r.(error).Error() wanted := "ext with id 127 is already registered" if got != wanted { t.Fatalf("got %q, wanted %q", got, wanted) } }() msgpack.RegisterExt(127, extTest{}) } type extTest struct { S string } type extTest2 struct { S string } func TestExt(t *testing.T) { for _, v := range []interface{}{extTest{"hello"}, &extTest{"hello"}} { b, err := msgpack.Marshal(v) if err != nil { t.Fatal(err) } var dst interface{} err = msgpack.Unmarshal(b, &dst) if err != nil { t.Fatal(err) } v, ok := dst.(extTest) if !ok { t.Fatalf("got %#v, wanted extTest", dst) } if v.S != "hello" { t.Fatalf("got %q, wanted hello", v.S) } } } func TestUnknownExt(t *testing.T) { b := []byte{codes.FixExt1, 1, 0} var dst interface{} err := msgpack.Unmarshal(b, &dst) if err == nil { t.Fatalf("got nil, wanted error") } got := err.Error() wanted := "msgpack: unregistered ext id 1" if got != wanted { t.Fatalf("got %q, wanted %q", got, wanted) } } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/map.go000066400000000000000000000101051264326106400214520ustar00rootroot00000000000000package msgpack import ( "fmt" "reflect" "gopkg.in/vmihailenco/msgpack.v2/codes" ) func (e *Encoder) encodeMapLen(l int) error { if l < 16 { return e.w.WriteByte(codes.FixedMapLow | byte(l)) } if l < 65536 { return e.write2(codes.Map16, uint64(l)) } return e.write4(codes.Map32, uint64(l)) } func (e *Encoder) encodeMapStringString(m map[string]string) error { if err := e.encodeMapLen(len(m)); err != nil { return err } for mk, mv := range m { if err := e.EncodeString(mk); err != nil { return err } if err := e.EncodeString(mv); err != nil { return err } } return nil } func (e *Encoder) encodeMap(value reflect.Value) error { if err := e.encodeMapLen(value.Len()); err != nil { return err } for _, key := range value.MapKeys() { if err := e.EncodeValue(key); err != nil { return err } if err := e.EncodeValue(value.MapIndex(key)); err != nil { return err } } return nil } func decodeMap(d *Decoder) (interface{}, error) { n, err := d.DecodeMapLen() if err != nil { return nil, err } if n == -1 { return nil, nil } m := make(map[interface{}]interface{}, n) for i := 0; i < n; i++ { mk, err := d.DecodeInterface() if err != nil { return nil, err } mv, err := d.DecodeInterface() if err != nil { return nil, err } m[mk] = mv } return m, nil } func (d *Decoder) DecodeMapLen() (int, error) { c, err := d.r.ReadByte() if err != nil { return 0, err } return d.mapLen(c) } func (d *Decoder) mapLen(c byte) (int, error) { if c == codes.Nil { return -1, nil } if c >= codes.FixedMapLow && c <= codes.FixedMapHigh { return int(c & codes.FixedMapMask), nil } if c == codes.Map16 { n, err := d.uint16() return int(n), err } if c == codes.Map32 { n, err := d.uint32() return int(n), err } return 0, fmt.Errorf("msgpack: invalid code %x decoding map length", c) } func (d *Decoder) decodeIntoMapStringString(mp *map[string]string) error { n, err := d.DecodeMapLen() if err != nil { return err } if n == -1 { return nil } // TODO(vmihailenco): simpler way? m := *mp if m == nil { *mp = make(map[string]string, n) m = *mp } for i := 0; i < n; i++ { mk, err := d.DecodeString() if err != nil { return err } mv, err := d.DecodeString() if err != nil { return err } m[mk] = mv } return nil } func (d *Decoder) DecodeMap() (interface{}, error) { return d.DecodeMapFunc(d) } func (d *Decoder) skipMap(c byte) error { n, err := d.mapLen(c) if err != nil { return err } for i := 0; i < n; i++ { if err := d.Skip(); err != nil { return err } if err := d.Skip(); err != nil { return err } } return nil } func (d *Decoder) mapValue(v reflect.Value) error { n, err := d.DecodeMapLen() if err != nil { return err } if n == -1 { return nil } typ := v.Type() if v.IsNil() { v.Set(reflect.MakeMap(typ)) } keyType := typ.Key() valueType := typ.Elem() for i := 0; i < n; i++ { mk := reflect.New(keyType).Elem() if err := d.DecodeValue(mk); err != nil { return err } mv := reflect.New(valueType).Elem() if err := d.DecodeValue(mv); err != nil { return err } v.SetMapIndex(mk, mv) } return nil } func (e *Encoder) encodeStruct(strct reflect.Value) error { structFields := structs.Fields(strct.Type()) fields := make([]*field, 0, structFields.Len()) for _, f := range structFields.List { if !f.Omit(strct) { fields = append(fields, f) } } if err := e.encodeMapLen(len(fields)); err != nil { return err } for _, f := range fields { if err := e.EncodeString(f.name); err != nil { return err } if err := f.EncodeValue(e, strct); err != nil { return err } } return nil } func (d *Decoder) structValue(strct reflect.Value) error { n, err := d.DecodeMapLen() if err != nil { return err } fields := structs.Fields(strct.Type()) for i := 0; i < n; i++ { name, err := d.DecodeString() if err != nil { return err } if f := fields.Table[name]; f != nil { if err := f.DecodeValue(d, strct); err != nil { return err } } else { if err := d.Skip(); err != nil { return err } } } return nil } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/msgpack.go000066400000000000000000000006021264326106400223230ustar00rootroot00000000000000package msgpack // import "gopkg.in/vmihailenco/msgpack.v2" // Deprecated. Use CustomEncoder. type Marshaler interface { MarshalMsgpack() ([]byte, error) } // Deprecated. Use CustomDecoder. type Unmarshaler interface { UnmarshalMsgpack([]byte) error } type CustomEncoder interface { EncodeMsgpack(*Encoder) error } type CustomDecoder interface { DecodeMsgpack(*Decoder) error } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/msgpack_test.go000066400000000000000000000612501264326106400233700ustar00rootroot00000000000000package msgpack_test import ( "bufio" "bytes" "encoding/binary" "encoding/csv" "encoding/gob" "encoding/json" "math" "strings" "testing" "time" gomsgpack "github.com/ugorji/go-msgpack" gocodec "github.com/ugorji/go/codec" . "gopkg.in/check.v1" "gopkg.in/vmihailenco/msgpack.v2" "gopkg.in/vmihailenco/msgpack.v2/codes" ) type nameStruct struct { Name string } func Test(t *testing.T) { TestingT(t) } type MsgpackTest struct { buf *bytes.Buffer enc *msgpack.Encoder dec *msgpack.Decoder } var _ = Suite(&MsgpackTest{}) func (t *MsgpackTest) SetUpTest(c *C) { t.buf = &bytes.Buffer{} t.enc = msgpack.NewEncoder(t.buf) t.dec = msgpack.NewDecoder(bufio.NewReader(t.buf)) } func (t *MsgpackTest) TestUint64(c *C) { table := []struct { v uint64 b []byte }{ {0, []byte{0x00}}, {1, []byte{0x01}}, {math.MaxInt8 - 1, []byte{0x7e}}, {math.MaxInt8, []byte{0x7f}}, {math.MaxInt8 + 1, []byte{0xcc, 0x80}}, {math.MaxUint8 - 1, []byte{0xcc, 0xfe}}, {math.MaxUint8, []byte{0xcc, 0xff}}, {math.MaxUint8 + 1, []byte{0xcd, 0x1, 0x0}}, {math.MaxUint16 - 1, []byte{0xcd, 0xff, 0xfe}}, {math.MaxUint16, []byte{0xcd, 0xff, 0xff}}, {math.MaxUint16 + 1, []byte{0xce, 0x0, 0x1, 0x0, 0x0}}, {math.MaxUint32 - 1, []byte{0xce, 0xff, 0xff, 0xff, 0xfe}}, {math.MaxUint32, []byte{0xce, 0xff, 0xff, 0xff, 0xff}}, {math.MaxUint32 + 1, []byte{0xcf, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x0}}, {math.MaxInt64 - 1, []byte{0xcf, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe}}, {math.MaxInt64, []byte{0xcf, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff}}, } for _, r := range table { var int64v int64 c.Assert(t.enc.Encode(r.v), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, r.b, Commentf("n=%d", r.v)) c.Assert(t.dec.Decode(&int64v), IsNil, Commentf("n=%d", r.v)) c.Assert(int64v, Equals, int64(r.v), Commentf("n=%d", r.v)) var uint64v uint64 c.Assert(t.enc.Encode(r.v), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, r.b, Commentf("n=%d", r.v)) c.Assert(t.dec.Decode(&uint64v), IsNil, Commentf("n=%d", r.v)) c.Assert(uint64v, Equals, uint64(r.v), Commentf("n=%d", r.v)) c.Assert(t.enc.Encode(r.v), IsNil) iface, err := t.dec.DecodeInterface() c.Assert(err, IsNil) switch iface.(type) { case int64: c.Assert(iface, Equals, int64(r.v)) case uint64: c.Assert(iface, Equals, r.v) default: panic("not reached") } } } func (t *MsgpackTest) TestInt64(c *C) { table := []struct { v int64 b []byte }{ {math.MinInt64, []byte{0xd3, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}}, {math.MinInt32 - 1, []byte{0xd3, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xff, 0xff, 0xff}}, {math.MinInt32, []byte{0xd2, 0x80, 0x00, 0x00, 0x00}}, {math.MinInt32 + 1, []byte{0xd2, 0x80, 0x00, 0x00, 0x01}}, {math.MinInt16 - 1, []byte{0xd2, 0xff, 0xff, 0x7f, 0xff}}, {math.MinInt16, []byte{0xd1, 0x80, 0x00}}, {math.MinInt16 + 1, []byte{0xd1, 0x80, 0x01}}, {math.MinInt8 - 1, []byte{0xd1, 0xff, 0x7f}}, {math.MinInt8, []byte{0xd0, 0x80}}, {math.MinInt8 + 1, []byte{0xd0, 0x81}}, {-33, []byte{0xd0, 0xdf}}, {-32, []byte{0xe0}}, {-31, []byte{0xe1}}, {-1, []byte{0xff}}, {0, []byte{0x00}}, {1, []byte{0x01}}, {math.MaxInt8 - 1, []byte{0x7e}}, {math.MaxInt8, []byte{0x7f}}, {math.MaxInt8 + 1, []byte{0xcc, 0x80}}, {math.MaxUint8 - 1, []byte{0xcc, 0xfe}}, {math.MaxUint8, []byte{0xcc, 0xff}}, {math.MaxUint8 + 1, []byte{0xcd, 0x1, 0x0}}, {math.MaxUint16 - 1, []byte{0xcd, 0xff, 0xfe}}, {math.MaxUint16, []byte{0xcd, 0xff, 0xff}}, {math.MaxUint16 + 1, []byte{0xce, 0x0, 0x1, 0x0, 0x0}}, {math.MaxUint32 - 1, []byte{0xce, 0xff, 0xff, 0xff, 0xfe}}, {math.MaxUint32, []byte{0xce, 0xff, 0xff, 0xff, 0xff}}, {math.MaxUint32 + 1, []byte{0xcf, 0x0, 0x0, 0x0, 0x1, 0x0, 0x0, 0x0, 0x0}}, {math.MaxInt64 - 1, []byte{0xcf, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfe}}, {math.MaxInt64, []byte{0xcf, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff}}, } for _, r := range table { var int64v int64 c.Assert(t.enc.Encode(r.v), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, r.b, Commentf("n=%d", r.v)) c.Assert(t.dec.Decode(&int64v), IsNil, Commentf("n=%d", r.v)) c.Assert(int64v, Equals, int64(r.v), Commentf("n=%d", r.v)) var uint64v uint64 c.Assert(t.enc.Encode(r.v), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, r.b, Commentf("n=%d", r.v)) c.Assert(t.dec.Decode(&uint64v), IsNil, Commentf("n=%d", r.v)) c.Assert(uint64v, Equals, uint64(r.v), Commentf("n=%d", r.v)) c.Assert(t.enc.Encode(r.v), IsNil) iface, err := t.dec.DecodeInterface() c.Assert(err, IsNil) switch iface.(type) { case int64: c.Assert(iface, Equals, r.v) case uint64: c.Assert(iface, Equals, uint64(r.v)) default: panic("not reached") } } } func (t *MsgpackTest) TestFloat32(c *C) { table := []struct { v float32 b []byte }{ {0.1, []byte{codes.Float, 0x3d, 0xcc, 0xcc, 0xcd}}, {0.2, []byte{codes.Float, 0x3e, 0x4c, 0xcc, 0xcd}}, {-0.1, []byte{codes.Float, 0xbd, 0xcc, 0xcc, 0xcd}}, {-0.2, []byte{codes.Float, 0xbe, 0x4c, 0xcc, 0xcd}}, {float32(math.Inf(1)), []byte{codes.Float, 0x7f, 0x80, 0x00, 0x00}}, {float32(math.Inf(-1)), []byte{codes.Float, 0xff, 0x80, 0x00, 0x00}}, {math.MaxFloat32, []byte{codes.Float, 0x7f, 0x7f, 0xff, 0xff}}, {math.SmallestNonzeroFloat32, []byte{codes.Float, 0x0, 0x0, 0x0, 0x1}}, } for _, r := range table { c.Assert(t.enc.Encode(r.v), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, r.b, Commentf("err encoding %v", r.v)) var f32 float32 c.Assert(t.dec.Decode(&f32), IsNil) c.Assert(f32, Equals, r.v) // Pass pointer to skip fast-path and trigger reflect. c.Assert(t.enc.Encode(&r.v), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, r.b, Commentf("err encoding %v", r.v)) var f64 float64 c.Assert(t.dec.Decode(&f64), IsNil) c.Assert(float32(f64), Equals, r.v) c.Assert(t.enc.Encode(r.v), IsNil) iface, err := t.dec.DecodeInterface() c.Assert(err, IsNil) c.Assert(iface, Equals, r.v) } in := float32(math.NaN()) c.Assert(t.enc.Encode(in), IsNil) var out float32 c.Assert(t.dec.Decode(&out), IsNil) c.Assert(math.IsNaN(float64(out)), Equals, true) } func (t *MsgpackTest) TestFloat64(c *C) { table := []struct { v float64 b []byte }{ {.1, []byte{0xcb, 0x3f, 0xb9, 0x99, 0x99, 0x99, 0x99, 0x99, 0x9a}}, {.2, []byte{0xcb, 0x3f, 0xc9, 0x99, 0x99, 0x99, 0x99, 0x99, 0x9a}}, {-.1, []byte{0xcb, 0xbf, 0xb9, 0x99, 0x99, 0x99, 0x99, 0x99, 0x9a}}, {-.2, []byte{0xcb, 0xbf, 0xc9, 0x99, 0x99, 0x99, 0x99, 0x99, 0x9a}}, {math.Inf(1), []byte{0xcb, 0x7f, 0xf0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0}}, {math.Inf(-1), []byte{0xcb, 0xff, 0xf0, 0x00, 0x00, 0x0, 0x0, 0x0, 0x0}}, {math.MaxFloat64, []byte{0xcb, 0x7f, 0xef, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff}}, {math.SmallestNonzeroFloat64, []byte{0xcb, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x1}}, } for _, r := range table { c.Assert(t.enc.Encode(r.v), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, r.b, Commentf("err encoding %v", r.v)) var v float64 c.Assert(t.dec.Decode(&v), IsNil) c.Assert(v, Equals, r.v) c.Assert(t.enc.Encode(r.v), IsNil) iface, err := t.dec.DecodeInterface() c.Assert(err, IsNil) c.Assert(iface, Equals, r.v) } in := math.NaN() c.Assert(t.enc.Encode(in), IsNil) var out float64 c.Assert(t.dec.Decode(&out), IsNil) c.Assert(math.IsNaN(out), Equals, true) } func (t *MsgpackTest) TestBool(c *C) { table := []struct { v bool b []byte }{ {false, []byte{0xc2}}, {true, []byte{0xc3}}, } for _, r := range table { c.Assert(t.enc.Encode(r.v), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, r.b, Commentf("err encoding %v", r.v)) var v bool c.Assert(t.dec.Decode(&v), IsNil) c.Assert(v, Equals, r.v) c.Assert(t.enc.Encode(r.v), IsNil) iface, err := t.dec.DecodeInterface() c.Assert(err, IsNil) c.Assert(iface, Equals, r.v) } } func (t *MsgpackTest) TestDecodeNil(c *C) { c.Assert(t.dec.Decode(nil), NotNil) } func (t *MsgpackTest) TestTime(c *C) { in := time.Now() var out time.Time c.Assert(t.enc.Encode(in), IsNil) c.Assert(t.dec.Decode(&out), IsNil) c.Assert(out.Equal(in), Equals, true) var zero time.Time c.Assert(t.enc.Encode(zero), IsNil) c.Assert(t.dec.Decode(&out), IsNil) c.Assert(out.Equal(zero), Equals, true) c.Assert(out.IsZero(), Equals, true) } func (t *MsgpackTest) TestSliceOfInts(c *C) { for _, test := range []struct { v []int64 b []byte }{ {nil, []byte{0xc0}}, {[]int64{}, []byte{0x90}}, {[]int64{0}, []byte{0x91, 0x0}}, } { c.Assert(t.enc.Encode(test.v), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, test.b) var dst []int64 c.Assert(t.dec.Decode(&dst), IsNil) c.Assert(dst, DeepEquals, test.v) } } func (t *MsgpackTest) TestArrayOfInts(c *C) { src := [3]int{1, 2, 3} c.Assert(t.enc.Encode(src), IsNil) var dst [3]int c.Assert(t.dec.Decode(&dst), IsNil) c.Assert(dst, DeepEquals, src) } func (t *MsgpackTest) TestSliceOfStrings(c *C) { for _, i := range []struct { src []string b []byte }{ {nil, []byte{0xc0}}, {[]string{}, []byte{0x90}}, {[]string{"foo", "bar"}, []byte{0x92, 0xa3, 'f', 'o', 'o', 0xa3, 'b', 'a', 'r'}}, } { c.Assert(t.enc.Encode(i.src), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, i.b) var dst []string c.Assert(t.dec.Decode(&dst), IsNil) c.Assert(dst, DeepEquals, i.src) } } func (t *MsgpackTest) TestArrayOfStrings(c *C) { src := [2]string{"hello", "world"} c.Assert(t.enc.Encode(src), IsNil) var dst [2]string c.Assert(t.dec.Decode(&dst), IsNil) c.Assert(dst, DeepEquals, src) } func (t *MsgpackTest) TestBin(c *C) { lowBin8 := []byte(strings.Repeat("w", 32)) highBin8 := []byte(strings.Repeat("w", 255)) lowBin16 := []byte(strings.Repeat("w", 256)) highBin16 := []byte(strings.Repeat("w", 65535)) lowBin32 := []byte(strings.Repeat("w", 65536)) for _, i := range []struct { src []byte b []byte }{ { lowBin8, append([]byte{0xc4, byte(len(lowBin8))}, lowBin8...), }, { highBin8, append([]byte{0xc4, byte(len(highBin8))}, highBin8...), }, { lowBin16, append([]byte{0xc5, 1, 0}, lowBin16...), }, { highBin16, append([]byte{0xc5, 255, 255}, highBin16...), }, { lowBin32, append([]byte{0xc6, 0, 1, 0, 0}, lowBin32...), }, } { c.Assert(t.enc.Encode(i.src), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, i.b) var dst []byte c.Assert(t.dec.Decode(&dst), IsNil) c.Assert(dst, DeepEquals, i.src) c.Assert(t.enc.Encode(i.src), IsNil) iface, err := t.dec.DecodeInterface() c.Assert(err, IsNil) c.Assert(iface, DeepEquals, i.src) } } func (t *MsgpackTest) TestString(c *C) { highFixStr := strings.Repeat("w", 31) lowStr8 := strings.Repeat("w", 32) highStr8 := strings.Repeat("w", 255) lowStr16 := strings.Repeat("w", 256) highStr16 := strings.Repeat("w", 65535) lowStr32 := strings.Repeat("w", 65536) for _, i := range []struct { src string b []byte }{ {"", []byte{0xa0}}, // fixstr {"a", []byte{0xa1, 'a'}}, // fixstr {"hello", append([]byte{0xa5}, "hello"...)}, // fixstr { highFixStr, append([]byte{0xbf}, highFixStr...), }, { lowStr8, append([]byte{0xd9, byte(len(lowStr8))}, lowStr8...), }, { highStr8, append([]byte{0xd9, byte(len(highStr8))}, highStr8...), }, { lowStr16, append([]byte{0xda, 1, 0}, lowStr16...), }, { highStr16, append([]byte{0xda, 255, 255}, highStr16...), }, { lowStr32, append([]byte{0xdb, 0, 1, 0, 0}, lowStr32...), }, } { c.Assert(t.enc.Encode(i.src), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, i.b) var dst string c.Assert(t.dec.Decode(&dst), IsNil) c.Assert(dst, Equals, i.src) c.Assert(t.enc.Encode(i.src), IsNil) iface, err := t.dec.DecodeInterface() c.Assert(err, IsNil) c.Assert(iface, DeepEquals, i.src) } } func (t *MsgpackTest) TestLargeBytes(c *C) { N := int(1e6) src := bytes.Repeat([]byte{'1'}, N) c.Assert(t.enc.Encode(src), IsNil) var dst []byte c.Assert(t.dec.Decode(&dst), IsNil) c.Assert(dst, DeepEquals, src) } func (t *MsgpackTest) TestLargeString(c *C) { N := int(1e6) src := string(bytes.Repeat([]byte{'1'}, N)) c.Assert(t.enc.Encode(src), IsNil) var dst string c.Assert(t.dec.Decode(&dst), IsNil) c.Assert(dst, Equals, src) } func (t *MsgpackTest) TestSliceOfStructs(c *C) { in := []*nameStruct{&nameStruct{"hello"}} var out []*nameStruct c.Assert(t.enc.Encode(in), IsNil) c.Assert(t.dec.Decode(&out), IsNil) c.Assert(out, DeepEquals, in) } func (t *MsgpackTest) TestMap(c *C) { for _, i := range []struct { m map[string]string b []byte }{ {map[string]string{}, []byte{0x80}}, {map[string]string{"hello": "world"}, []byte{0x81, 0xa5, 0x68, 0x65, 0x6c, 0x6c, 0x6f, 0xa5, 0x77, 0x6f, 0x72, 0x6c, 0x64}}, } { c.Assert(t.enc.Encode(i.m), IsNil) c.Assert(t.buf.Bytes(), DeepEquals, i.b, Commentf("err encoding %v", i.m)) var m map[string]string c.Assert(t.dec.Decode(&m), IsNil) c.Assert(m, DeepEquals, i.m) } } func (t *MsgpackTest) TestStructNil(c *C) { var dst *nameStruct c.Assert(t.enc.Encode(nameStruct{Name: "foo"}), IsNil) c.Assert(t.dec.Decode(&dst), IsNil) c.Assert(dst, Not(IsNil)) c.Assert(dst.Name, Equals, "foo") } func (t *MsgpackTest) TestStructUnknownField(c *C) { in := struct { Field1 string Field2 string Field3 string }{ Field1: "value1", Field2: "value2", Field3: "value3", } c.Assert(t.enc.Encode(in), IsNil) out := struct { Field2 string }{} c.Assert(t.dec.Decode(&out), IsNil) c.Assert(out.Field2, Equals, "value2") } //------------------------------------------------------------------------------ type coderStruct struct { name string } type wrapperStruct struct { coderStruct `msgpack:",inline"` } var ( _ msgpack.CustomEncoder = &coderStruct{} _ msgpack.CustomDecoder = &coderStruct{} ) func (s *coderStruct) Name() string { return s.name } func (s *coderStruct) EncodeMsgpack(enc *msgpack.Encoder) error { return enc.Encode(s.name) } func (s *coderStruct) DecodeMsgpack(dec *msgpack.Decoder) error { return dec.Decode(&s.name) } func (t *MsgpackTest) TestCoder(c *C) { in := &coderStruct{name: "hello"} var out coderStruct c.Assert(t.enc.Encode(in), IsNil) c.Assert(t.dec.Decode(&out), IsNil) c.Assert(out.Name(), Equals, "hello") } func (t *MsgpackTest) TestNilCoder(c *C) { in := &coderStruct{name: "hello"} var out *coderStruct c.Assert(t.enc.Encode(in), IsNil) c.Assert(t.dec.Decode(&out), IsNil) c.Assert(out.Name(), Equals, "hello") } // func (t *MsgpackTest) TestNilCoderValue(c *C) { // in := &coderStruct{name: "hello"} // var out *coderStruct // v := reflect.ValueOf(out) // c.Assert(t.enc.Encode(in), IsNil) // c.Assert(t.dec.DecodeValue(v), IsNil) // c.Assert(out.Name(), Equals, "hello") // } func (t *MsgpackTest) TestPtrToCoder(c *C) { in := &coderStruct{name: "hello"} var out coderStruct out2 := &out c.Assert(t.enc.Encode(in), IsNil) c.Assert(t.dec.Decode(&out2), IsNil) c.Assert(out.Name(), Equals, "hello") } func (t *MsgpackTest) TestWrappedCoder(c *C) { in := &wrapperStruct{coderStruct: coderStruct{name: "hello"}} var out wrapperStruct c.Assert(t.enc.Encode(in), IsNil) c.Assert(t.dec.Decode(&out), IsNil) c.Assert(out.Name(), Equals, "hello") } //------------------------------------------------------------------------------ type struct2 struct { Name string } type struct1 struct { Name string Struct2 struct2 } func (t *MsgpackTest) TestNestedStructs(c *C) { in := &struct1{Name: "hello", Struct2: struct2{Name: "world"}} var out struct1 c.Assert(t.enc.Encode(in), IsNil) c.Assert(t.dec.Decode(&out), IsNil) c.Assert(out.Name, Equals, in.Name) c.Assert(out.Struct2.Name, Equals, in.Struct2.Name) } type Struct4 struct { Name2 string } type Struct3 struct { Struct4 Name1 string } func TestEmbedding(t *testing.T) { in := &Struct3{ Name1: "hello", Struct4: Struct4{ Name2: "world", }, } var out Struct3 b, err := msgpack.Marshal(in) if err != nil { t.Fatal(err) } err = msgpack.Unmarshal(b, &out) if err != nil { t.Fatal(err) } if out.Name1 != in.Name1 { t.Fatalf("") } if out.Name2 != in.Name2 { t.Fatalf("") } } func (t *MsgpackTest) TestSliceNil(c *C) { in := [][]*int{nil} var out [][]*int c.Assert(t.enc.Encode(in), IsNil) c.Assert(t.dec.Decode(&out), IsNil) c.Assert(out, DeepEquals, in) } //------------------------------------------------------------------------------ func (t *MsgpackTest) TestMapStringInterface(c *C) { in := map[string]interface{}{ "foo": "bar", "hello": map[string]interface{}{ "foo": "bar", }, } var out map[string]interface{} c.Assert(t.enc.Encode(in), IsNil) c.Assert(t.dec.Decode(&out), IsNil) c.Assert(out["foo"], Equals, "bar") mm := out["hello"].(map[interface{}]interface{}) c.Assert(mm["foo"], Equals, "bar") } func (t *MsgpackTest) TestMapStringInterface2(c *C) { buf := &bytes.Buffer{} enc := msgpack.NewEncoder(buf) dec := msgpack.NewDecoder(buf) dec.DecodeMapFunc = func(d *msgpack.Decoder) (interface{}, error) { n, err := d.DecodeMapLen() if err != nil { return nil, err } m := make(map[string]interface{}, n) for i := 0; i < n; i++ { mk, err := d.DecodeString() if err != nil { return nil, err } mv, err := d.DecodeInterface() if err != nil { return nil, err } m[mk] = mv } return m, nil } in := map[string]interface{}{ "foo": "bar", "hello": map[string]interface{}{ "foo": "bar", }, } var out map[string]interface{} c.Assert(enc.Encode(in), IsNil) c.Assert(dec.Decode(&out), IsNil) c.Assert(out["foo"], Equals, "bar") mm := out["hello"].(map[string]interface{}) c.Assert(mm["foo"], Equals, "bar") } //------------------------------------------------------------------------------ func benchmarkEncodeDecode(b *testing.B, src, dst interface{}) { buf := &bytes.Buffer{} enc := msgpack.NewEncoder(buf) dec := msgpack.NewDecoder(buf) b.ResetTimer() for i := 0; i < b.N; i++ { if err := enc.Encode(src); err != nil { b.Fatal(err) } if err := dec.Decode(dst); err != nil { b.Fatal(err) } } } func BenchmarkBool(b *testing.B) { var dst bool benchmarkEncodeDecode(b, true, &dst) } func BenchmarkInt0(b *testing.B) { var dst int benchmarkEncodeDecode(b, 1, &dst) } func BenchmarkInt1(b *testing.B) { var dst int benchmarkEncodeDecode(b, -33, &dst) } func BenchmarkInt2(b *testing.B) { var dst int benchmarkEncodeDecode(b, 128, &dst) } func BenchmarkInt4(b *testing.B) { var dst int benchmarkEncodeDecode(b, 32768, &dst) } func BenchmarkInt8(b *testing.B) { var dst int benchmarkEncodeDecode(b, 2147483648, &dst) } func BenchmarkIntBinary(b *testing.B) { buf := &bytes.Buffer{} var out int32 for i := 0; i < b.N; i++ { if err := binary.Write(buf, binary.BigEndian, int32(1)); err != nil { b.Fatal(err) } if err := binary.Read(buf, binary.BigEndian, &out); err != nil { b.Fatal(err) } } } func BenchmarkIntUgorjiGoMsgpack(b *testing.B) { buf := &bytes.Buffer{} dec := gomsgpack.NewDecoder(buf, nil) enc := gomsgpack.NewEncoder(buf) var out int for i := 0; i < b.N; i++ { if err := enc.Encode(1); err != nil { b.Fatal(err) } if err := dec.Decode(&out); err != nil { b.Fatal(err) } } } func BenchmarkIntUgorjiGoCodec(b *testing.B) { buf := &bytes.Buffer{} enc := gocodec.NewEncoder(buf, &gocodec.MsgpackHandle{}) dec := gocodec.NewDecoder(buf, &gocodec.MsgpackHandle{}) var out int for i := 0; i < b.N; i++ { if err := enc.Encode(1); err != nil { b.Fatal(err) } if err := dec.Decode(&out); err != nil { b.Fatal(err) } } } func BenchmarkTime(b *testing.B) { var dst time.Time benchmarkEncodeDecode(b, time.Now(), &dst) } func BenchmarkDuration(b *testing.B) { var dst time.Duration benchmarkEncodeDecode(b, time.Hour, &dst) } func BenchmarkBytes(b *testing.B) { src := make([]byte, 1024) var dst []byte benchmarkEncodeDecode(b, src, &dst) } func BenchmarkMapStringString(b *testing.B) { src := map[string]string{ "hello": "world", "foo": "bar", } var dst map[string]string benchmarkEncodeDecode(b, src, &dst) } func BenchmarkMapStringStringPtr(b *testing.B) { src := map[string]string{ "hello": "world", "foo": "bar", } var dst map[string]string dstptr := &dst benchmarkEncodeDecode(b, src, &dstptr) } func BenchmarkMapIntInt(b *testing.B) { src := map[int]int{ 1: 10, 2: 20, } var dst map[int]int benchmarkEncodeDecode(b, src, &dst) } func BenchmarkStringSlice(b *testing.B) { src := []string{"hello", "world"} var dst []string benchmarkEncodeDecode(b, src, &dst) } func BenchmarkStringSlicePtr(b *testing.B) { src := []string{"hello", "world"} var dst []string dstptr := &dst benchmarkEncodeDecode(b, src, &dstptr) } type benchmarkStruct struct { Name string Age int Colors []string Data []byte CreatedAt time.Time UpdatedAt time.Time } type benchmarkStruct2 struct { Name string Age int Colors []string Data []byte CreatedAt time.Time UpdatedAt time.Time } var ( _ msgpack.CustomEncoder = &benchmarkStruct2{} _ msgpack.CustomDecoder = &benchmarkStruct2{} ) func (s *benchmarkStruct2) EncodeMsgpack(enc *msgpack.Encoder) error { return enc.Encode( s.Name, s.Colors, s.Age, s.Data, s.CreatedAt, s.UpdatedAt, ) } func (s *benchmarkStruct2) DecodeMsgpack(dec *msgpack.Decoder) error { return dec.Decode( &s.Name, &s.Colors, &s.Age, &s.Data, &s.CreatedAt, &s.UpdatedAt, ) } func structForBenchmark() *benchmarkStruct { return &benchmarkStruct{ Name: "Hello World", Colors: []string{"red", "orange", "yellow", "green", "blue", "violet"}, Age: math.MaxInt32, Data: make([]byte, 1024), CreatedAt: time.Now(), UpdatedAt: time.Now(), } } func structForBenchmark2() *benchmarkStruct2 { return &benchmarkStruct2{ Name: "Hello World", Colors: []string{"red", "orange", "yellow", "green", "blue", "violet"}, Age: math.MaxInt32, Data: make([]byte, 1024), CreatedAt: time.Now(), UpdatedAt: time.Now(), } } func BenchmarkStruct(b *testing.B) { in := structForBenchmark() out := &benchmarkStruct{} for i := 0; i < b.N; i++ { buf, err := msgpack.Marshal(in) if err != nil { b.Fatal(err) } err = msgpack.Unmarshal(buf, out) if err != nil { b.Fatal(err) } } } func BenchmarkStructManual(b *testing.B) { in := structForBenchmark2() out := &benchmarkStruct2{} for i := 0; i < b.N; i++ { buf, err := msgpack.Marshal(in) if err != nil { b.Fatal(err) } err = msgpack.Unmarshal(buf, out) if err != nil { b.Fatal(err) } } } func BenchmarkStructUgorjiGoMsgpack(b *testing.B) { in := structForBenchmark() out := &benchmarkStruct{} for i := 0; i < b.N; i++ { buf, err := gomsgpack.Marshal(in) if err != nil { b.Fatal(err) } err = gomsgpack.Unmarshal(buf, out, nil) if err != nil { b.Fatal(err) } } } func BenchmarkStructUgorjiGoCodec(b *testing.B) { in := structForBenchmark() out := &benchmarkStruct{} for i := 0; i < b.N; i++ { buf := &bytes.Buffer{} enc := gocodec.NewEncoder(buf, &gocodec.MsgpackHandle{}) dec := gocodec.NewDecoder(buf, &gocodec.MsgpackHandle{}) if err := enc.Encode(in); err != nil { b.Fatal(err) } if err := dec.Decode(out); err != nil { b.Fatal(err) } } } func BenchmarkStructJSON(b *testing.B) { in := structForBenchmark() out := &benchmarkStruct{} for i := 0; i < b.N; i++ { buf, err := json.Marshal(in) if err != nil { b.Fatal(err) } err = json.Unmarshal(buf, out) if err != nil { b.Fatal(err) } } } func BenchmarkStructGOB(b *testing.B) { in := structForBenchmark() out := &benchmarkStruct{} for i := 0; i < b.N; i++ { buf := &bytes.Buffer{} enc := gob.NewEncoder(buf) dec := gob.NewDecoder(buf) if err := enc.Encode(in); err != nil { b.Fatal(err) } if err := dec.Decode(out); err != nil { b.Fatal(err) } } } func BenchmarkStructDecode(b *testing.B) { in := structForBenchmark() buf, err := msgpack.Marshal(in) if err != nil { b.Fatal(err) } out := &benchmarkStruct{} b.ResetTimer() for i := 0; i < b.N; i++ { err = msgpack.Unmarshal(buf, out) if err != nil { b.Fatal(err) } } } type benchmarkSubStruct struct { Name string Age int } func BenchmarkStructDecodePartially(b *testing.B) { in := structForBenchmark() buf, err := msgpack.Marshal(in) if err != nil { b.Fatal(err) } out := &benchmarkSubStruct{} b.ResetTimer() for i := 0; i < b.N; i++ { err = msgpack.Unmarshal(buf, out) if err != nil { b.Fatal(err) } } } func BenchmarkCSV(b *testing.B) { for i := 0; i < b.N; i++ { record := []string{"1", "hello", "world"} buf := &bytes.Buffer{} r := csv.NewReader(buf) w := csv.NewWriter(buf) if err := w.Write(record); err != nil { b.Fatal(err) } w.Flush() if _, err := r.Read(); err != nil { b.Fatal(err) } } } func BenchmarkCSVMsgpack(b *testing.B) { for i := 0; i < b.N; i++ { var num int var hello, world string buf := &bytes.Buffer{} enc := msgpack.NewEncoder(buf) dec := msgpack.NewDecoder(buf) if err := enc.Encode(1, "hello", "world"); err != nil { b.Fatal(err) } if err := dec.Decode(&num, &hello, &world); err != nil { b.Fatal(err) } } } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/slice.go000066400000000000000000000135051264326106400220030ustar00rootroot00000000000000package msgpack import ( "fmt" "io" "reflect" "gopkg.in/vmihailenco/msgpack.v2/codes" ) func (e *Encoder) encodeBytesLen(l int) error { if l < 256 { return e.write1(codes.Bin8, uint64(l)) } if l < 65536 { return e.write2(codes.Bin16, uint64(l)) } return e.write4(codes.Bin32, uint64(l)) } func (e *Encoder) encodeStrLen(l int) error { if l < 32 { return e.w.WriteByte(codes.FixedStrLow | uint8(l)) } if l < 256 { return e.write1(codes.Str8, uint64(l)) } if l < 65536 { return e.write2(codes.Str16, uint64(l)) } return e.write4(codes.Str32, uint64(l)) } func (e *Encoder) EncodeString(v string) error { if err := e.encodeStrLen(len(v)); err != nil { return err } return e.writeString(v) } func (e *Encoder) EncodeBytes(v []byte) error { if v == nil { return e.EncodeNil() } if err := e.encodeBytesLen(len(v)); err != nil { return err } return e.write(v) } func (e *Encoder) EncodeSliceLen(l int) error { if l < 16 { return e.w.WriteByte(codes.FixedArrayLow | byte(l)) } if l < 65536 { return e.write2(codes.Array16, uint64(l)) } return e.write4(codes.Array32, uint64(l)) } func (e *Encoder) encodeStringSlice(s []string) error { if s == nil { return e.EncodeNil() } if err := e.EncodeSliceLen(len(s)); err != nil { return err } for _, v := range s { if err := e.EncodeString(v); err != nil { return err } } return nil } func (e *Encoder) encodeSlice(v reflect.Value) error { if v.IsNil() { return e.EncodeNil() } return e.encodeArray(v) } func (e *Encoder) encodeArray(v reflect.Value) error { l := v.Len() if err := e.EncodeSliceLen(l); err != nil { return err } for i := 0; i < l; i++ { if err := e.EncodeValue(v.Index(i)); err != nil { return err } } return nil } func (d *Decoder) DecodeBytesLen() (int, error) { c, err := d.r.ReadByte() if err != nil { return 0, err } return d.bytesLen(c) } func (d *Decoder) bytesLen(c byte) (int, error) { if c == codes.Nil { return -1, nil } else if c >= codes.FixedStrLow && c <= codes.FixedStrHigh { return int(c & codes.FixedStrMask), nil } switch c { case codes.Str8, codes.Bin8: n, err := d.uint8() return int(n), err case codes.Str16, codes.Bin16: n, err := d.uint16() return int(n), err case codes.Str32, codes.Bin32: n, err := d.uint32() return int(n), err } return 0, fmt.Errorf("msgpack: invalid code %x decoding bytes length", c) } func (d *Decoder) DecodeBytes() ([]byte, error) { c, err := d.r.ReadByte() if err != nil { return nil, err } return d.bytes(c) } func (d *Decoder) bytes(c byte) ([]byte, error) { n, err := d.bytesLen(c) if err != nil { return nil, err } if n == -1 { return nil, nil } b := make([]byte, n) _, err = io.ReadFull(d.r, b) if err != nil { return nil, err } return b, nil } func (d *Decoder) skipBytes(c byte) error { n, err := d.bytesLen(c) if err != nil { return err } if n == -1 { return nil } return d.skipN(n) } func (d *Decoder) bytesValue(value reflect.Value) error { v, err := d.DecodeBytes() if err != nil { return err } value.SetBytes(v) return nil } func (d *Decoder) DecodeString() (string, error) { c, err := d.r.ReadByte() if err != nil { return "", err } return d.string(c) } func (d *Decoder) string(c byte) (string, error) { n, err := d.bytesLen(c) if err != nil { return "", err } if n == -1 { return "", nil } b, err := d.readN(n) if err != nil { return "", err } return string(b), nil } func (d *Decoder) stringValue(value reflect.Value) error { v, err := d.DecodeString() if err != nil { return err } value.SetString(v) return nil } func (d *Decoder) DecodeSliceLen() (int, error) { c, err := d.r.ReadByte() if err != nil { return 0, err } return d.sliceLen(c) } func (d *Decoder) sliceLen(c byte) (int, error) { if c == codes.Nil { return -1, nil } else if c >= codes.FixedArrayLow && c <= codes.FixedArrayHigh { return int(c & codes.FixedArrayMask), nil } switch c { case codes.Array16: n, err := d.uint16() return int(n), err case codes.Array32: n, err := d.uint32() return int(n), err } return 0, fmt.Errorf("msgpack: invalid code %x decoding array length", c) } func (d *Decoder) decodeIntoStrings(sp *[]string) error { n, err := d.DecodeSliceLen() if err != nil { return err } if n == -1 { return nil } s := *sp if s == nil || len(s) < n { s = make([]string, n) } for i := 0; i < n; i++ { v, err := d.DecodeString() if err != nil { return err } s[i] = v } *sp = s return nil } func (d *Decoder) DecodeSlice() ([]interface{}, error) { n, err := d.DecodeSliceLen() if err != nil { return nil, err } if n == -1 { return nil, nil } s := make([]interface{}, n) for i := 0; i < n; i++ { v, err := d.DecodeInterface() if err != nil { return nil, err } s[i] = v } return s, nil } func (d *Decoder) skipSlice(c byte) error { n, err := d.sliceLen(c) if err != nil { return err } for i := 0; i < n; i++ { if err := d.Skip(); err != nil { return err } } return nil } func (d *Decoder) sliceValue(v reflect.Value) error { n, err := d.DecodeSliceLen() if err != nil { return err } if n == -1 { v.Set(reflect.Zero(v.Type())) return nil } if v.Len() < n || (v.Kind() == reflect.Slice && v.IsNil()) { v.Set(reflect.MakeSlice(v.Type(), n, n)) } for i := 0; i < n; i++ { sv := v.Index(i) if err := d.DecodeValue(sv); err != nil { return err } } return nil } func (d *Decoder) strings() ([]string, error) { n, err := d.DecodeSliceLen() if err != nil { return nil, err } if n == -1 { return nil, nil } ss := make([]string, n) for i := 0; i < n; i++ { s, err := d.DecodeString() if err != nil { return nil, err } ss[i] = s } return ss, nil } func (d *Decoder) stringsValue(value reflect.Value) error { ss, err := d.strings() if err != nil { return err } value.Set(reflect.ValueOf(ss)) return nil } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/tags.go000066400000000000000000000020731264326106400216400ustar00rootroot00000000000000// Copyright 2011 The Go Authors. All rights reserved. // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. package msgpack import ( "strings" ) // tagOptions is the string following a comma in a struct field's "json" // tag, or the empty string. It does not include the leading comma. type tagOptions string // parseTag splits a struct field's json tag into its name and // comma-separated options. func parseTag(tag string) (string, tagOptions) { if idx := strings.Index(tag, ","); idx != -1 { return tag[:idx], tagOptions(tag[idx+1:]) } return tag, tagOptions("") } // Contains reports whether a comma-separated list of options // contains a particular substr flag. substr must be surrounded by a // string boundary or commas. func (o tagOptions) Contains(optionName string) bool { if len(o) == 0 { return false } s := string(o) for s != "" { var next string i := strings.IndexRune(s, ',') if i >= 0 { s, next = s[:i], s[i+1:] } if s == optionName { return true } s = next } return false } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/time.go000066400000000000000000000021071264326106400216360ustar00rootroot00000000000000package msgpack import ( "fmt" "reflect" "time" ) var ( timeType = reflect.TypeOf((*time.Time)(nil)).Elem() ) func init() { Register(timeType, encodeTimeValue, decodeTimeValue) } func (e *Encoder) EncodeTime(tm time.Time) error { if err := e.w.WriteByte(0x92); err != nil { return err } if err := e.EncodeInt64(tm.Unix()); err != nil { return err } return e.EncodeInt(tm.Nanosecond()) } func (d *Decoder) DecodeTime() (time.Time, error) { b, err := d.r.ReadByte() if err != nil { return time.Time{}, err } if b != 0x92 { return time.Time{}, fmt.Errorf("msgpack: invalid code %x decoding time", b) } sec, err := d.DecodeInt64() if err != nil { return time.Time{}, err } nsec, err := d.DecodeInt64() if err != nil { return time.Time{}, err } return time.Unix(sec, nsec), nil } func encodeTimeValue(e *Encoder, v reflect.Value) error { tm := v.Interface().(time.Time) return e.EncodeTime(tm) } func decodeTimeValue(d *Decoder, v reflect.Value) error { tm, err := d.DecodeTime() if err != nil { return err } v.Set(reflect.ValueOf(tm)) return nil } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/typeinfo.go000066400000000000000000000316661264326106400225510ustar00rootroot00000000000000package msgpack import ( "fmt" "io/ioutil" "reflect" "sync" ) var ( marshalerType = reflect.TypeOf(new(Marshaler)).Elem() unmarshalerType = reflect.TypeOf(new(Unmarshaler)).Elem() encoderType = reflect.TypeOf(new(CustomEncoder)).Elem() decoderType = reflect.TypeOf(new(CustomDecoder)).Elem() ) type ( encoderFunc func(*Encoder, reflect.Value) error decoderFunc func(*Decoder, reflect.Value) error ) var ( typEncMap = make(map[reflect.Type]encoderFunc) typDecMap = make(map[reflect.Type]decoderFunc) ) // Register registers encoder and decoder functions for a type. // In most cases you should prefer implementing CustomEncoder and // CustomDecoder interfaces. func Register(typ reflect.Type, enc encoderFunc, dec decoderFunc) { typEncMap[typ] = enc typDecMap[typ] = dec } var structs = newStructCache() var ( valueEncoders []encoderFunc valueDecoders []decoderFunc ) func init() { valueEncoders = []encoderFunc{ reflect.Bool: encodeBoolValue, reflect.Int: encodeInt64Value, reflect.Int8: encodeInt64Value, reflect.Int16: encodeInt64Value, reflect.Int32: encodeInt64Value, reflect.Int64: encodeInt64Value, reflect.Uint: encodeUint64Value, reflect.Uint8: encodeUint64Value, reflect.Uint16: encodeUint64Value, reflect.Uint32: encodeUint64Value, reflect.Uint64: encodeUint64Value, reflect.Float32: encodeFloat32Value, reflect.Float64: encodeFloat64Value, reflect.Complex64: encodeUnsupportedValue, reflect.Complex128: encodeUnsupportedValue, reflect.Array: encodeArrayValue, reflect.Chan: encodeUnsupportedValue, reflect.Func: encodeUnsupportedValue, reflect.Interface: encodeInterfaceValue, reflect.Map: encodeMapValue, reflect.Ptr: encodePtrValue, reflect.Slice: encodeSliceValue, reflect.String: encodeStringValue, reflect.Struct: encodeStructValue, reflect.UnsafePointer: encodeUnsupportedValue, } valueDecoders = []decoderFunc{ reflect.Bool: decodeBoolValue, reflect.Int: decodeInt64Value, reflect.Int8: decodeInt64Value, reflect.Int16: decodeInt64Value, reflect.Int32: decodeInt64Value, reflect.Int64: decodeInt64Value, reflect.Uint: decodeUint64Value, reflect.Uint8: decodeUint64Value, reflect.Uint16: decodeUint64Value, reflect.Uint32: decodeUint64Value, reflect.Uint64: decodeUint64Value, reflect.Float32: decodeFloat64Value, reflect.Float64: decodeFloat64Value, reflect.Complex64: decodeUnsupportedValue, reflect.Complex128: decodeUnsupportedValue, reflect.Array: decodeArrayValue, reflect.Chan: decodeUnsupportedValue, reflect.Func: decodeUnsupportedValue, reflect.Interface: decodeInterfaceValue, reflect.Map: decodeMapValue, reflect.Ptr: decodePtrValue, reflect.Slice: decodeSliceValue, reflect.String: decodeStringValue, reflect.Struct: decodeStructValue, reflect.UnsafePointer: decodeUnsupportedValue, } } //------------------------------------------------------------------------------ type field struct { name string index []int omitEmpty bool encoder encoderFunc decoder decoderFunc } func (f *field) value(strct reflect.Value) reflect.Value { return strct.FieldByIndex(f.index) } func (f *field) Omit(strct reflect.Value) bool { return f.omitEmpty && isEmptyValue(f.value(strct)) } func (f *field) EncodeValue(e *Encoder, strct reflect.Value) error { return f.encoder(e, f.value(strct)) } func (f *field) DecodeValue(d *Decoder, strct reflect.Value) error { return f.decoder(d, f.value(strct)) } //------------------------------------------------------------------------------ type fields struct { List []*field Table map[string]*field } func newFields(numField int) *fields { return &fields{ List: make([]*field, 0, numField), Table: make(map[string]*field, numField), } } func (fs *fields) Len() int { return len(fs.List) } func (fs *fields) Add(field *field) { fs.List = append(fs.List, field) fs.Table[field.name] = field } func getFields(typ reflect.Type) *fields { numField := typ.NumField() fs := newFields(numField) for i := 0; i < numField; i++ { f := typ.Field(i) if f.PkgPath != "" { continue } name, opts := parseTag(f.Tag.Get("msgpack")) if name == "-" { continue } if opts.Contains("inline") { inlineFields(fs, f) continue } if name == "" { name = f.Name } field := &field{ name: name, index: f.Index, omitEmpty: opts.Contains("omitempty"), encoder: getEncoder(f.Type), decoder: getDecoder(f.Type), } fs.Add(field) } return fs } //------------------------------------------------------------------------------ func encodeUnsupportedValue(e *Encoder, v reflect.Value) error { return fmt.Errorf("msgpack: Encode(unsupported %T)", v.Interface()) } func decodeUnsupportedValue(d *Decoder, v reflect.Value) error { return fmt.Errorf("msgpack: Decode(unsupported %T)", v.Interface()) } //------------------------------------------------------------------------------ func encodeBoolValue(e *Encoder, v reflect.Value) error { return e.EncodeBool(v.Bool()) } func decodeBoolValue(d *Decoder, v reflect.Value) error { return d.boolValue(v) } //------------------------------------------------------------------------------ func encodeFloat32Value(e *Encoder, v reflect.Value) error { return e.EncodeFloat32(float32(v.Float())) } func encodeFloat64Value(e *Encoder, v reflect.Value) error { return e.EncodeFloat64(v.Float()) } func decodeFloat64Value(d *Decoder, v reflect.Value) error { return d.float64Value(v) } //------------------------------------------------------------------------------ func encodeStringValue(e *Encoder, v reflect.Value) error { return e.EncodeString(v.String()) } func decodeStringValue(d *Decoder, v reflect.Value) error { return d.stringValue(v) } //------------------------------------------------------------------------------ func encodeBytesValue(e *Encoder, v reflect.Value) error { return e.EncodeBytes(v.Bytes()) } func decodeBytesValue(d *Decoder, v reflect.Value) error { return d.bytesValue(v) } //------------------------------------------------------------------------------ func encodeInt64Value(e *Encoder, v reflect.Value) error { return e.EncodeInt64(v.Int()) } func decodeInt64Value(d *Decoder, v reflect.Value) error { return d.int64Value(v) } //------------------------------------------------------------------------------ func encodeUint64Value(e *Encoder, v reflect.Value) error { return e.EncodeUint64(v.Uint()) } func decodeUint64Value(d *Decoder, v reflect.Value) error { return d.uint64Value(v) } //------------------------------------------------------------------------------ func encodeSliceValue(e *Encoder, v reflect.Value) error { return e.encodeSlice(v) } func decodeSliceValue(d *Decoder, v reflect.Value) error { return d.sliceValue(v) } //------------------------------------------------------------------------------ func encodeArrayValue(e *Encoder, v reflect.Value) error { return e.encodeArray(v) } func decodeArrayValue(d *Decoder, v reflect.Value) error { return d.sliceValue(v) } //------------------------------------------------------------------------------ func encodeInterfaceValue(e *Encoder, v reflect.Value) error { if v.IsNil() { return e.EncodeNil() } return e.EncodeValue(v.Elem()) } func decodeInterfaceValue(d *Decoder, v reflect.Value) error { if v.IsNil() { return d.interfaceValue(v) } return d.DecodeValue(v.Elem()) } //------------------------------------------------------------------------------ func encodeMapValue(e *Encoder, v reflect.Value) error { return e.encodeMap(v) } func decodeMapValue(d *Decoder, v reflect.Value) error { return d.mapValue(v) } //------------------------------------------------------------------------------ func encodePtrValue(e *Encoder, v reflect.Value) error { if v.IsNil() { return e.EncodeNil() } return e.EncodeValue(v.Elem()) } func decodePtrValue(d *Decoder, v reflect.Value) error { if v.IsNil() { if !v.CanSet() { return fmt.Errorf("msgpack: Decode(nonsettable %T)", v.Interface()) } vv := reflect.New(v.Type().Elem()) v.Set(vv) } return d.DecodeValue(v.Elem()) } //------------------------------------------------------------------------------ func encodeStructValue(e *Encoder, v reflect.Value) error { return e.encodeStruct(v) } func decodeStructValue(d *Decoder, v reflect.Value) error { return d.structValue(v) } //------------------------------------------------------------------------------ func encodeCustomValuePtr(e *Encoder, v reflect.Value) error { if !v.CanAddr() { return fmt.Errorf("msgpack: Encode(non-addressable %T)", v.Interface()) } switch v.Kind() { case reflect.Chan, reflect.Func, reflect.Interface, reflect.Map, reflect.Ptr, reflect.Slice: if v.IsNil() { return e.EncodeNil() } } encoder := v.Addr().Interface().(CustomEncoder) return encoder.EncodeMsgpack(e) } func encodeCustomValue(e *Encoder, v reflect.Value) error { switch v.Kind() { case reflect.Chan, reflect.Func, reflect.Interface, reflect.Map, reflect.Ptr, reflect.Slice: if v.IsNil() { return e.EncodeNil() } } encoder := v.Interface().(CustomEncoder) return encoder.EncodeMsgpack(e) } func decodeCustomValuePtr(d *Decoder, v reflect.Value) error { if !v.CanAddr() { return fmt.Errorf("msgpack: Decode(nonsettable %T)", v.Interface()) } if d.gotNilCode() { return d.DecodeNil() } decoder := v.Addr().Interface().(CustomDecoder) return decoder.DecodeMsgpack(d) } func decodeCustomValue(d *Decoder, v reflect.Value) error { if d.gotNilCode() { return d.DecodeNil() } if v.IsNil() { v.Set(reflect.New(v.Type().Elem())) } decoder := v.Interface().(CustomDecoder) return decoder.DecodeMsgpack(d) } func marshalValue(e *Encoder, v reflect.Value) error { marshaler := v.Interface().(Marshaler) b, err := marshaler.MarshalMsgpack() if err != nil { return err } _, err = e.w.Write(b) return err } func unmarshalValue(d *Decoder, v reflect.Value) error { if v.IsNil() { v.Set(reflect.New(v.Type().Elem())) } b, err := ioutil.ReadAll(d.r) if err != nil { return err } unmarshaler := v.Interface().(Unmarshaler) return unmarshaler.UnmarshalMsgpack(b) } //------------------------------------------------------------------------------ type structCache struct { l sync.RWMutex m map[reflect.Type]*fields } func newStructCache() *structCache { return &structCache{ m: make(map[reflect.Type]*fields), } } func (m *structCache) Fields(typ reflect.Type) *fields { m.l.RLock() fs, ok := m.m[typ] m.l.RUnlock() if !ok { m.l.Lock() fs, ok = m.m[typ] if !ok { fs = getFields(typ) m.m[typ] = fs } m.l.Unlock() } return fs } func inlineFields(fs *fields, f reflect.StructField) { typ := f.Type for typ.Kind() == reflect.Ptr { typ = typ.Elem() } inlinedFields := getFields(typ).List if len(inlinedFields) == 0 { panic("no fields to inline") } for _, field := range inlinedFields { if _, ok := fs.Table[field.name]; ok { // Don't overwrite shadowed fields. continue } field.index = append(f.Index, field.index...) fs.Add(field) } } func getEncoder(typ reflect.Type) encoderFunc { enc := getTypeEncoder(typ) if id := extTypeId(typ); id != -1 { return makeExtEncoder(id, enc) } return enc } func getTypeEncoder(typ reflect.Type) encoderFunc { kind := typ.Kind() if typ.Implements(encoderType) { return encodeCustomValue } // Addressable struct field value. if reflect.PtrTo(typ).Implements(encoderType) { return encodeCustomValuePtr } if typ.Implements(marshalerType) { return marshalValue } if encoder, ok := typEncMap[typ]; ok { return encoder } if kind == reflect.Slice && typ.Elem().Kind() == reflect.Uint8 { return encodeBytesValue } return valueEncoders[kind] } func getDecoder(typ reflect.Type) decoderFunc { kind := typ.Kind() // Addressable struct field value. if kind != reflect.Ptr && reflect.PtrTo(typ).Implements(decoderType) { return decodeCustomValuePtr } if typ.Implements(decoderType) { return decodeCustomValue } if typ.Implements(unmarshalerType) { return unmarshalValue } if decoder, ok := typDecMap[typ]; ok { return decoder } if kind == reflect.Slice && typ.Elem().Kind() == reflect.Uint8 { return decodeBytesValue } return valueDecoders[kind] } func isEmptyValue(v reflect.Value) bool { switch v.Kind() { case reflect.Array, reflect.Map, reflect.Slice, reflect.String: return v.Len() == 0 case reflect.Bool: return !v.Bool() case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64: return v.Int() == 0 case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr: return v.Uint() == 0 case reflect.Float32, reflect.Float64: return v.Float() == 0 case reflect.Interface, reflect.Ptr: return v.IsNil() } return false } golang-gopkg-vmihailenco-msgpack.v2-2.4.7/types_test.go000066400000000000000000000133561264326106400231130ustar00rootroot00000000000000package msgpack_test import ( "reflect" "testing" "time" "gopkg.in/vmihailenco/msgpack.v2" "gopkg.in/vmihailenco/msgpack.v2/codes" ) //------------------------------------------------------------------------------ type intSet map[int]struct{} var ( _ msgpack.CustomEncoder = (*intSet)(nil) _ msgpack.CustomDecoder = (*intSet)(nil) ) func (set intSet) EncodeMsgpack(enc *msgpack.Encoder) error { slice := make([]int, 0, len(set)) for n, _ := range set { slice = append(slice, n) } return enc.Encode(slice) } func (setptr *intSet) DecodeMsgpack(dec *msgpack.Decoder) error { n, err := dec.DecodeSliceLen() if err != nil { return err } set := make(intSet, n) for i := 0; i < n; i++ { n, err := dec.DecodeInt() if err != nil { return err } set[n] = struct{}{} } *setptr = set return nil } //------------------------------------------------------------------------------ type compactEncoding struct { str string ref *compactEncoding num int } var ( _ msgpack.CustomEncoder = &compactEncoding{} _ msgpack.CustomDecoder = &compactEncoding{} ) func (s *compactEncoding) EncodeMsgpack(enc *msgpack.Encoder) error { return enc.Encode(s.str, s.ref, s.num) } func (s *compactEncoding) DecodeMsgpack(dec *msgpack.Decoder) error { return dec.Decode(&s.str, &s.ref, &s.num) } type compactEncodingFieldValue struct { Field compactEncoding } //------------------------------------------------------------------------------ type OmitEmptyTest struct { Foo string `msgpack:",omitempty"` Bar string `msgpack:",omitempty"` } type InlineTest struct { OmitEmptyTest `msgpack:",inline"` } //------------------------------------------------------------------------------ type binTest struct { in interface{} wanted []byte } var binTests = []binTest{ {nil, []byte{codes.Nil}}, {OmitEmptyTest{}, []byte{codes.FixedMapLow}}, {intSet{}, []byte{codes.FixedArrayLow}}, {intSet{8: struct{}{}}, []byte{codes.FixedArrayLow | 1, 0x8}}, {&compactEncoding{}, []byte{codes.FixedStrLow, codes.Nil, 0x0}}, { &compactEncoding{"n", &compactEncoding{"o", nil, 7}, 6}, []byte{codes.FixedStrLow | 1, 'n', codes.FixedStrLow | 1, 'o', codes.Nil, 0x7, 0x6}, }, } func init() { test := binTest{in: &OmitEmptyTest{Foo: "hello"}} test.wanted = append(test.wanted, codes.FixedMapLow|1) test.wanted = append(test.wanted, codes.FixedStrLow|byte(len("Foo"))) test.wanted = append(test.wanted, "Foo"...) test.wanted = append(test.wanted, codes.FixedStrLow|byte(len("hello"))) test.wanted = append(test.wanted, "hello"...) binTests = append(binTests, test) test = binTest{in: &InlineTest{OmitEmptyTest: OmitEmptyTest{Bar: "world"}}} test.wanted = append(test.wanted, codes.FixedMapLow|1) test.wanted = append(test.wanted, codes.FixedStrLow|byte(len("Bar"))) test.wanted = append(test.wanted, "Bar"...) test.wanted = append(test.wanted, codes.FixedStrLow|byte(len("world"))) test.wanted = append(test.wanted, "world"...) binTests = append(binTests, test) } func TestBin(t *testing.T) { for _, test := range binTests { b, err := msgpack.Marshal(test.in) if err != nil { t.Fatal(err) } if !reflect.DeepEqual(b, test.wanted) { t.Fatalf("% x != % x", b, test.wanted) } } } //------------------------------------------------------------------------------ type embeddedTime struct { time.Time } type ( stringAlias string uint8Alias uint8 stringSlice []string ) type testStruct struct { F1 stringSlice F2 []string } type typeTest struct { *testing.T in interface{} out interface{} encErr string decErr string } func (t *typeTest) assertErr(err error, s string) { if err == nil { t.Fatalf("got %v, wanted %q", err, s) } if err.Error() != s { t.Fatalf("got %q, wanted %q", err, s) } } var ( typeTests = []typeTest{ {in: make(chan bool), encErr: "msgpack: Encode(unsupported chan bool)"}, {in: nil, out: nil, decErr: "msgpack: Decode(nil)"}, {in: nil, out: 0, decErr: "msgpack: Decode(nonsettable int)"}, {in: nil, out: (*int)(nil), decErr: "msgpack: Decode(nonsettable *int)"}, {in: nil, out: new(chan bool), decErr: "msgpack: Decode(unsupported chan bool)"}, {in: []int(nil), out: new([]int)}, {in: make([]int, 0), out: new([]int)}, {in: make([]int, 1000), out: new([]int)}, {in: []interface{}{uint64(1), "hello"}, out: new([]interface{})}, {in: map[string]interface{}{"foo": nil}, out: new(map[string]interface{})}, {in: stringSlice{"foo", "bar"}, out: new(stringSlice)}, {in: []stringAlias{"hello"}, out: new([]stringAlias)}, {in: []uint8Alias{1}, out: new([]uint8Alias)}, {in: intSet{}, out: new(intSet)}, {in: intSet{8: struct{}{}}, out: new(intSet)}, {in: testStruct{stringSlice{"foo", "bar"}, []string{"hello"}}, out: new(testStruct)}, {in: &coderStruct{name: "hello"}, out: new(*coderStruct)}, {in: &embeddedTime{Time: time.Now()}, out: new(*embeddedTime)}, {in: &compactEncoding{}, out: new(compactEncoding)}, {in: &compactEncoding{"a", &compactEncoding{"b", nil, 1}, 2}, out: new(compactEncoding)}, { in: &compactEncodingFieldValue{Field: compactEncoding{"a", nil, 1}}, out: new(compactEncodingFieldValue), }, } ) func deref(viface interface{}) interface{} { v := reflect.ValueOf(viface) for v.Kind() == reflect.Ptr { v = v.Elem() } if v.IsValid() { return v.Interface() } return nil } func TestTypes(t *testing.T) { for _, test := range typeTests { test.T = t b, err := msgpack.Marshal(test.in) if test.encErr != "" { test.assertErr(err, test.encErr) continue } if err != nil { t.Fatal(err) } err = msgpack.Unmarshal(b, test.out) if test.decErr != "" { test.assertErr(err, test.decErr) continue } if err != nil { t.Fatal(err) } in := deref(test.in) out := deref(test.out) if !reflect.DeepEqual(out, in) { t.Fatalf("%#v != %#v", out, in) } } }