I have a wcf service written in a contract-first fashion. As some of the elements in the schema uses attributes, I had to create a custom serialization for this (using IXmlSerializable
). Below is a snippet of the schema, and the classes, as well as the schema from the wsdl output.
My problem is that even though I render the xsd for my IXmlSerializable classes, the schema is not included in the wsdl. They are just referenced with processContents="lax"
. This seems to be a problem for consumers of my services, as they can not use their wizards to create clients.
Has anyone encountered this problem? Is there anyway to control the wsdl output to avoid this. I experience the same behaviour using both message contracts and data contracts.
The schema for collection and item:
<xs:element name="TelephoneList">
<xs:complexType>
<xs:sequence>
<xs:element ref="Telephone" maxOccurs="unbounded"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="Telephone">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attribute name="Type">
<xs:simpleType>
<xs:restriction base="xs:NMTOKEN">
<xs:enumeration value="Preferred"/>
<xs:enumeration value="Office"/>
<xs:enumeration value="Mobile"/>
<xs:enumeration value="Home"/>
<xs:enumeration value="MobilePhoneFromExternalPartner"/>
<xs:enumeration value="HomePhoneFromExternalPartner"/>
</xs:restriction>
</xs:simpleType>
</xs:attribute>
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
The collection class:
[CollectionDataContract(ItemName = "Telephone", Name = "TelephoneList", Namespace = Schema.WorkOrderNamespace)]
public class TelephoneSet : SetBase<Telephone>
{ }
The item class:
[XmlSchemaProvider("GetSchemaFile")]
public class Telephone : CustomSerializedEntity //The base class implements IXmlSerializable
{
public virtual TelephoneType? Type { get; set; }
public virtual string Number { get; set; }
/// <remarks>This method is referenced in the <seealso cref="XmlSchemaProviderAttribute"/> decoration.</remarks>
public static XmlSchemaComplexType GetSchemaFile(XmlSchemaSet xs)
{
return CreateSchema(xs, "Telephone");
}
public override void ReadXml(XmlReader reader)
{
Type = ReadEnumAttribute<TelephoneType?>(reader, "Type");
reader.MoveToElement();
Number = reader.Value;
}
public override void WriteXml(XmlWriter writer)
{
WriteAttribute(writer, "Type", Type);
if (!string.IsNullOrEmpty(Number))
{
writer.WriteValue(Number);
}
}
}
The xsd rendered by the service:
<xs:complexType name="TelephoneList">
<xs:sequence>
<xs:element minOccurs="0" maxOccurs="unbounded" name="Telephone" nillable="true">
<xs:complexType>
<xs:sequence>
<xs:any minOccurs="0" processContents="lax"/>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
</xs:complexType>
<xs:element name="TelephoneList" nillable="true" type="tns:TelephoneList"/>