在很多团队里,HTTP 接口文档是“代码写完以后补的”。
但 gRPC 的默认姿势是反过来的:
先定义合同
│
▼
写 .proto
│
▼
生成客户端 stub / 服务端骨架 / message 类
│
▼
两边按同一份图纸开发这会带来三个本质变化。
第一,接口不再靠“约定俗成”,而是靠正式合同。
前端、后端、服务 A、服务 B,不再通过口头说“这个字段大概叫 userId 吧”,而是看同一份 .proto。
第二,调用方不再手搓请求细节。
调用方拿到 stub 以后,更像在调一个本地对象:
reply = stub.GetRoute(RouteRequest(origin="税务局", destination="港口仓库"))你看到的是方法调用,底层才是远程通信。
第三,演进必须讲秩序。
message 的字段号是上线路由,不是随便玩的变量名。字段名可以重构,字段号才是线上的协议身份。
一个典型的协议演进片段:
message CitizenRecord {
reserved 4, 7;
reserved "old_phone";
string name = 1;
string id_card = 2;
string mobile = 3;
}这段的意思是:
- 老字段删了以后,不要复用原字段号
- 旧字段名也保留掉,防止后来的人误加回来
- 协议演进的重点是兼容,不是“看起来整齐”