定义protobuf消息字段的自定义go结构标签

时间:2018-08-13 18:51:48

标签: go protocol-buffers grpc

我是grpc的新手,并一直试图从网络服务器获取json的响应。然后,存根可以从json服务器请求rpc

在我的.proto文件中,我创建了一种消息类型:

message Post {
    int64 number = 1;
    string now = 2;
    string name = 3;
}

但是我无法整理number字段,因为protoc生成带有pb.go标签的结构number文件:

{
        "no": "23",
        "now": "12:06:46",
        "name": "bob"
}

如何强制Message使用消息字段的小写字母以外的标签进行“转换”?例如使用json标签no,即使Message中的字段名称为number

2 个答案:

答案 0 :(得分:2)

您可以使用json_name

在原型消息定义上设置proto3字段选项。
message Post {
    int64 number = 1 [json_name="no"];
    string now = 2;
    string name = 3;
}

link to the docs

答案 1 :(得分:0)

import "github.com/gogo/protobuf/gogoproto/gogo.proto";

// Result example:
// type Post struct {
//    Number int64 `protobuf:"bytes,1,opt,name=number,json=no1,proto3" json:"no2"`
// }
message Post {
    int64 number = 1 [json_name="no1", (gogoproto.jsontag) = "no2"];
}

,其中:

  • 否1 - jsonpb 编组/解组
  • 的新名称
  • no2 - json 编组/解组
  • 的新名称

jsonpb示例:

import (
    "bytes"
    "testing"
    "encoding/json"

    "github.com/golang/protobuf/jsonpb"
    "github.com/stretchr/testify/require"
)

func TestJSON(t *testing.T) {
    msg := &Post{
        Number: 1,
    }

    buf := bytes.NewBuffer(nil)

    require.NoError(t, (&jsonpb.Marshaler{}).Marshal(buf, msg))
    require.Equal(t, `{"no1":1}`, buf.String())

    buf.Truncate(0)

    require.NoError(t, json.NewEncoder(buf).Encode(msg))
    require.Equal(t, `{"no2":1}`, buf.String())
}

有关protobuf extensions的更多信息