go-kit Truss 代码生成

go-kit Truss 代码生成

依赖

前提

Truss 安装

请参考: MacOS go-kit 自动生成代码工具 truss 安装

ProtoBuf 规范基本说明

请参考: go-kit Truss Protobuf 3 语法基本规范

Truss 使用

1. 创建项目

举个例子:

mkdir -p ~/goWork/truss_demo

2. 定义 protobuf

例如:vim ~/goWork/truss_demo/demo.proto

syntax = "proto3";
package demo;

import "github.com/metaverse/truss/deftree/googlethirdparty/annotations.proto";
import "google/protobuf/any.proto";
import "google/protobuf/struct.proto";

service MyDemo {

  // 获取
  rpc GetSomething (DefaultRequest) returns (DefaultResponse) {
    option (google.api.http) = {

      get: "/my_demo_service/something"

      additional_bindings {
        get: "/my_demo_service/something"
      }
    };
  }
  // 提交
  rpc PostSomething (PostSomethingRequest) returns (DefaultResponse) {
    option (google.api.http) = {
      custom {
        kind: "HEAD"
        path: "/my_demo_service/something"
      }
      additional_bindings {
        post: "/my_demo_service/something"
        body: "*"
      }
    };
  }
}

message DefaultRequest {
  string query = 1;
  string fields = 2;
  string order = 3;
  string sortby = 4;
  int64 limit = 5;
  int64 offset = 6;
}

message PostSomethingRequest {
  string id = 1;
  string name = 2;
  string age = 3;
}

message DefaultResponse {
  string message = 1;
  int64 code = 2;
  google.protobuf.Struct data = 3;
}

3. 初始化 go mod

go mod init my_demo

如图:

mod初始化.png

4. 生成代码

cd ~/goWork/truss_demo
truss ./demo.proto

执行完成后,会自动生成以下内容:

appledeMacBook-Pro:truss_demo apple$ truss ./demo.proto
appledeMacBook-Pro:truss_demo apple$ ls
demo.pb.go  demo.proto  go.mod      mydemo-service
appledeMacBook-Pro:truss_demo apple$ 

如图:

truss代码生成.png

结构图:

truss文件结构.png
结构说明
truss_demo
  |
    |--demo.proto // protobuf 文件
    |--demo.pb.go // RPC接口以及数据结构定义--自动生成
    |--mydemo-service
            |
            |--cmd
            |    |
            |    |--mydemo
            |        |- main.go // 入口 - 自动生成,除特殊情况不建议修改
            |
      |--handlers //业务逻辑--需要我们写代码的地方
      |    |
      |    |--handlers.go //实际业务逻辑
      |    |--hooks.go // 配置信息以及阻断处理
      |    |--middlewares.go //中间件
      |
      |--svc // 通讯协议以及客户端,自动生成,除特殊情况不建议修改
      |  |
      |  |--client // 客户端定义
      |  |   |
      |  |   |--grpc
      |  |   |  |--client.go
      |  |   |--http
      |  |      |--client.go
      |  |--server // 服务端定义
      |  |  |--run.go 
      |  |
      |  |-- config.go // 服务端口定义
      |  |-- endpoints.go //接口定义
      |  |-- transport_grpc.go // grpc 传输协议层
      |  |-- transport_http.go // http 传输协议层

4. 导入包

最后记得使用 go mod 导入依赖。

go mod tidy

如图:


mod_tidy.png

5. 运行

go run mydemo-service/cmd/mydemo/main.go

如图:


go_run.png

6. 打包编译

最终项目发布时需要打包为 Linux 可执行程序。

如下所示:

cd ~/goWork/truss_demo && \
mkdir -p build &&  \
GOARCH=amd64 CGO_ENABLED=0 GOOS=linux go build -o build/main mydemo-service/cmd/mydemo/main.go

最后会在当前目录创建 build 文件夹,同时在 build 文件夹下生成 main 程序。
启动 mian 程序: ./main 即可。

7. 访问测试

不指定端口情况下默认端口分别为:

