go与grpc

参考: https://github.com/grpc/grpc-go
http://doc.oschina.net/grpc?t=60133
快速入门 建议grpc服务分三步:写proto文件、写serve、写client
proto文件
建立文件:proto/ServeRoute.proto

syntax = "proto3"; // 指定proto版本 package proto; // 指定包名//定义传输过程用到的数据类型,数字代表内部成员序号 message Name { string name = 1; } message Msg1 { string message = 1; } message Msg2 { Msg1 message = 1; }//定义提供的服务 service ServeRoute{ rpc Serve1(Name) returns (Msg1) {} rpc Serve2(Name) returns (Msg2) {} }

在proto文件所在的文件夹输入下面命令,生产pb.go文件
protoc --go_out=plugins=grpc:. ServeRoute.proto

serve文件
【go与grpc】建立serve/serve.go
package mainimport ( pb "../proto" // 引入编译生成的包 "golang.org/x/net/context" "google.golang.org/grpc" "log" "net" ) //通过一个结构体,实现proto中定义的所有服务 type ServeRoute struct{}func (h ServeRoute) Serve1(ctx context.Context, in *pb.Name) (*pb.Msg1, error) { log.Println("serve 1 works: get name: ", in.Name) resp := &pb.Msg1{Message:"this is serve 1"} return resp, nil }func (h ServeRoute) Serve2(ctx context.Context, in *pb.Name) (*pb.Msg2, error) { log.Println("serve 2 works, get name: ", in.Name) resp := &pb.Msg2{ Message:&pb.Msg1{Message:"this is serve 2"}, } return resp, nil } func main() { listen, err := net.Listen("tcp", "127.0.0.1:50052") // Address gRPC服务地址 if err != nil { log.Fatalf("failed to listen: %v", err) } s := grpc.NewServer() // 与http的注册路由类似,此处将所有服务注册到grpc服务器上, pb.RegisterServeRouteServer(s, ServeRoute{}) log.Println("grpc serve running") if err := s.Serve(listen); err != nil{ log.Fatal(err) } }

client文件
建立client/client.go(与serve分别为独立项目)
package main import ( pb "../proto" // 引入proto包 "golang.org/x/net/context" "google.golang.org/grpc" "log" )func main() { conn, err := grpc.Dial("127.0.0.1:50052", grpc.WithInsecure()) if err != nil { log.Fatalln(err) } defer conn.Close() c := pb.NewServeRouteClient(conn) reqBody1 := &pb.Name{Name:"wang"} res1, err := c.Serve1(context.Background(), reqBody1)//就像调用本地函数一样,通过serve1得到返回值 if err != nil { log.Fatalln(err) } log.Println("message from serve: ", res1.Message) reqBody2 := &pb.Name{Name:"li"} res2, err := c.Serve2(context.Background(), reqBody2)//就像调用本地函数一样,通过serve2得到返回值 if err != nil { log.Fatalln(err) } log.Println("message from serve: ", res2.Message.Message) }

运行

运行serve.go之后 serve端等待请求: 2019/07/04 20:37:40 grpc serve running运行client.go之后 serve端: 2019/07/04 20:37:51 serve 1 works: get name:wang 2019/07/04 20:37:51 serve 2 works, get name:li client端: 2019/07/04 20:37:51 message from serve:this is serve 1 2019/07/04 20:37:51 message from serve:this is serve 2


    推荐阅读