安装 protoc

https://github.com/protocolbuffers/protobuf/releases

这里找到你需要的版本

下载解压后,把 bin 目录放到环境变量

放好后 protoc 测试下

写 proto 文件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
syntax = "proto3";

package hello;

option go_package = "/proto";

// 定义 Greeter 服务
service Greeter {
// Sends a greeting
rpc SayHello (HelloRequest) returns (HelloReply) {}
}

// 请求消息
message HelloRequest {
string name = 1;
}

// 响应消息
message HelloReply {
string message = 1;
}

  1. 生成 Go 代码:使用 protoc 命令生成 Go 代码:
1
2
3
protoc --go_out=. --go_opt=paths=source_relative \
--go-grpc_out=. --go-grpc_opt=paths=source_relative \
proto/hello.proto

这将在同一目录下生成两个文件:hello.pb.gohello_grpc.pb.go

步骤 3: 实现服务端

创建一个新的 Go 文件 server.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
package main

import (
"context"
"log"
"net"

"google.golang.org/grpc"
pb "你的项目路径/proto"
)

type server struct {
pb.UnimplementedGreeterServer
}

func (s *server) SayHello(ctx context.Context, in *pb.HelloRequest) (*pb.HelloReply, error) {
return &pb.HelloReply{Message: "Hello " + in.Name}, nil
}

func main() {
lis, err := net.Listen("tcp", ":50051")
if err != nil {
log.Fatalf("failed to listen: %v", err)
}
s := grpc.NewServer()
pb.RegisterGreeterServer(s, &server{})
if err := s.Serve(lis); err != nil {
log.Fatalf("failed to serve: %v", err)
}
}

步骤 4: 实现客户端

创建一个新的 Go 文件 client.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
package main

import (
"context"
"log"
"time"

"google.golang.org/grpc"
pb "你的项目路径/proto"
)

func main() {
conn, err := grpc.Dial("localhost:50051", grpc.WithInsecure(), grpc.WithBlock())
if err != nil {
log.Fatalf("did not connect: %v", err)
}
defer conn.Close()
c := pb.NewGreeterClient(conn)

name := "world"
ctx, cancel := context.WithTimeout(context.Background(), time.Second)
defer cancel()
r, err := c.SayHello(ctx, &pb.HelloRequest{Name: name})
if err != nil {
log.Fatalf("could not greet: %v", err)
}
log.Printf("Greeting: %s", r.Message)
}

步骤 5: 运行 gRPC 应用

首先运行服务器:

1
go run server.go

然后在另一个终端窗口运行客户端:

1
go run client.go

如果一切正常,客户端将打印出从服务器接收到的问候消息。