Go 快速搭建 Grpc 服务

179 阅读2分钟

开启掘金成长之旅!这是我参与「掘金日新计划 · 12 月更文挑战」的第7天,点击查看活动详情

记录下 golang 集成 Grpc + protobuf 的完整流程和开发,这个过程中可谓是走遍了各种坑,如果有不懂的可以留言或私信我

文章结尾附源码地址~

安装 protobuf

// mac下载方式
brew install protobuf

// 检查版本号  我这里用的是 3.19.x
protoc --version 

安装 go 的 protoc 插件

// proto 文件生成 go文件
go get -u github.com/golang/protobuf/protoc-gen-go

go get google.golang.org/protobuf

安装完成后会在 GOPATH/bin下生成执行文件,只要吧GOPATH/bin 下生成执行文件,只要吧 GOPATH/bin 加入到环境变量就可以了

测试 proto 生成 go 文件

创建个proto文件

syntax = "proto3";

//option go_package = "path;name";

import "google/api/annotations.proto";
option go_package = "./student-go";

enum ClassName {//枚举
    class1 = 0;  //标号 必须从 0开始
    class2 = 1;
    class3 = 2;
}

message ListStudentReq {//消息,对应于Go的结构体
    string name = 1; //1:标号,唯一 即可(相当于数据库中的Id,不一定要从1 ,2的顺序依次排列。)
    int32 age = 2;  //必须指定整型的范围,如int32,int64
    string address = 3;
    ClassName cn = 4;
}

message StudentsRes {
    string school = 2;
}



service StudentService {

    
    rpc ListStudent (ListStudentReq) returns (StudentsRes) {
        option (google.api.http) = {
            post: "/api/v1/calculation/discount/prompt"
            body: "*"
        };
    }
}

因为proto 文件中会涉及第三方的包,这里先下载下面的文件放到自己的目录下

📎protobuf.zip

下载这个protobuf.zip文件,放到自己的执行目录下,我这里放到了 /User/song/下,然后解压

然后进入到proto文件夹下 执行下面语句

protoc --version 版本为 libprotoc 3.17.x

protoc --proto_path=./ -I. -I /Users/song/protobuf --go_out=plugins=grpc:.  student.proto

protoc --version 版本为 libprotoc 3.19.x

 protoc --proto_path=./ -I. -I /Users/song/protobuf --go_out=. --go-grpc_out=. student.proto 

发现会生成两个文件

  • student.pb.go --go_out 命令生成
  • student_grpc.pb.go --go-grpc_out 生成

坑: libprotoc 3.19.x

  1. 在grpc server实现结构体中匿名嵌入Unimplemented***Server结构体

  2. 使用protoc生成server代码时命令行加上关闭选项,

protoc --go-grpc_out=require_unimplemented_servers=false

完整应该是

protoc --proto_path=./ -I. -I /Users/zhangshenghao/go/protobuf --go_out=. --go-grpc_out=require_unimplemented_servers=false:. student.proto

或者

protoc --proto_path=./ -I. -I /Users/zhangshenghao/go/protobuf --go_out=plugins=grpc:.  student.proto

具体的protoc 命令可以去了解一下

创建grpc服务

  1. 实现接口

我们实现下 pb.go 文件中的方法

type Student struct {
}

func (*Student) GetStudentById(context.Context, *student.StudentReq) (*student.StudentRes, error) {
    s := &student.StudentRes{}
    s.Id = 1
    s.Name = "zhang"
    return s, nil
}
  1. 创建服务端
package main

import (
    "flag"
    "fmt"
    "google.golang.org/grpc"
    "google.golang.org/grpc/reflection"
    "grpc-server/controller"
    "grpc-server/proto/student"
    "log"
    "net"
)

func main() {
    flag.Parse()
    lis, err := net.Listen("tcp", fmt.Sprintf(":%d", 7001))
    if err != nil {
       log.Fatalf("failed to listen: %v", err)
   }
    grpcServer := grpc.NewServer()
    // 注册服务
    student.RegisterStudentServiceServer(grpcServer, &controller.Student{})
    // 允许反射
    reflection.Register(grpcServer)
    grpcServer.Serve(lis)
}

使用 postman 的 grpc 功能进行测试

  1. 点击 new

  1. grpc request

3.输入 host 和 ip,红框2处会自动刷新反射出你的服务列表,选择你要测试的服务,message 中输入你的参数,我这里为了测试没有放入参,点击 invoke 输出结果,到此就结束了

源码地址:gitee.com/jar_project…