ASMX服务KnownType属性不生效,存储的自定义类型未被引用问题求助
ASMX服务Data字段存储自定义类型未生成契约的解决方案
问题根因
你的Table类中Data字段声明为List<List<object>>类型,序列化器无法自动推断object中可能存储的自定义类型,因此不会将这些类型写入WSDL schema,导致客户端代理生成时缺少对应类,手动定义的类因命名空间/序列化标记不匹配会触发异常。
解决方案步骤
1. 正确配置KnownType(DataContractSerializer场景,WCF/支持DataContract的ASMX)
你之前KnownType未生效是因为挂载位置错误,需要将所有自定义类型的KnownType标记到包含object类型字段的父数据契约上,也就是Table类:
[DataContract] [KnownType(typeof(Email))] [KnownType(typeof(Strings))] // 后续新增的存储在Data中的自定义类型都在此处声明 public class Table { [DataMember] public string Name { get; set; } [DataMember] public List<Column> Columns { get; set; } [DataMember] public List<List<object>> Data { get; set; } }
2. 修正自定义类型的序列化标记
- 给所有自定义类加上完整的DataContract标记,且必须提供无参构造函数(序列化必备)
- 派生自集合的自定义类型需要用
CollectionDataContract标记,否则不会被识别为数据契约
// 修正Email类 [DataContract] public class Email { [DataMember] public string address { get; set; } // 新增无参构造 public Email() { } } // 修正Strings集合类 [CollectionDataContract] public class Strings : List<string> { public Strings(IEnumerable<string> collection) : base(collection) { } // 新增无参构造 public Strings() { } }
3. 原生ASMX服务(使用XmlSerializer)的特殊适配
如果你用的是传统.NET Framework ASMX服务,默认不支持DataContractSerializer,需要改用XmlInclude标记:
- 将所有自定义类型的XmlInclude标记挂载到服务方法上
- 自定义类可以改用Serializable或XmlType标记
[WebService] public class DbService : WebService { [WebMethod] [XmlInclude(typeof(Email))] [XmlInclude(typeof(Strings))] // 所有返回Data/Table/DataBase的方法都要加上述XmlInclude标记 public DataBase GetDbInfo(string dbName) { // 业务实现 } }
4. 客户端侧适配
更新服务引用后,不要手动定义同名类,直接使用代理自动生成的类型即可。如果需要服务端客户端复用类型,可将自定义类放到独立共享类库中,服务端和客户端都引用该类库,同时在服务引用配置中开启「重用引用程序集中的类型」选项。
内容的提问来源于stack exchange,提问作者Faith Li'Mei
相关产品推荐
相关产品推荐

