views:

494

answers:

1

I am using wsdl.exe to auto generate the web service proxy code from a huge wsdl file. I then take the .cs file it generates compile it to a dll and use it in my program to make web service calls.

The problem is that when using sql session state in my program I can not save the proxxy object to session state. I marked the main class in the wsdl.exe generated file serializable, but it doesnt matter since it inherits System.Web.Services.Protocols.SoapHttpClientProtocol which is not serializable?

Does anyone know of a way to have the autogenerated code work with session state?

+1  A: 

Typically, you would serialize state (entities), not the WSDL service wrapper. Most code-gen since 2.0 will write files as partial classes, which means you can add a second code file to add things like attributes:

namespace MyNamespace
{
    [Serializable] partial class Customer {}
    [Serializable] partial class Order {}
    [Serializable] partial class Address {}
}

This is combined with the other half in the wsdl-generated types, and should make it usable from BinaryFormatter - however, personally I suspect that is a bad way to do it. Since you are using wsdl.exe, your types are already serializable via XmlSerializer. Instead of serializing them with BinaryFormatter (which is what will be used by default, and which is very brittle), consider serializing them via XmlSerializer to a string or a byte[], and add that to session-state. This will work without extra code changes, and is a lot more robust as it avoids the multiple brittle points of BinaryFormatter.

For example:

static string SerializeXml<T>(T obj) where T : class
{
    if (obj == null) return null;
    StringWriter sw = new StringWriter();
    using (XmlWriter xw = XmlWriter.Create(sw))
    {
        new XmlSerializer(typeof(T))
            .Serialize(xw, obj);
    }
    return sw.ToString();
}
static T DeserializeXml<T>(string xml) where T : class
{
    if (xml == null) return null;
    using (XmlReader xr = XmlReader.Create(new StringReader(xml)))
    {
        return (T)new XmlSerializer(typeof(T))
            .Deserialize(xr);
    }
}
Marc Gravell
Thanks for the very detailed post and sample code, it put me on the right track. :)
Aros