-
Notifications
You must be signed in to change notification settings - Fork 5
/
main.go
114 lines (92 loc) · 2.64 KB
/
main.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
package main
import (
"context"
"fmt"
"math/rand"
"net"
"time"
pb "github.com/zhufuyi/grpc_examples/metadata/proto/hellopb"
grpc_middleware "github.com/grpc-ecosystem/go-grpc-middleware"
"github.com/grpc-ecosystem/go-grpc-middleware/util/metautils"
"github.com/zhufuyi/sponge/pkg/krand"
"google.golang.org/grpc"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/metadata"
"google.golang.org/grpc/status"
)
type greeterServer struct {
pb.UnimplementedGreeterServer
}
func (g *greeterServer) SayHello(ctx context.Context, r *pb.HelloRequest) (*pb.HelloReply, error) {
// return之后创建新的metadata
defer func() {
trailer := metadata.Pairs("foo", "bar2")
err := grpc.SetTrailer(ctx, trailer)
if err != nil {
fmt.Println(err)
}
}()
// 从client读取metadata
md, ok := metadata.FromIncomingContext(ctx)
if !ok {
return nil, status.Errorf(codes.DataLoss, "SayHello: failed to get metadata")
}
printMetadata(md, "token_str")
printMetadata(md, contextRequestIDKey)
// 创建新的metadata
header := metadata.New(map[string]string{
"foo": "bar",
})
_ = grpc.SendHeader(ctx, header)
// 随机延时0~1000微秒
time.Sleep(time.Duration(rand.Intn(1000)) * time.Microsecond)
return &pb.HelloReply{Message: "hello " + r.Name}, nil
}
func printMetadata(md metadata.MD, key string) {
if ts, ok := md[key]; ok {
fmt.Printf("metadata: %s=%v\n", key, ts)
} else {
fmt.Printf("not found '%s' in metadata\n", key)
}
}
var contextRequestIDKey = "request_id"
func unaryServerRequestID() grpc.UnaryServerInterceptor {
return func(ctx context.Context, req interface{}, info *grpc.UnaryServerInfo, handler grpc.UnaryHandler) (interface{}, error) {
requestID := serverCtxRequestID(ctx)
if requestID == "" {
md, _ := metadata.FromIncomingContext(ctx)
requestID = krand.String(krand.R_All, 10)
if md == nil {
md = metadata.Pairs(contextRequestIDKey, requestID)
} else {
md[contextRequestIDKey] = []string{requestID}
}
ctx = metadata.NewOutgoingContext(ctx, md)
}
return handler(ctx, req)
}
}
func serverCtxRequestID(ctx context.Context) string {
return metautils.ExtractIncoming(ctx).Get(contextRequestIDKey)
}
func getServerOptions() []grpc.ServerOption {
var options []grpc.ServerOption
options = append(options, grpc_middleware.WithUnaryServerChain(
unaryServerRequestID(),
))
return options
}
func main() {
addr := ":8282"
fmt.Println("grpc service is running", addr)
list, err := net.Listen("tcp", addr)
if err != nil {
panic(err)
}
server := grpc.NewServer(getServerOptions()...)
pb.RegisterGreeterServer(server, &greeterServer{})
err = server.Serve(list)
if err != nil {
panic(err)
}
}