From 4cb6fca7e99d31dde0a6aa6116fab85501f7c7e5 Mon Sep 17 00:00:00 2001 From: Vasiliy Tolstov Date: Tue, 18 Aug 2020 16:24:11 +0300 Subject: [PATCH] grpc: avoid allocations for each message (#1939) Signed-off-by: Vasiliy Tolstov --- grpc.go | 40 +++++++++++++++++++++++++++------------- 1 file changed, 27 insertions(+), 13 deletions(-) diff --git a/grpc.go b/grpc.go index f230fa4..ef0c9be 100644 --- a/grpc.go +++ b/grpc.go @@ -8,6 +8,7 @@ import ( "net" "reflect" "strings" + "sync" "sync/atomic" "time" @@ -24,9 +25,11 @@ import ( ) type grpcClient struct { - opts client.Options - pool *pool - once atomic.Value + opts client.Options + codecs map[string]encoding.Codec + pool *pool + once atomic.Value + sync.RWMutex } func init() { @@ -301,18 +304,13 @@ func (g *grpcClient) maxSendMsgSizeValue() int { } func (g *grpcClient) newGRPCCodec(contentType string) (encoding.Codec, error) { - codecs := make(map[string]encoding.Codec) - if g.opts.Context != nil { - if v := g.opts.Context.Value(codecsKey{}); v != nil { - codecs = v.(map[string]encoding.Codec) - } - } - if c, ok := codecs[contentType]; ok { - return wrapCodec{c}, nil - } - if c, ok := defaultGRPCCodecs[contentType]; ok { + g.RLock() + defer g.RUnlock() + + if c, ok := g.codecs[contentType]; ok { return wrapCodec{c}, nil } + return nil, fmt.Errorf("Unsupported Content-Type: %s", contentType) } @@ -721,6 +719,22 @@ func newClient(opts ...client.Option) client.Client { c = options.Wrappers[i-1](c) } + rc.codecs = make(map[string]encoding.Codec, len(defaultGRPCCodecs)) + for k, v := range defaultGRPCCodecs { + rc.codecs[k] = v + } + + var codecs map[string]encoding.Codec + if rc.opts.Context != nil { + if v := rc.opts.Context.Value(codecsKey{}); v != nil { + codecs = v.(map[string]encoding.Codec) + } + } + + for k, v := range codecs { + rc.codecs[k] = v + } + return c }