3

I am using Google Protocol Buffers to send a message to a server. My confusion comes in about how I send an image vs how I receive the image. See code below for details but my question is:

Do I need to base64_decode the returned string that has never been base64 encoded, because it was sent using char * and size? Perhaps Google Protocol Buffers handles this but I can't find any evidence in the generated class.

I may have found the answer here but I want to be sure.


Here is the code to send the data. Clearly I am sending an unsigned char * and a const long unsigned int to set the image.

std::string message::myMessaging::generateMessage(unsigned char *imageData, const long unsigned int elemSize, long unsigned int *msgSize)
{
    ImageMessage message;
    message.set_ismaster(true);
    message.set_personname("Lucy");
    message.set_image(imageData, elemSize);

    string out;
    message.SerializeToString(&out);
    int size = message.ByteSize();
    memcpy(msgSize, &size, sizeof(int));
    return out;
}

Here is the code to receive the data. Coming back from the server I receive the messageData as a const string. I create my Google Protocol Buffer message and parse it to get the information out of it. Here, my image is a string.

std::string message::myMessaging::parseMessage(const string messageData, long unsigned int *msgSize)
{
    ImageMessage message;
    message.Clear();
    message.ParseFromString(messageData);

    string personname = message.personname();
    string image = message.image();

    // do I need to decode it ?
    std::string decoded = base64_decode(image);

    // or can I just return the string image ?
    return decoded;
}
Community
  • 1
  • 1
Patricia
  • 5,019
  • 14
  • 72
  • 152

1 Answers1

6

No, you do not need to base64 decode. The image field should have type bytes in your .proto file, so you're allowed to put arbitrary bytes in it without encoding.

Note that a C++ std::string is allowed to contain arbitrary bytes, not just text. Just make sure that you use image.size() and image.data() to access the contents. Do not use image.c_str() as that is for text strings, and definitely do not use strlen() or any other C string function on the image data.

Also:

 int size = message.ByteSize();

You can delete this line and just use out.size() instead. If you call ByteSize(), protobufs has to recompute the size of the whole message because it doesn't know if you've changed it.

Kenton Varda
  • 41,353
  • 8
  • 121
  • 105