[ACCEPTED]-What does the ProtoInclude attribute mean (in protobuf-net)-protobuf-net

Accepted answer
Score: 28

Sorry, I didn't mean to miss this one - alas, I 38 don't see everything.

Given the specifics 37 in the question, I'm going to assume that 36 you are at least passingly familiar with 35 .proto; correct me if I am wrong.

[ProtoInclude] works 34 a lot like [XmlInclude] for XmlSerializer - or [KnownType] for DataContractSerializer - it allows 33 it to recognise subclasses of a type during 32 (de)serialization. The only additional thing 31 is that it needs a tag (number) to identify 30 each sub-type (that must be unique, and 29 not clash with any of the fields from the 28 parent type).

Re protogen: nope; the underlying 27 spec (by google) makes no provision for 26 inheritance at all, so protogen (via .proto) has 25 no mechanism to express this. protobuf-net 24 provides inheritance support as an extension, but 23 does it in a way that still leaves the messages 22 wire-compatible with the other implementations. At 21 a push, maybe I could add protogen support via 20 the new extension properties in the google 19 spec, but I haven't done this yet.

So; to 18 look at the example; that expresses an inheritance 17 relationship between BaseMessage and BeginRequest; regardless of 16 whether you do:

  • either way, it will start at the base (BaseMessage) and work upwards; which isn't exactly true - it writes the data starting with BeginRequest (so that it knows we have a BeginRequest as early as possible during deserialization). The important thing is that the fields from any parent contract types is included, and the serializer looks at the actual object passed in - not just the type you say it is.

Likewise, during deserilaization, regardless 15 of whether you use:


you will get the type 14 you actually serialized (presumably a BeginRequest).

Under 13 the bonnet, for compatibility purposes (with 12 the wide protocol buffers specification), this 11 is similar to writing something like (forgive 10 any errors, my .proto is rusty):

message BaseMessage {
    optional BeginRequest beginRequest = 50;
    optional uint32 messageType = 1;   
message BeginRequest {        

(the override 9 probably shouldn't specify [ProtoMember], btw.

Normally, it 8 would write fields in ascending tag order, but 7 to make for efficient deserialization the 6 engine cheekily chooses to write the subclass 5 data first (which is explicitly allowed by the 4 spec) - i.e. it writes something like (you'll 3 have to imagine the binary...):

[tag 50, string][length of sub-message][body of sub-message][tag 1, int][value]

(in this 2 case, the body of the sub-message is empty)

Does 1 that cover it?

More Related questions