2010-02-24 13 views
15

seri ile probem ben bu sınıfları var. Şimdi ErrorBase örnekleri ile ResponseFileInquiry.errors doldurmak eğer, her şey gayet iyi çalışıyor, ama kalıtsal tip FileMissingError bir örneğini eklerseniz, ben seri hale getirme sırasında bir servis yan istisna olsun:WCF kalıtsal tipleri

Type 'MyNamespace.FileMissingError' with data contract name 'FileMissingError' 
is not expected. Add any types not known statically to the list of known types - 
for example, by using the KnownTypeAttribute attribute or by adding them to the 
list of known types passed to DataContractSerializer.' 

Yani serileştirici çünkü karıştı oluyor o bildirilmiş bir tür nesneleri (ErrorBase) içerecek şekilde Listesini bekliyor ama miras türü (FileMissingError) nesneleri oluyor.

Ben hata türlerinin sürü var ve Liste bunların kombinasyonlarını içerecek, bu yüzden o iş yapmak için ne yapabiliriz ???

cevap

17

Sen Biraz biraz geç bu blog

+1

Teşekkürler, blog girişi bilinen türleri bildirmenin tüm olası yollarına sahiptir. – Andrey

+0

Durumumda, KnownType kullanmak, tür referans almadığım ayrı bir derlemeden geldiğinden çok yardımcı olmaz. Diğer devreler, DataContract'ım için bazı özellikleri eklemek için sahip olduğum sınıfı genişletiyorlar. Ne tür bir sınıf atmak ve temel sınıfı kullanmak istiyorsam? – brendonparker

+0

Kullanmam gereken çözüm: http: // stackoverflow.com/a/8414390/2460073 Not: Müşteri DataContractSerializer'ı ClientBase'e uygulamak zorunda kaldım. – brendonparker

7

bu deneyin: Hata mesajı devletler olarak

[DataContract] 
[KnownType(typeof(FileMissingError))] 
public class ErrorBase {} 

, niteliklerin yoluyla sağlanmalıdır (burada ifade ettiler polimorfik ilişki gibi) statik biliyorum edilemez herhangi bir bilgi. Bu durumda size FileMissingError veri sözleşmesi onun temel sınıfı, ErrorBase bir bilinen tip olduğunu belirtmek gerekir.

+0

Yani burada tüm alt Error sınıflarını belirlemek gerektiği anlamına gelmektedir? Bunu yapmanın başka bir yolu var mı? Ebeveyn sınıfının, sınıf dosyalarında ekli katılımcılar ve "kullanma" cümleleriyle çocuk sınıflarının farkında olabileceğini sevmiyorum. istisna "bilinen türleri listesine statik olarak bilinmemektedir herhangi türlerini ekleyin. - örneğin, KnownTypeAttribute özelliğini kullanarak veya DataContractSerializer geçirilen bilinen türleri listesine ekleyerek" dedi Yani, onları bilinen türlerin listesine eklemenin bir yolu var mı? Bunu nasıl yaparım? – Andrey

+2

Sen el sözleşmeleri kendiniz seri sadece eğer tefrika bilinen türlerinin listesini geçebilir. WCF'nin sizin için serileştirme işlemlerini gerçekleştirmesine izin vermişsiniz gibi göründüğünden, yapabileceğiniz tek şey, bilmeniz gereken her alt sınıf için bir tane "KnownTypeAttribute" ekleyecektir. –

2

yılında KnownType özelliği hakkında daha fazla oku temel sınıf

[DataContract] 
[KnownType(typeof(FileMissingError))] 
public class ErrorBase {} 

için KnownType özelliğini eklemek, ama belki gelecek nesiller için olmalıdır. =) Eğer üst sınıfa her çocuk sınıf için bir öznitelik eklemek istemiyorsanız

, sen

IEnumerable<Assembly> assemblies = AppDomain.CurrentDomain 
              .GetAssemblies() 
              .Where(a => !a.GlobalAssemblyCache); 

IEnumerable<Type> serializableTypes = assemblies.SelectMany(a => a.GetTypes()) 
               .Where(t => IsSerializable(t)); 

// ... 

private static bool IsSerializable(Type type) 
{ 
    return type.GetCustomAttributes(true).Any(a => a is DataContractAttribute); 
} 

kullanarak ana sınıfları statik yapıcı bilinen türlerinin bir listesini oluşturmak ve bu geçebileceği de/serializers yapıcısını listeler. Bu çözümün ne kadar sağlam olduğunu bilmiyorum, ama şu anda yapıyorum ve şu ana kadar çalışıyor. Biraz yavaş, bu yüzden sonucu önbelleğe aldığınızdan emin olun.