Siamo abituati con i web services in ASP.NET ad utilizzare (spesso incosapevolmente) l'XmlSerializer per serializzare/deserializzare le nostre istanze di classi nel messaggio SOAP. La caratteristica dell'XmlSerializer (fra le altre cose) è di serializzare i tipi primitivi come tipi XML Schema (definiti sotto il namespace http://www.w3.org/2001/XMLSchema). In Indigo, se definiamo il seguente contratto:

[ServiceContract(Namespace="http://Microsoft.ServiceModel.Samples")]
public interface ICalculator
{
    [OperationContract]
    double Add(double n1, double n2);
}

lo schema generato produrrà qualche cosa di veramente nuovo:

<xs:element name="Add">
  <xs:complexType>
    <xs:sequence>
      <xs:element name="n1" xmlns:q1="
http://schemas.microsoft.com/2003/10/Serialization/" type="q1:double" />
      <xs:element name="n2" xmlns:q2="
http://schemas.microsoft.com/2003/10/Serialization/" type="q2:double" />
    </xs:sequence>
  </xs:complexType>
</xs:element>

perchè è stato definito il tipo double (primitivo) sotto un'altro namespace ? In sostanza, by default, Indigo non usa l'XmlSerializer bensì l'XmlFormatter. L'XmlFormatter è un pò il successore del SoapFormatter (quindi può serializzare anche membri privati e protetti). Ha delle caratteristiche che lo rendono decisamente interessante, quali:

  • supporta le Hashtable (finalmente!)
  • supporta una serie di eventi OnDeserialized, OnSerialized, OnSerializing e OnDeserializing
  • permette di gestire sia l'accoppiamento debole (come fa l'XMLSerializer oggi) che forte (come fa il .NET Remoting oggi)
  • ....

Se è necessario mantenere una compatibilità massima con i tipi XSD (Xml Schema) allora è possibile forzare il ServiceContract ad utilizzare l'XmlSerializer aggiungendo un parametro nell'attributo:

[ServiceContract(Namespace="http://Microsoft.ServiceModel.Samples",
        FormatMode = ContractFormatMode.XmlSerializer)]
public interface ICalculator
{
    [OperationContract]
    double Add(double n1, double n2);
}

che produrrà

<xs:schema xmlns:tns="http://Microsoft.ServiceModel.Samples" elementFormDefault="qualified" targetNamespace="http://Microsoft.ServiceModel.Samples" xmlns:xs="http://www.w3.org/2001/XMLSchema">
 <xs:element name="Add">
  <xs:complexType>
   <xs:sequence>
    <xs:element minOccurs="1" maxOccurs="1" name="n1" type="xs:double" />
    <xs:element minOccurs="1" maxOccurs="1" name="n2" type="xs:double" />
   </xs:sequence>
  </xs:complexType>
 </xs:element>