summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorYuxuan 'fishy' Wang <yuxuan.wang@reddit.com>2021-01-22 09:37:18 -0800
committerYuxuan 'fishy' Wang <fishywang@gmail.com>2021-01-22 20:50:27 -0800
commitc2ddaf0766499ab522cb7c0ca011d579707fcb5f (patch)
treec05776669d220308884aa1fde25980035de056ad /lib
parent8dd04f4adfaea08699b1745c79f122bf9cbd6f07 (diff)
downloadthrift-c2ddaf0766499ab522cb7c0ca011d579707fcb5f.tar.gz
THRIFT-4914: Make TClient.Call to return the response meta
Client: go Make a breaking change so that TClient.Call returns the response meta, currently only contains headers but could be expanded in the future, and make a compiler change to compiler generated clients to take advantage of that and provide access to response metadata to users.
Diffstat (limited to 'lib')
-rw-r--r--lib/go/thrift/client.go24
-rw-r--r--lib/go/thrift/example_client_middleware_test.go6
-rw-r--r--lib/go/thrift/header_protocol.go14
-rw-r--r--lib/go/thrift/middleware.go4
-rw-r--r--lib/go/thrift/middleware_test.go6
5 files changed, 27 insertions, 27 deletions
diff --git a/lib/go/thrift/client.go b/lib/go/thrift/client.go
index 1c5705d55..ea2c01fda 100644
--- a/lib/go/thrift/client.go
+++ b/lib/go/thrift/client.go
@@ -5,8 +5,15 @@ import (
"fmt"
)
+// ResponseMeta represents the metadata attached to the response.
+type ResponseMeta struct {
+ // The headers in the response, if any.
+ // If the underlying transport/protocol is not THeader, this will always be nil.
+ Headers THeaderMap
+}
+
type TClient interface {
- Call(ctx context.Context, method string, args, result TStruct) error
+ Call(ctx context.Context, method string, args, result TStruct) (ResponseMeta, error)
}
type TStandardClient struct {
@@ -78,18 +85,25 @@ func (p *TStandardClient) Recv(ctx context.Context, iprot TProtocol, seqId int32
return iprot.ReadMessageEnd(ctx)
}
-func (p *TStandardClient) Call(ctx context.Context, method string, args, result TStruct) error {
+func (p *TStandardClient) Call(ctx context.Context, method string, args, result TStruct) (ResponseMeta, error) {
p.seqId++
seqId := p.seqId
if err := p.Send(ctx, p.oprot, seqId, method, args); err != nil {
- return err
+ return ResponseMeta{}, err
}
// method is oneway
if result == nil {
- return nil
+ return ResponseMeta{}, nil
}
- return p.Recv(ctx, p.iprot, seqId, method, result)
+ err := p.Recv(ctx, p.iprot, seqId, method, result)
+ var headers THeaderMap
+ if hp, ok := p.iprot.(*THeaderProtocol); ok {
+ headers = hp.transport.readHeaders
+ }
+ return ResponseMeta{
+ Headers: headers,
+ }, err
}
diff --git a/lib/go/thrift/example_client_middleware_test.go b/lib/go/thrift/example_client_middleware_test.go
index 8a29083c0..a68cdbc34 100644
--- a/lib/go/thrift/example_client_middleware_test.go
+++ b/lib/go/thrift/example_client_middleware_test.go
@@ -45,16 +45,16 @@ func NewMyServiceClient(_ TClient) MyService {
func simpleClientLoggingMiddleware(next TClient) TClient {
return WrappedTClient{
- Wrapped: func(ctx context.Context, method string, args, result TStruct) error {
+ Wrapped: func(ctx context.Context, method string, args, result TStruct) (ResponseMeta, error) {
log.Printf("Before: %q", method)
log.Printf("Args: %#v", args)
- err := next.Call(ctx, method, args, result)
+ headers, err := next.Call(ctx, method, args, result)
log.Printf("After: %q", method)
log.Printf("Result: %#v", result)
if err != nil {
log.Printf("Error: %v", err)
}
- return err
+ return headers, err
},
}
}
diff --git a/lib/go/thrift/header_protocol.go b/lib/go/thrift/header_protocol.go
index 35e045805..878041f8d 100644
--- a/lib/go/thrift/header_protocol.go
+++ b/lib/go/thrift/header_protocol.go
@@ -345,20 +345,6 @@ func (p *THeaderProtocol) SetTConfiguration(cfg *TConfiguration) {
p.cfg = cfg
}
-// GetResponseHeadersFromClient is a helper function to get the read THeaderMap
-// from the last response received from the given client.
-//
-// If the last response was not sent over THeader protocol,
-// a nil map will be returned.
-func GetResponseHeadersFromClient(c TClient) THeaderMap {
- if sc, ok := c.(*TStandardClient); ok {
- if hp, ok := sc.iprot.(*THeaderProtocol); ok {
- return hp.transport.readHeaders
- }
- }
- return nil
-}
-
var (
_ TConfigurationSetter = (*tHeaderProtocolFactory)(nil)
_ TConfigurationSetter = (*THeaderProtocol)(nil)
diff --git a/lib/go/thrift/middleware.go b/lib/go/thrift/middleware.go
index b575e16c4..8a788df02 100644
--- a/lib/go/thrift/middleware.go
+++ b/lib/go/thrift/middleware.go
@@ -78,11 +78,11 @@ type ClientMiddleware func(TClient) TClient
//
// This is provided to aid in developing ClientMiddleware.
type WrappedTClient struct {
- Wrapped func(ctx context.Context, method string, args, result TStruct) error
+ Wrapped func(ctx context.Context, method string, args, result TStruct) (ResponseMeta, error)
}
// Call implements the TClient interface by calling and returning c.Wrapped.
-func (c WrappedTClient) Call(ctx context.Context, method string, args, result TStruct) error {
+func (c WrappedTClient) Call(ctx context.Context, method string, args, result TStruct) (ResponseMeta, error) {
return c.Wrapped(ctx, method, args, result)
}
diff --git a/lib/go/thrift/middleware_test.go b/lib/go/thrift/middleware_test.go
index 2a4d1f957..6c4058fe1 100644
--- a/lib/go/thrift/middleware_test.go
+++ b/lib/go/thrift/middleware_test.go
@@ -54,7 +54,7 @@ func testProcessorMiddleware(c *counter) ProcessorMiddleware {
func testClientMiddleware(c *counter) ClientMiddleware {
return func(next TClient) TClient {
return WrappedTClient{
- Wrapped: func(ctx context.Context, method string, args, result TStruct) error {
+ Wrapped: func(ctx context.Context, method string, args, result TStruct) (ResponseMeta, error) {
c.incr()
return next.Call(ctx, method, args, result)
},
@@ -122,8 +122,8 @@ func TestWrapTMultiplexedProcessor(t *testing.T) {
func TestWrapClient(t *testing.T) {
client := WrappedTClient{
- Wrapped: func(ctx context.Context, method string, args, result TStruct) error {
- return nil
+ Wrapped: func(ctx context.Context, method string, args, result TStruct) (ResponseMeta, error) {
+ return ResponseMeta{}, nil
},
}
c := newCounter(t)