3

I'd like to have a base class that implements the majority of this example, and inherit for the parts that differ. All messages are the same except for the message node, which can be very different. Anyone know how to do this?

[XmlRoot("Package")]
public class Package
{
    [XmlElement("Parameters")]
    public parameters Parameters;
    public class parameters
    {
        [XmlElement("MessageType")]
        public string MessageType { get; set; }

        [XmlElement("CreationDateTime")]
        public string CreationDateTime { get; set; }

        //etc...
    }

    [XmlElement("Message")]
    public message Message;
    public class message
    {
        // here I want different message types
        // hopefully through inheritance
    }
}

For example, I want this sometimes...

<Package>
    <Parameters>
        <MessageType></MessageType>
        <CreationDateTime></CreationDateTime>
        <MessageId></MessageId>
    </Parameters>
    <Message>
        <MessageTypeRequest>
            <etc1></etc1>
            <etc2></etc2>
        </MessageTypeRequest>
    </Message>
</Package>

... but I want this at other times.

<Package>
    <Parameters>
        <MessageType></MessageType>
        <CreationDateTime></CreationDateTime>
        <MessageId></MessageId>
    </Parameters>
    <Message>
        <MessageTypeResponse>
            <etc1></etc1>
            <etc2></etc2>
        </MessageTypeResponse>
    </Message>
</Package>

3 Answers 3

1

If you have a class

public class Message { }

then you can create new message types by inheriting from them (of course you know that part):

public class Request : Message { ... }  
public class Response : Message { ... }

Now if you want to be able to assign instances of those classes to your property Package.Message and want them to be serialized correctly, you have to include those inherited types via attributes:

[XmlInclude(typeof(Request))]
[XmlInclude(typeof(Response))]
public class Package { ... }

The resulting Xml would look a bit different though, but it has the same meaning:

<Message d3p1:type="Request" xmlns:d3p1="http://www.w3.org/2001/XMLSchema-instance">
...
</Message>
Sign up to request clarification or add additional context in comments.

Comments

1

Thank you Botz3000 for your reply, and your hints helped.

I'm going with this, which produces the exact results. Although I would have preferred that the base class had no knowledge of the classes that consumed it. Here's the code:

[XmlRoot("Package")]
public class Package
{
    public Package() { }
    public Package(MessageTypeRequest req)
    {
        Message = new message();
        Message.requestMessage = req;
    }
    public Package(MessageTypeResponse resp)
    {
        Message = new message();
        Message.responseMessage = resp;
    }

    [XmlElement("Parameters")]
    public parameters Parameters;
    public class parameters
    {
        [XmlElement("MessageType")]
        public string MessageType { get; set; }

        [XmlElement("CreationDateTime")]
        public string CreationDateTime { get; set; }
    }

    [XmlElement("Message")]
    public message Message;
    public class message
    {
        [XmlElement("MessageTypeRequest")]
        public MessageTypeRequest requestMessage { get; set; }

        [XmlElement("MessageTypeResponse")]
        public MessageTypeResponse responseMessage { get; set; }
    }
}

public class MessageTypeRequest : Package
{
    public MessageTypeRequest()
    {
        etc1 = "A simple request.";
        etc2 = "test 2";
    }

    [XmlElement("etc1")]
    public string etc1 { get; set; }

    [XmlElement("etc2")]
    public string etc2 { get; set; }
}

public class MessageTypeResponse : Package
{
    public MessageTypeResponse()
    {
        etc1 = "My simple response";
        etc2 = "test 2";
    }

    [XmlElement("etc1")]
    public string etc1 { get; set; }

    [XmlElement("etc2")]
    public string etc2 { get; set; }
}

Comments

0

As it turns out, after adding more properties to my message classes, the serialization began to serialize the xml file incorrectly including items in the base class in the derived class as well... this is what fixed the problem:

[XmlRoot("Package")]
public class Package
{
    public Package() { }
    public Package(MessageContent messageContent)
    {
        Message = new message();
        Message.messageContent = messageContent;
    }

    [XmlElement("Parameters")]
    public parameters Parameters;
    public class parameters
    {
        [XmlElement("MessageType")]
        public string MessageType { get; set; }

        [XmlElement("CreationDateTime")]
        public string CreationDateTime { get; set; }
    }

    [XmlElement("Message")]
    public message Message;
    public class message
    {
        [XmlElement(Type = typeof(MessageTypeRequest)), XmlElement(Type = typeof(MessageTypeResponse))]
        public MessageContent messageContent { get; set; }
    }
}

public class MessageContent { }

public class MessageTypeRequest : MessageContent
{
    public MessageTypeRequest()
    {
        etc1 = "A simple request.";
        etc2 = "test 2";
    }

    public static Package MessageRequest()
    {
        return new Package(new MessageTypeRequest());
    }

    [XmlElement("etc1")]
    public string etc1 { get; set; }

    [XmlElement("etc2")]
    public string etc2 { get; set; }
}

public class MessageTypeResponse : MessageContent
{
    public MessageTypeResponse()
    {
        etc1 = "My simple response";
        etc2 = "test 2";
    }

    public static Package MessageRequest()
    {
        return new Package(new MessageTypeResponse());
    }

    [XmlElement("etc1")]
    public string etc1 { get; set; }

    [XmlElement("etc2")]
    public string etc2 { get; set; }
}

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.