【问题标题】:Compile protobuf to use primitive classes instead of well-known types编译 protobuf 以使用原始类而不是众所周知的类型
【发布时间】:2018-01-04 08:45:34
【问题描述】:

假设我有 test.proto 文件:

syntax = "proto3";

option java_package = "testing";
option java_outer_classname = "Test_v1";

import "google/protobuf/wrappers.proto";

message TestMessage {
    .google.protobuf.Int32Value integerField = 1;
}

如果我将其编译(使用 protoc v3.5.0)为 c# 代码,我将获得可为空的类型属性:

public int? IntegerField {
   get { return integerField_; }
   set { integerField_ = value; }
 }

但是如果我将它编译成 Java 代码,字段将是众所周知的类型:

public Builder setIntegerField(com.google.protobuf.Int32Value value) {
  if (integerFieldBuilder_ == null) {
    if (value == null) {
      throw new NullPointerException();
    }
    integerField_ = value;
    onChanged();
  } else {
    integerFieldBuilder_.setMessage(value);
 }

我正在将项目从 proto2 移动到 proto3,因此我想避免使用众所周知的类型,因为更改相关代码需要大量工作。对于 c# 项目,我不需要修改任何东西,但在 Java 中,我需要按照以下示例进行操作:

TestMessage.Builder builder = TestMessage.newBuilder();
builder.setIntegerField(5); //<-- instead of this with proto2
builder.setIntegerField(Int32Value.newBuilder().setValue(5)); //<-- I will need to do something like this with proto3

有没有办法将 proto 文件编译为 Java,以便设置器接受原始类/包装器(字符串、整数等)作为参数?

【问题讨论】:

    标签: java protocol-buffers protoc proto3


    【解决方案1】:

    这里的问题是缺少值时该怎么办。这不是int32(在.proto 中)的问题,因为(至少在proto3 中)int32 将始终存在(默认为0)。然而,.google.protobuf.Int32Value 是一个消息,因此它可能丢失代表一个值(可能为 0)。在 C# 中,这个概念可以通过 int?(可以是 null)巧妙地表示,但 Java 没有类似于 Nullable&lt;T&gt; 的概念。 Int32Value 封装了这一点,允许 null 引用。

    这么短的版本:不,(^^^) 这就是原因。

    我假设您实际上是在替换以前的东西:

    message TestMessage {
        optional int32 integerField = 1;
    }
    

    ???

    【讨论】:

    • 是的,你是对的。我将可选(在原型 2 中)替换为众所周知的类型(在原型 3 中)。我在 Java 方面不是很强,但据我所知,Java 土地 int 是原始的,而 Integer 是可以为空的包装器。所以我们在c# Nullable<int> might be the same as Integer in Java 中有什么。这就是为什么我期待看到Integer 而不是Int32Value。如果我将.proto 文件中的字段更改为oneof,我可以获得预期的结果,但不能使用oneofs
    • @Reniuz 是的,这是一个有效的观点 - 我可以看到 Integer 在那里会很好。我猜想实现它的人只是不想这样做,大概是为了更容易提供预期的message 功能,而不是必须特殊情况下的Integer
    • 我将问题发布到protobuf group 并得到了答案。 Functionality was already requested 问题仍然存在。谢谢您的回答。我会接受它,因为答案的简短版本是正确的:)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-03-15
    • 1970-01-01
    • 2020-09-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多