What is the API to know the kind of protobuf Message is being sent?
For example I use the following to get the SendNameMessage object.
SendNameMessage sendNameObj = Serializer.DeserializeWithLengthPrefix< SendNameMessage>(stream, PrefixStyle.Fixed32);
How does a listener know what kind of message is being sent?
The following is my SendNameMessage class:
[ProtoContract]
cl开发者_开发问答ass SendNameMessage
{
[ProtoMember(1)]
public string sendName { get; set; }
[ProtoMember(2)]
public int sendId { get; set; }
}
How do I know if the message being sent is sendName or sendId?
protobuf (under any implementation) is just the serialization API. When talking on the wire, the default is that both ends already agree what the data is. For sending different types of messages, a few options present themselves:
- have a wrapper object that simply has child objects to represent different message types. With protobuf-net specifically you can also map this directly to inheritance (since protobuf-net maps inheritance to encapsulation)
- use a message header - some kind of data before your message that identifies this. In particular, if using the
Base128
prefix-style, you can include a field number that is sent with the message (it defaults to1
, but an overloaded method allows you to specify this). You would then deserialize this viaSerializer.NonGeneric.TryDeserializeWithLengthPrefix
which includes a delegate parameter to perform type resolution from the field number.
After the edit... you mention sendId
and sendName
, but the message is SendNameMessage
. It will always be everything (except defaults) in that message. It could be both. It could be neither. So in that scenario, you would just deserialize it and check .sendName
and .sendId
.
Another common option here is to add a discriminator, perhaps simply an enum:
enum MesageType {
Error = 0,
Name = 1,
Id = 2
}
and include that on the message:
[ProtoMember(10)]
public MessageType MessageType {get;set;}
Now you have an explicit way of expressing your meaning of message-type.
精彩评论