// // 解析Thrift数据的Message Header // func ParseThriftMsgBegin(msg []byte) (name string, typeId thrift.TMessageType, seqId int32, err error) { transport := thrift.NewTMemoryBufferLen(256) transport.Write(msg) protocol := thrift.NewTBinaryProtocolTransport(transport) name, typeId, seqId, err = protocol.ReadMessageBegin() return }
// // 将Request中的SeqNum进行替换(修改Request部分的数据) // func (r *Request) ReplaceSeqId(newSeq int32) { if r.Request.Data != nil { // log.Printf(Green("Replace SeqNum: %d --> %d"), r.Request.SeqId, newSeq) if r.Response.SeqId != 0 { log.Errorf("Unexpected Response SedId") } r.Response.SeqId = newSeq start := 0 if r.ProxyRequest { start = len(r.Service) } if start > 0 { start += 1 // ":" // log.Printf("Service: %s, Name: %s\n", r.Service, r.Request.Name) } transport := NewTMemoryBufferWithBuf(r.Request.Data[start:start]) protocol := thrift.NewTBinaryProtocolTransport(transport) protocol.WriteMessageBegin(r.Request.Name, r.Request.TypeId, newSeq) if start > 0 { r.Request.DataOrig = r.Request.Data } // 将service从name中剥离出去 r.Request.Data = r.Request.Data[start:len(r.Request.Data)] } else { log.Errorf("ReplaceSeqId called on processed Data") } }
func fakeData(name string, typeId thrift.TMessageType, seqId int32, buf []byte) int { transport := NewTMemoryBufferWithBuf(buf) protocol := thrift.NewTBinaryProtocolTransport(transport) // 切换回原始的SeqId protocol.WriteMessageBegin(name, typeId, seqId) return transport.Buffer.Len() }
func HandleProxyPingRequest(req *Request) { transport := NewTMemoryBufferLen(30) protocol := thrift.NewTBinaryProtocolTransport(transport) protocol.WriteMessageBegin("ping", thrift.REPLY, req.Request.SeqId) result := services.NewRpcServiceBasePingResult() result.Write(protocol) protocol.WriteMessageEnd() protocol.Flush() req.Response.Data = transport.Bytes() }
// // 后端如何处理一个Request // func (p *ThriftRpcServer) Dispatch(r *Request) error { transport := NewTMemoryBufferWithBuf(r.Request.Data) ip := thrift.NewTBinaryProtocolTransport(transport) slice := getSlice(0, DEFAULT_SLICE_LEN) transport = NewTMemoryBufferWithBuf(slice) op := thrift.NewTBinaryProtocolTransport(transport) p.Processor.Process(ip, op) r.Response.Data = transport.Bytes() _, _, seqId, _ := DecodeThriftTypIdSeqId(r.Response.Data) log.Debugf("SeqId: %d vs. %d, Dispatch Over", r.Request.SeqId, seqId) // // 如果transport重新分配了内存,则立即归还slice // if cap(r.Response.Data) != DEFAULT_SLICE_LEN { // returnSlice(slice) // } return nil }
func GetWorkerNotFoundData(req *Request, module string) []byte { req.Response.TypeId = thrift.EXCEPTION // 构建thrift的Transport transport := thrift.NewTMemoryBufferLen(100) protocol := thrift.NewTBinaryProtocolTransport(transport) // 构建一个Message, 写入Exception msg := fmt.Sprintf("Worker FOR %s#%s.%s Not Found", module, req.Service, req.Request.Name) exc := thrift.NewTApplicationException(thrift.INTERNAL_ERROR, msg) protocol.WriteMessageBegin(req.Request.Name, thrift.EXCEPTION, req.Request.SeqId) exc.Write(protocol) protocol.WriteMessageEnd() bytes := transport.Bytes() return bytes }
func NewPingRequest() *Request { // 构建thrift的Transport transport := NewTMemoryBufferLen(30) protocol := thrift.NewTBinaryProtocolTransport(transport) protocol.WriteMessageBegin("ping", MESSAGE_TYPE_HEART_BEAT, 0) protocol.WriteMessageEnd() protocol.Flush() r := &Request{} // 告诉Request, Data中不包含service,在ReplaceSeqId时不需要特别处理 r.ProxyRequest = false r.Start = microseconds() r.Request.Data = transport.Bytes() r.Request.Name = "ping" r.Request.SeqId = 0 // SeqId在这里无效,因此设置为0 r.Request.TypeId = MESSAGE_TYPE_HEART_BEAT return r }
// // 生成Thrift格式的Exception Message // func GetServiceNotFoundData(req *Request) []byte { req.Response.TypeId = thrift.EXCEPTION // 构建thrift的Transport transport := thrift.NewTMemoryBufferLen(100) protocol := thrift.NewTBinaryProtocolTransport(transport) // 构建一个Message, 写入Exception msg := fmt.Sprintf("Service: %s Not Found", req.Service) exc := thrift.NewTApplicationException(thrift.UNKNOWN_APPLICATION_EXCEPTION, msg) protocol.WriteMessageBegin(req.Request.Name, thrift.EXCEPTION, req.Request.SeqId) exc.Write(protocol) protocol.WriteMessageEnd() protocol.Flush() bytes := transport.Bytes() return bytes }
func GetThriftException(req *Request, module string) []byte { req.Response.TypeId = thrift.EXCEPTION // 构建thrift的Transport transport := thrift.NewTMemoryBufferLen(256) protocol := thrift.NewTBinaryProtocolTransport(transport) msg := fmt.Sprintf("Module: %s, Service: %s, Method: %s, Error: %v", module, req.Service, req.Request.Name, req.Response.Err) // 构建一个Message, 写入Exception exc := thrift.NewTApplicationException(thrift.INTERNAL_ERROR, msg) // 注意消息的格式 protocol.WriteMessageBegin(req.Request.Name, thrift.EXCEPTION, req.Request.SeqId) exc.Write(protocol) protocol.WriteMessageEnd() bytes := transport.Bytes() return bytes }
// // 从Request.Data中读取出 Request的Name, TypeId, SeqId // RequestName可能和thrift package中的name不一致,Service部分从Name中剔除 // func (r *Request) DecodeRequest() error { var err error transport := NewTMemoryBufferWithBuf(r.Request.Data) protocol := thrift.NewTBinaryProtocolTransport(transport) // 如果数据异常,则直接报错 r.Request.Name, r.Request.TypeId, r.Request.SeqId, err = protocol.ReadMessageBegin() if err != nil { return err } // 参考 : TMultiplexedProtocol idx := strings.Index(r.Request.Name, thrift.MULTIPLEXED_SEPARATOR) if idx == -1 { r.Service = "" } else { r.Service = r.Request.Name[0:idx] r.Request.Name = r.Request.Name[idx+1 : len(r.Request.Name)] } return nil }