http: 5050
rpc: 5040
debug: 5060

因为没有写业务逻辑,返回值为默认值:

postman 测试:


postman_test.png

curl 测试:

curl --location --request GET 'localhost:5050/my_demo_service/something' -w "\n"

结果如图:


curl_test.png

特殊情况

数据结构不确定

对于上面 protobuf 定义时,有一种特殊情况需要注意:请求数据结构不确定。

我遇到的情况是:
因为业务需求,需要我提供一个回调接口,用来接收三方程序执行过程信息,但是并不知道具体数据结构,在咨询过 truss 的开发人员后得知,这种情况需要特殊处理。

这时需要将 OPTIONPOST 分开处理:

重新编辑 demo.proto

vim ~/demo.proto

编辑后:

syntax = "proto3";
package demo;

import "github.com/metaverse/truss/deftree/googlethirdparty/annotations.proto";
import "google/protobuf/any.proto";
import "google/protobuf/struct.proto";

service MyDemo {

  // 获取
  rpc GetSomething (DefaultRequest) returns (DefaultResponse) {
    option (google.api.http) = {

      get: "/my_demo_service/something"

      additional_bindings {
        get: "/my_demo_service/something"
      }
    };
  }
  // 提交
  rpc PostSomething (PostSomethingRequest) returns (DefaultResponse) {
    option (google.api.http) = {
      custom {
        kind: "HEAD"
        path: "/my_demo_service/something"
      }
      additional_bindings {
        post: "/my_demo_service/something"
        body: "*"
      }
    };
  }
  // 特殊请求
  rpc SpecialPost (SpecialPostRequest) returns (DefaultResponse) {
    option (google.api.http) = {
      post: "/my_demo_service/special/{id}"
      body : "*"
    };
  }

  // 特殊请求
  rpc SpecialPostHEAD (Empty) returns (Empty) {
    option (google.api.http) = {
      custom {
        kind: "HEAD"
        path: "/my_demo_service/special/*"
      }
    };
  }
}


message Empty {}
message DefaultRequest {
  string query = 1;
  string fields = 2;
  string order = 3;
  string sortby = 4;
  int64 limit = 5;
  int64 offset = 6;
}

message PostSomethingRequest {
  string id = 1;
  string name = 2;
  string age = 3;
}


message SpecialPostRequest {
  string id = 1;
  google.protobuf.Any metadata = 2;
}

message DefaultResponse {
  string message = 1;
  int64 code = 2;
  google.protobuf.Struct data = 3;
}

重新生成代码

经过调整后 protobuf 文件发生变化,这时重新执行生成代码命令即可。

truss ./demo.proto

成功时返回:

appledeMacBook-Pro:truss_demo apple$ truss ./demo.proto
INFO[0000] Generating handler from rpc definition        Method=SpecialPost
INFO[0000] Generating handler from rpc definition        Method=SpecialPostHEAD

如图:

truss代码重生成.png

注意:重生成代码时,如果方法名称发生变化,会导致业务逻辑代码被删除

例如: 上例中 PostSomething 改为PostSomethings, 会导致原有与 PostSomething相关内容被删除,之后新创建 PostSomethings 相关方法。

其他

关于protobufmessage 定义特殊数据,protobuf 并不支持 golang 中的 interface 类型,具体如何接收/解析不确定数据将在下篇文章中介绍,上面其实也有提及,感兴趣的朋友可以先提前去看一下 google/protobuf/any.proto 以及 google/protobuf/structs.proto.

这次先介绍到这里,如有错误,欢迎留言指正。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 195,719评论 5 462
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 82,337评论 2 373
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 142,887评论 0 324
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,488评论 1 266
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 61,313评论 4 357
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,284评论 1 273
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,672评论 3 386
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,346评论 0 254
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,644评论 1 293
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,700评论 2 312
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,457评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,316评论 3 313
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,706评论 3 299
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 28,990评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,261评论 1 251
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,648评论 2 342
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,859评论 2 335

推荐阅读更多精彩内容