我正在定义一个ProtoBuf消息,我想要一个"可以为空"的字段 - 即,我想要区分具有值而没有值的字段.举一个具体的例子,假设我有"x"和"y"字段来记录某个对象的坐标.但在某些情况下,坐标是未知的.下面的定义将无法正常工作,因为如果x或y是不确定的,那么他们默认为零(这是一个有效的值):
message MyObject {
optional float x = 1;
optional float y = 2;
}
Run Code Online (Sandbox Code Playgroud)
一种选择是添加一个布尔字段,记录相应字段的值是否已知.即:
message MyObject {
optional bool has_x = 1; // if false, then x is unknown.
optional bool has_y = 2; // if false, then y is unknown.
optional float x = 3; // should only be set if has_x==true.
optional float y = 4; // should only be set if has_y==true.
}
Run Code Online (Sandbox Code Playgroud)
但这会增加一些额外的簿记 - 例如,当我设置x字段的值时,我必须始终记住也设置has_x.另一种选择是使用列表值,其中列表总是长度为0或长度为1:
message MyObject {
repeated float …Run Code Online (Sandbox Code Playgroud) 我目前正在使用Google Protocol Buffers的 v3.0.0-alpha-2 .
据我所知,v3删除了required关键字,extensions
字段的关键字和默认值,以简化原型语言.
我不明白的是optionalproto3中关键字的含义.
例:
syntax = "proto3";
package fw.example;
message ExampleMessage {
optional string optional_string = 1;
string normal_string = 2;
}
Run Code Online (Sandbox Code Playgroud)
问:是什么区别optional_string和normal_string
除了名称和标记?
我已经阅读了以下资源(它们似乎是protobuf v3的唯一公开版本):
但他们甚至没有提到optional关键字.
optional在proto3过时,因为现场始终是可选的?required?似乎在proto3中,人们不能再将未设置的字段和客户端设置的字段区分为(隐式)默认值.
最好的做法是将每个proto3消息包装在特定于语言的类中吗?我正在使用C++,我需要确保设置特定的字段.与proto2相比,现在似乎必须在语言特定的源代码中手动完成验证.
有人可以启发我,对proto3消息应用约束但允许方案演变的最佳方法是什么?目前我认为必须围绕proto3消息编写新的API,以便客户端不直接处理proto3生成的代码,而是使用自定义API代码.那是对的吗?
也许有人可以给我一个具体的例子来讨论.
我很困惑,因为v3的发行说明中说明了以下内容:
我们建议新的Protocol Buffers用户使用proto3.但是,由于API不兼容,我们通常不建议现有用户从proto3迁移proto2,并且我们将继续支持proto2很长一段时间.
如果proto3是要走的路,为什么事情变得复杂?在我看来,我现在需要编写比proto2更多的代码.
有人解释我如何处理 google protobuf 中的空值。
我有这样的结构:
syntax = "proto3";
import "google/protobuf/wrappers.proto";
message Person {
google.protobuf.DoubleValue age = 4;
}
Run Code Online (Sandbox Code Playgroud)
和java代码:
DoubleValue myAge = null;
Person build = Person.newBuilder()
.setAge(myAge) // <- NPE
.build();
Run Code Online (Sandbox Code Playgroud)
此代码导致.setAge(myAge)在线出现空指针异常。
那么 protobuf DoubleValue 的用例是什么?我以为它是用来管理空值的。但仍然收到 NullPointerException 。
您使用这样的代码来处理这个问题吗?
DoubleValue a = null;
Person.Builder builder = Person.newBuilder();
if (a != null) {
builder.setAge(a);
}
Person build = builder.build();
Run Code Online (Sandbox Code Playgroud)
更新:
这是 protoc 命令生成的代码的一部分:
/**
* <code>.google.protobuf.DoubleValue age = 9;</code>
*/
public Builder setAge(com.google.protobuf.DoubleValue value) {
if (ageBuilder_ == …Run Code Online (Sandbox Code Playgroud) I am running into a bit of a problem with Protoc and my existing struct that contains nullable string fields.
The struct I am trying to serialize for transmission contains a bunch of fields that are nullable in json (so we can distinguish between null, "" and a set value).
type Message struct {
Path *string `json:"path"`
}
Run Code Online (Sandbox Code Playgroud)
So if a user sends a empty json string {} the Path will be nil and not "", whereas {"path":""} …
我想使用 Enum 或类似方法为我的 gRPC 服务器定义这样的路由器或映射
我有一个名为 ServerHubService 的简单服务和一个 Hubs 文件夹,其中包含一些类,这些类将处理客户端将传递到我的 gRPC 服务器的每个请求
这是我的项目的屏幕 截图, 现在可以在照片中看到该文件的内容也是 HubMap.cs下面的图像
正如你所看到的,我想定义一个 switch case 语句来运行不同的类
这是我的 ServiceHubService gRPC 类 ServerHubService.cs
最后这是我的客户端调用grpc-client.cs
视觉工作室 2019 版本 16.10
这是我的 ServerHub.proto 文件:
syntax = "proto3";
option csharp_namespace = "NetPlus.Server.Core";
package server;
service ServereHub {
rpc ActionManager (ActionRequest) returns (ActionResult);
}
message ActionRequest {
string ActionType = 1;
}
message ActionResult {
string ActionResultType = 1;
}
Run Code Online (Sandbox Code Playgroud)
我的 ServerHubService.cs :
using Microsoft.Extensions.Logging;
using NetPlus.Server.Core;
using System;
using System.Collections.Generic;
using …Run Code Online (Sandbox Code Playgroud)