43 Star 147 Fork 48

梁大帅 / mqant

加入 Gitee
与超过 1200万 开发者一起发现、参与优秀开源项目,私有仓库也完全免费 :)
免费加入
克隆/下载
encode_value.go 3.77 KB
一键复制 编辑 原始数据 按行查看 历史
liangdas 提交于 2017-03-21 22:11 . v1.2.0
package msgpack
import (
"fmt"
"reflect"
)
var valueEncoders []encoderFunc
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: encodeUnsupportedValue,
reflect.Slice: encodeSliceValue,
reflect.String: encodeStringValue,
reflect.Struct: encodeStructValue,
reflect.UnsafePointer: encodeUnsupportedValue,
}
}
func getEncoder(typ reflect.Type) encoderFunc {
enc := _getEncoder(typ)
if id := extTypeId(typ); id != -1 {
return makeExtEncoder(id, enc)
}
return enc
}
func _getEncoder(typ reflect.Type) encoderFunc {
kind := typ.Kind()
if typ.Implements(customEncoderType) {
return encodeCustomValue
}
// Addressable struct field value.
if kind != reflect.Ptr && reflect.PtrTo(typ).Implements(customEncoderType) {
return encodeCustomValuePtr
}
if typ.Implements(marshalerType) {
return marshalValue
}
if encoder, ok := typEncMap[typ]; ok {
return encoder
}
if typ == errorType {
return encodeErrorValue
}
switch kind {
case reflect.Ptr:
return ptrEncoderFunc(typ)
case reflect.Slice:
if typ.Elem().Kind() == reflect.Uint8 {
return encodeByteSliceValue
}
case reflect.Array:
if typ.Elem().Kind() == reflect.Uint8 {
return encodeByteArrayValue
}
case reflect.Map:
if typ.Key() == stringType {
switch typ.Elem() {
case stringType:
return encodeMapStringStringValue
case interfaceType:
return encodeMapStringInterfaceValue
}
}
}
return valueEncoders[kind]
}
func ptrEncoderFunc(typ reflect.Type) encoderFunc {
encoder := getEncoder(typ.Elem())
return func(e *Encoder, v reflect.Value) error {
if v.IsNil() {
return e.EncodeNil()
}
return encoder(e, v.Elem())
}
}
func encodeCustomValuePtr(e *Encoder, v reflect.Value) error {
if !v.CanAddr() {
return fmt.Errorf("msgpack: Encode(non-addressable %T)", v.Interface())
}
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 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 encodeBoolValue(e *Encoder, v reflect.Value) error {
return e.EncodeBool(v.Bool())
}
func encodeInterfaceValue(e *Encoder, v reflect.Value) error {
if v.IsNil() {
return e.EncodeNil()
}
return e.EncodeValue(v.Elem())
}
func encodeErrorValue(e *Encoder, v reflect.Value) error {
if v.IsNil() {
return e.EncodeNil()
}
return e.EncodeString(v.Interface().(error).Error())
}
func encodeUnsupportedValue(e *Encoder, v reflect.Value) error {
return fmt.Errorf("msgpack: Encode(unsupported %s)", v.Type())
}
Go
1
https://gitee.com/liangdas/mqant.git
git@gitee.com:liangdas/mqant.git
liangdas
mqant
mqant
v1.6.7

搜索帮助