In a local structure with messages passed in XML via pub / sub, I need to be able to consume several messages, however, all messages are accepted as plain text and must be deserialized into objects created by the Xsd tool.
The messages themselves are all derived from the base MessageType element / object, but if I deserialize based on this like this:
XmlSerializer serializer = new XmlSerializer (typeof (MessageType));
XmlReader reader = XmlReader.Create (new StringReader (rawMessage));
MessageType message = (MessageType) serializer.Deserialize (reader);
I get an error that the actual element type ("UpdateParameter" say) was not expected.
For now, the only solution I can come up with is to use the switch statement:
XmlReader reader = XmlReader.Create (new StringReader (upString));
reader.MoveToContent ();
switch (reader.LocalName.ToLower ())
{
case "updateparameter":
serializer = new XmlSerializer (typeof (UpdateParameter));
doStuff ((UpdateParameter) serializer.Deserialize (xml));
break;
case "updateparameterresponse":
serializer = new XmlSerializer (typeof (UpdateParameterResponse));
doStuff ((UpdateParameterResponse) serializer.Deserialize (xml));
break;
case "UpdateStatusResponse":
serializer = new XmlSerializer (typeof (UpdateStatusResponse));
doStuff ((UpdateStatusResponse) serializer.Deserialize (xml));
break;
//...etc. Repeat for all possible elements
} But I really would not do this if there is an elegant solution. I wanted to do something like
Type rootType = Type.GetType (reader.localName); // could work if name is right
serializer = new XmlSerializer (typeof (rootType)); // would work
doStuff ((rootType) serializer.Deserialize (xml)); // won't work
But, as noted in the comments, this does not work, at least because you cannot use a type variable to convert. In addition, while the localName of the xml elements matches the local name of Object, the method described above requires (as I understand it) a qualified assembly name, which is another beast. Note that the ideal case would be to overload the doStuff method.
Is there an elegant solution that I am missing? Or at least a solution that is not related to infinite switch statements?