我正在创建一个Web服务的客户端,它或多或少不受我的控制。
<xs:complexType name="A">
<xs:sequence>
<xs:element minOccurs="0" maxOccurs="1" name="element1" type="xs:string" />
<xs:element minOccurs="0" maxOccurs="1" name="element2" type="xs:string" />
</xs:sequence>
</xs:complexType>
<xs:complexType name="B">
<xs:complexContent>
<xs:restriction base="A">
<xs:sequence>
<xs:element minOccurs="1" maxOccurs="1" name="element2" type="xs:string" />
</xs:sequence>
</xs:restriction>
</xs:complexContent>
</xs:complexType>
简言之,我们有一个包含所有元素的对象A,服务有几个基于A的类型,但有一些限制,因此继承的类型通常比基类型小--这里以类型B为例。
在架构查看器(如Visual Studio 2010、SoapUI等)中,这看起来与预期一致。A有2个元素,而B只有1个(=元素2)。
通过使用svcutil,我得到了类型A和B中的完整元素集,或者在使用选项时,我得到了如下错误消息:
错误:无法导入命名空间“http://tempuri.org/XMLSchema.xsd”中的类型“B”。不支持通过限制派生的复杂类型。请更改架构以便这些类型可以Map到数据协定类型,或者使用ImportXmlType或使用其他序列化程序。
在继承的类型中隐藏字段/属性不是我喜欢的做法/道路,但如果我不能让提供程序更改WSDL,似乎我必须这样做。
是否有替代svcutil的方法可以正确处理此问题,或者我是否必须手动编写代理代码?
更新1
正如John Saunders所指出的,我没有展示svcutil的建议的结果。这部分是为了保持文章简短......但这里有:
svcutil schema.xsd /importXmlTypes /datacontonly结果为:
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.Runtime.Serialization", "4.0.0.0")]
[System.Runtime.Serialization.DataContractAttribute(Name="A", Namespace="http://tempuri.org/XMLSchema.xsd")]
public partial class A : object, System.Runtime.Serialization.IExtensibleDataObject
{
private System.Runtime.Serialization.ExtensionDataObject extensionDataField;
private string element1Field;
private string element2Field;
public System.Runtime.Serialization.ExtensionDataObject ExtensionData
{
get
{
return this.extensionDataField;
}
set
{
this.extensionDataField = value;
}
}
[System.Runtime.Serialization.DataMemberAttribute(EmitDefaultValue=false)]
public string element1
{
get
{
return this.element1Field;
}
set
{
this.element1Field = value;
}
}
[System.Runtime.Serialization.DataMemberAttribute(EmitDefaultValue=false)]
public string element2
{
get
{
return this.element2Field;
}
set
{
this.element2Field = value;
}
}
}
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.CodeDom.Compiler.GeneratedCodeAttribute("System.Runtime.Serialization", "4.0.0.0")]
[System.Xml.Serialization.XmlSchemaProviderAttribute("ExportSchema")]
[System.Xml.Serialization.XmlRootAttribute(IsNullable=false)]
public partial class B : object, System.Xml.Serialization.IXmlSerializable
{
private System.Xml.XmlNode[] nodesField;
private static System.Xml.XmlQualifiedName typeName = new System.Xml.XmlQualifiedName("B", "http://tempuri.org/XMLSchema.xsd");
public System.Xml.XmlNode[] Nodes
{
get
{
return this.nodesField;
}
set
{
this.nodesField = value;
}
}
public void ReadXml(System.Xml.XmlReader reader)
{
this.nodesField = System.Runtime.Serialization.XmlSerializableServices.ReadNodes(reader);
}
public void WriteXml(System.Xml.XmlWriter writer)
{
System.Runtime.Serialization.XmlSerializableServices.WriteNodes(writer, this.Nodes);
}
public System.Xml.Schema.XmlSchema GetSchema()
{
return null;
}
public static System.Xml.XmlQualifiedName ExportSchema(System.Xml.Schema.XmlSchemaSet schemas)
{
System.Runtime.Serialization.XmlSerializableServices.AddDefaultSchema(schemas, typeName);
return typeName;
}
}
在XML级别上工作是不可取的,这将迫使我们编写一个 Package 器。从getgo手工编写代理更容易。
svcutil schema.xsd /serializer:XmlSerializer /datacontonly给出下面的错误,这也是我要求使用替代工具的原因。
svcutil schema.xsd /序列化程序:XmlSerializer /数据压缩程序错误:无法导入命名空间“http://tempuri.org/XMLSchema.xsd”中的类型“B”。不支持通过限制派生的复杂类型。请更改架构以便这些类型可以Map到数据协定类型,或者使用ImportXmlType或使用其他序列化程序。
如果使用/dataContractOnly选项导入数据协定类型并收到此错误消息,请考虑改用xsd.exe。在服务协定上应用XmlSerializerFormatAttribute特性后,可以在Windows Communication Foundation中使用xsd.exe生成的类型。或者,请考虑使用/importXmlTypes选项将这些类型作为XML类型导入,以便与服务协定上的DataContractFormatAttribute属性一起使用。
使用xsd schema.xsd /c给出一个继承A而不隐藏element 1的类型B:
[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.0.30319.1")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(Namespace="http://tempuri.org/XMLSchema.xsd")]
[System.Xml.Serialization.XmlRootAttribute("request", Namespace="http://tempuri.org/XMLSchema.xsd", IsNullable=false)]
public partial class B : A {
}
/// <remarks/>
[System.Xml.Serialization.XmlIncludeAttribute(typeof(B))]
[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "4.0.30319.1")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(Namespace="http://tempuri.org/XMLSchema.xsd")]
public partial class A {
private string element1Field;
private string element2Field;
/// <remarks/>
public string element1 {
get {
return this.element1Field;
}
set {
this.element1Field = value;
}
}
/// <remarks/>
public string element2 {
get {
return this.element2Field;
}
set {
this.element2Field = value;
}
}
}
1条答案
按热度按时间oyxsuwqo1#
错误消息会告诉您使用
/importXmlTypes
参数,或变更为使用XmlSerializer。从说明:/importXmlTypes -将数据协定序列化程序配置为将非数据协定类型作为IXmlSerializable类型导入。
和
/serializer:XmlSerializer -生成使用XmlSerializer进行序列化与反序列化得数据类型