C++ JsonStringToMessage with nested Any message

22 views
Skip to first unread message

Justin Lynch

unread,
Sep 24, 2020, 5:40:31 PM9/24/20
to Protocol Buffers
I hit a roadblock trying to parse out a nested message. I have found a workaround, but I'd like to get to the bottom of this.

I have a .proto file like this:

```syntax = "proto3";

import "google/protobuf/descriptor.proto";
import "google/protobuf/any.proto";

package Test2;

message Subscription {
google.protobuf.FileDescriptorSet descriptor_set = 1;
string name = 2;
int32 interval = 3;
}

message AnotherMsg {
google.protobuf.FileDescriptorSet descriptor_set = 1;
string test = 2;
}

enum msg_id {
UNSPECIFIED = 0;
SUBSCRIBE = 1;
}

message WSMessage{
msg_id req_id = 1;
google.protobuf.Any msg_body = 2;
google.protobuf.FileDescriptorSet descriptor_set = 3;
}

message WSReceivedMessage {
repeated WSMessage message = 1;
google.protobuf.FileDescriptorSet descriptor_set = 2;

}```

WSMessage has an ID, and a message.  The documentation indicates JsonStringToMessage "It will use the DescriptorPool of the passed-in message to resolve Any types."

Now, I haven't been able to find any member data or member function of Message that allows access to a DescriptorPool. I see access to descriptors...

I even went down the rabbit hole of using the "Parser" with input from the Tokenizer to read the descriptor.proto file:

```std::fstream myFile;
myFile.open("descriptor.proto");
google::protobuf::io::IstreamInputStream realFileInput(&myFile);
google::protobuf::io::IstreamInputStream* myFileInput = &realFileInput;
myCollector realCollector{};
myCollector* collector = &realCollector;
google::protobuf::io::Tokenizer myTkn(myFileInput, collector);
google::protobuf::compiler::Parser myParser{};
google::protobuf::FileDescriptorProto myProto;
myParser.Parse(&myTkn, &myProto);```

From this parser, I obtained my FileDescriptorProto, which I then used in a DescriptorPool:

```google::protobuf::DescriptorPool myPool{};
myPool.BuildFile(myProto);```

Next I tried to use the DynamicMessageFactory to create a message that would contain the whole DescriptorPool of messages in my main .proto file.

This is where I hit the roadblock. There is no single descriptor, or converter from a descriptor pool to a descriptor. The DynamicMessageFactory creates a message from a single descriptor.

I can just simply declare a single message. My issue is I'm looking to have a message with a descriptor pool (or some sort of descriptor) that contains the possibilities for my "Any" message.

The documentation seems incorrect to me. util::Status util::JsonStringToMessage(
        StringPiece input,
        Message * message,
        const JsonParseOptions & options)

Converts from JSON to protobuf message.

This is a simple wrapper of JsonStringToBinary(). It will use the DescriptorPool of the passed-in message to resolve Any types.


There doesn't appear to be a "DescriptorPool" for a message. What am I missing? Thanks very much for your help.

Reply all
Reply to author
Forward
0 new messages