使用重载的端点构建proto3 gRPC API

huangapple go评论76阅读模式
英文:

Build proto3 gRPC API with overloaded endpoints

问题

我对API构建还比较新手,所以这可能是一个比我最初提出的问题更广泛的问题。
我正在使用Golang(使用protobuf 3和gRPC)创建一个API,其中有两个类似的端点:

  • GET /project/genres
  • GET /project/{id}

问题是,当我运行curl localhost:8080/project/genres时,模式匹配会导致以genres作为id调用/project/{id}端点。有没有简单的方法来解决这个问题,或者我是否需要在服务器代码中构建一些内容,以根据类型调用正确的函数?

我还尝试了交换这些定义的顺序,以防模式匹配有一些我不知道的操作顺序,但这没有任何区别。

这是我proto文件中的定义:

message EmptyRequest { }
message ProjectRequest {
  string id = 1;
}

message GenreResponse {
  int32 id = 1;
  string name = 2;
}

message ProjectResponse {
  int32 id = 1;
  string name = 2;
}

service ProjectService {
  rpc GetProject(ProjectRequest) returns (ProjectResponse) {
    option (google.api.http) = {
      get: "/v1/project/{id}"
    };
  }
  rpc GetGenres(EmptyRequest) returns (GenreResponse) {
    option (google.api.http) = {
      get: "/v1/project/genres"
    };
  }
}
英文:

I am fairly new to API building, so this may be a broader question than I originally posed.
I am creating an API in Golang (using protobuf 3 and gRPC) that has two similar endpoints:

  • GET /project/genres
  • GET /project/{id}

The problem is that when I run curl localhost:8080/project/genres, the pattern matching results in the /project/{id} endpoint getting called with genres as the id. Is there some simple way around this, or do I have to build something into the server code to call the proper function based on the type?

I also tried flipping the ordering of these definitions, just in case the pattern matching had some order of operations that I didn't know about, but this didn't make a difference.

Here are the definitions in my proto file:

message EmptyRequest { }
message ProjectRequest {
  string id = 1;
}

message GenreResponse {
  int32 id = 1;
  string name = 2;
}

message ProjectResponse {
  int32 id = 1;
  string name = 2;
}

service ProjectService {
  rpc GetProject(ProjectRequest) returns (ProjectResponse) {
    option (google.api.http) = {
      get: "/v1/project/{id}"
    };
  }
  rpc GetGenres(EmptyRequest) returns (GenreResponse) {
    option (google.api.http) = {
      get: "/v1/project/genres"
    };
  }
}

答案1

得分: 0

我能够在URL路径模板中指定一个检查来解决这个问题:

 rpc GetGenres(EmptyRequest) returns (GenreResponse) {
    option (google.api.http) = {
    get: "/v1/project/{id=genres}"
  };
}

这似乎解决了问题。我不知道是否还有其他解决方案,或者这是否是正确的方法,但如果有更好的解决方案,我愿意接受其他答案。

英文:

I was able to specify a check in the url path template to get around this issue:

 rpc GetGenres(EmptyRequest) returns (GenreResponse) {
    option (google.api.http) = {
    get: "/v1/project/{id=genres}"
  };
}

This seems to have fixed the problem. I don't know if there are other solutions, or if this is the right way to do this, but I'm happy to accept other answers if something better comes in.

huangapple
  • 本文由 发表于 2021年5月24日 22:46:36
  • 转载请务必保留本文链接:https://go.coder-hub.com/67674129.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定