const protobuf = require('protobufjs'); const parseArgs = require('minimist'); const fs = require('fs'); class PBTools { constructor() { this.csMsgIdPb = null; this.csProtoPb = null; this.ssMsgIdPb = null; this.ssProtoPb = null; this.mtPb = null; this.protoDir = './proto/'; } async init() { { this.csProtoPb = await (new protobuf.Root()).load( this.protoDir + 'cs_proto.proto', { 'keepCase': true } ); } { this.csMsgIdPb = await (new protobuf.Root()).load( this.protoDir + 'cs_msgid.proto', { 'keepCase': true } ); this.csCmMsgId = this.csMsgIdPb.lookup('CMMessageId_e'); this.csSmMsgId = this.csMsgIdPb.lookup('SMMessageId_e'); } { this.ssProtoPb = await (new protobuf.Root()).load( this.protoDir + 'ss_proto.proto', { 'keepCase': true } ); } { this.ssMsgIdPb = await (new protobuf.Root()).load( this.protoDir + 'ss_msgid.proto', { 'keepCase': true } ); this.ssSSmMsgId = this.ssMsgIdPb.lookup('SSMMessageId_e'); } { this.mtPb = await (new protobuf.Root()).load( this.protoDir + 'mt.proto', { 'keepCase': true } ); } await this.genCsAutoGen(); await this.genMtAutoGen(); } async genCsAutoGen() { let data = `package cs import ( "f5" proto "github.com/golang/protobuf/proto" ) type MsgHandlerImpl struct { } type NetMsgHandler struct { MsgId int HandlerId int parseCb func([]byte) interface{} cb func(*f5.MsgHdr, MsgHandler) } var handlers [2000]*NetMsgHandler func GetNetMsgHandler(msgId uint16) *NetMsgHandler { handler := handlers[msgId] return handler } func DispatchMsg(handler *NetMsgHandler, hdr *f5.MsgHdr, msgHandler MsgHandler) { handler.cb(hdr, msgHandler) } func RegHandlerId(msgId int, handlerId int) { handler := handlers[msgId] handler.HandlerId = handlerId } func ParsePb(msgId uint16, data []byte) interface{} { handler := handlers[msgId] if handler == nil { return nil } return handler.parseCb(data) } `; data += ` type MsgHandler interface {`; this.csProtoPb.nested.cs.nestedArray.forEach( (item) => { if (item.name[0] == 'C' && item.name[1] == 'M') { data += ` ${item.name}(*f5.MsgHdr, *${item.name})`; } }); data += ` } `; this.csProtoPb.nested.cs.nestedArray.forEach( (item) => { if (item.name[0] == 'C' && item.name[1] == 'M') { data += ` func (this *MsgHandlerImpl) ${item.name}(hdr *f5.MsgHdr, msg *${item.name}) { } `; } }); this.csProtoPb.nested.cs.nestedArray.forEach( (item) => { if (item.name[0] == 'C' && item.name[1] == 'M') { data += ` func (this *${item.name}) GetNetMsgId() uint16 { return uint16(CMMessageIdE__${item.name}) } `; } else if (item.name[0] == 'S' && item.name[1] == 'M') { data += ` func (this *${item.name}) GetNetMsgId() uint16 { return uint16(SMMessageIdE__${item.name}) } `; } }); data += ` func init() { `; this.csProtoPb.nested.cs.nestedArray.forEach( (item) => { if (item.name[0] == 'C' && item.name[1] == 'M') { data += ` handlers[int(CMMessageIdE__${item.name})] = &NetMsgHandler{ MsgId: int(CMMessageIdE__${item.name}), parseCb: func (data []byte) interface{} { msg := &${item.name}{} proto.Unmarshal(data, msg) return msg }, cb: func (hdr *f5.MsgHdr, handler MsgHandler) { handler.${item.name}(hdr, hdr.Msg.(*${item.name})) }, } `; } }); data += ` }`; fs.writeFileSync('./cs/cs.auto_gen.go', data); } async genMtAutoGen() { let data = `package mtb `; fs.writeFileSync('./mtb/mtb.auto_gen.go', data); } } (new PBTools).init();