davyxu / cellnet

High performance, simple, extensible golang open source network library
MIT License
4.04k stars 880 forks source link

大佬 如何用json或者proto协议 作为数据传递 能否给个实列 #109

Open xdouzi opened 2 years ago

xdouzi commented 2 years ago

大佬 如何用json或者proto协议 作为数据传递 能否给个实列 大佬 我的游戏客户端是unity+xlua 解析层在lua 能否有 不用pb文件 lua直接解析成lua table 这样客户端体验要好些 能否给个demo www.408309839@qq.com 麻烦大佬

CuteReimu commented 1 year ago

自己实现一下codec那个接口就行了,主要是EncodeDecode函数。下面例子是解析proto,直接调用google的那个proto库。解析json你就换成json.Marshaljson.Unmashal。解析lua你就找个解析lua的第三方库调用一下就行了。


import (
    "github.com/davyxu/cellnet"
    "github.com/davyxu/cellnet/util"
    "google.golang.org/protobuf/proto"
    "google.golang.org/protobuf/reflect/protoreflect"
    "google.golang.org/protobuf/reflect/protoregistry"
    "reflect"
)

type protoCodec struct {
}

func (c *protoCodec) Name() string {
    return "protobuf" // 随便填
}

func (c *protoCodec) MimeType() string {
    return "application/x-protobuf" // 随便填
}

func (c *protoCodec) Encode(msgObj interface{}, _ cellnet.ContextSet) (data interface{}, err error) {
    // 这里是直接调用protobuf的Marshal函数,如果你想用lua你就换成lua的就行了
    return proto.Marshal(msgObj.(proto.Message))
}

func (c *protoCodec) Decode(data interface{}, msgObj interface{}) error {
    // 这里是直接调用protobuf的UnMarshal函数,如果你想用lua你就换成lua的就行了
    return proto.Unmarshal(data.([]byte), msgObj.(proto.Message))
}

// 将消息注册到系统
func init() {
    c := new(protoCodec)
    // 遍历注册所有协议,想手动指定协议ID就改成自己一个一个写
    protoregistry.GlobalTypes.RangeMessages(func(messageType protoreflect.MessageType) bool {
        cellnet.RegisterMessageMeta(&cellnet.MessageMeta{
            Codec: c,
            Type:  reflect.TypeOf(messageType.Zero().Interface()).Elem(),
            ID:    int(util.StringHash(string(messageType.Descriptor().Name()))),
        })
        return true
    })
}