REST

GRPC服务一般用于集群内部通信,如果需要对外暴露服务一般会提供等价的REST接口。通过REST接口比较方便前端JavaScript和后端交互。开源社区中的grpc-gateway项目就实现了将GRPC服务转为REST服务的能力。

syntax = "proto3";
package main;
import "google/api/annotations.proto";
message StringMessage {
  string value = 1;
}
service RestService {
    rpc Get(StringMessage) returns (StringMessage) {
        option (google.api.http) = {
            get: "/get/{value}"
        };
    }
    rpc Post(StringMessage) returns (StringMessage) {
        option (google.api.http) = {
            post: "/post"
            body: "*"
        };
    }
}

import "google/api/annotations.proto";存储的仓库路径有区别,在网上找到
https://github.com/googleapis/googleapis/blob/master/google/api/annotations.proto 
下载之后把它单独分开,并未在google目录结构:
自己的目录结构如下:
image.png

生成grpc代码和rest代码

protoc -I=F:\GoWeb\src\rpc\yuwei\rest -I=F:\GoWeb\src -I=F:\GoWeb\src\github.com\grpc-ecosystem\grpc-gateway\third_party\googleapis --go_out=plugins=grpc:F:\GoWeb\src\rpc\yuwei\rest F:\GoWeb\src\rpc\yuwei\rest\hello.proto
protoc -I=F:\GoWeb\src\rpc\yuwei\rest -I=F:\GoWeb\src -I=F:\GoWeb\src\github.com\grpc-ecosystem\grpc-gateway\third_party\googleapis --grpc-gateway_out=F:\GoWeb\src\rpc\yuwei\rest F:\GoWeb\src\rpc\yuwei\rest\hello.proto

grpc服务:

package main

import (
    "context"
    "log"
    "net"
    "rpc/yuwei/rest"

    "google.golang.org/grpc"
)

// 定义服务
type HelloServiceImpl struct {
}

func (p *HelloServiceImpl) Get(ctx context.Context, args *rest.StringMessage) (*rest.StringMessage, error) {
    reply := &rest.StringMessage{Value: args.GetValue()}
    return reply, nil
}
func (p *HelloServiceImpl) Post(ctx context.Context, args *rest.StringMessage) (*rest.StringMessage, error) {
    reply := &rest.StringMessage{Value: args.GetValue()}
    return reply, nil
}

func main() {
    grpcserver := grpc.NewServer()
    rest.RegisterRestServiceServer(grpcserver, new(HelloServiceImpl))
    lis, err := net.Listen("tcp", ":5000")
    if err != nil {
        log.Fatal(err)
    }
    grpcserver.Serve(lis)
}

rest服务:

package main

import (
    "context"
    "log"
    "net/http"
    "rpc/yuwei/rest"

    "google.golang.org/grpc"

    "github.com/grpc-ecosystem/grpc-gateway/runtime"
)

func main() {
    ctx := context.Background()
    ctx, cancel := context.WithCancel(ctx)
    defer cancel()

    mux := runtime.NewServeMux()
    var opts []grpc.DialOption
    opts = append(opts, grpc.WithInsecure())
    err := rest.RegisterRestServiceHandlerFromEndpoint(
        ctx, mux, "localhost:5000",
        opts,
    )

    if err != nil {
        log.Fatal(err)
    }
    http.ListenAndServe(":8080", mux)
}
Last modification:May 23rd, 2019 at 09:44 pm
如果觉得我的文章对你有用,请随意赞赏