func (c *client) Call(ctx Context, serviceName, methodName string, req, resp thrift.TStruct) (bool, error) { call, err := c.sc.BeginCall(ctx, serviceName+"::"+methodName, &tchannel.CallOptions{Format: tchannel.Thrift}) if err != nil { return false, err } writer, err := call.Arg2Writer() if err != nil { return false, err } if err := writeHeaders(writer, ctx.Headers()); err != nil { return false, err } if err := writer.Close(); err != nil { return false, err } writer, err = call.Arg3Writer() if err != nil { return false, err } protocol := thrift.NewTBinaryProtocolTransport(&readWriterTransport{Writer: writer}) if err := req.Write(protocol); err != nil { return false, err } if err := writer.Close(); err != nil { return false, err } reader, err := call.Response().Arg2Reader() if err != nil { return false, err } headers, err := readHeaders(reader) if err != nil { return false, err } ctx.SetResponseHeaders(headers) if err := reader.Close(); err != nil { return false, err } success := !call.Response().ApplicationError() reader, err = call.Response().Arg3Reader() if err != nil { return success, err } protocol = thrift.NewTBinaryProtocolTransport(&readWriterTransport{Reader: reader}) if err := resp.Read(protocol); err != nil { return success, err } if err := reader.Close(); err != nil { return success, err } return success, nil }
// readResponse reads the response struct into resp, and returns: // (response headers, whether there was an application error, unexpected error). func readResponse(response *tchannel.OutboundCallResponse, resp thrift.TStruct) (map[string]string, bool, error) { reader, err := response.Arg2Reader() if err != nil { return nil, false, err } headers, err := readHeaders(reader) if err != nil { return nil, false, err } if err := reader.Close(); err != nil { return nil, false, err } success := !response.ApplicationError() reader, err = response.Arg3Reader() if err != nil { return headers, success, err } wp := getProtocolReader(reader) if err := resp.Read(wp.protocol); err != nil { thriftProtocolPool.Put(wp) return headers, success, err } thriftProtocolPool.Put(wp) return headers, success, reader.Close() }
// DeserializeThrift takes a byte slice and attempts to write it into the // given thrift struct using the thrift binary protocol. This is a temporary // measure before frames can be forwarded directly past the endpoint to the proper // destinaiton. func DeserializeThrift(b []byte, s athrift.TStruct) error { reader := bytes.NewReader(b) transport := athrift.NewStreamTransportR(reader) return s.Read(athrift.NewTBinaryProtocolTransport(transport)) }
// ReadStruct reads the given Thrift struct. It pools TProtocols. func ReadStruct(reader io.Reader, s thrift.TStruct) error { wp := getProtocolReader(reader) err := s.Read(wp.protocol) thriftProtocolPool.Put(wp) return err }