Sdílet prostřednictvím


Použití překladače kontraktů dat

Překladač kontraktů dat umožňuje dynamicky konfigurovat známé typy. Známé typy jsou vyžadovány při serializaci nebo deserializaci typu, který neočekává kontrakt dat. Další informace o známýchtypech Známé typy jsou obvykle specifikovány staticky. To znamená, že byste při implementaci operace museli znát všechny možné typy operací. Existují scénáře, ve kterých to není pravda a schopnost dynamicky specifikovat známé typy je důležitá.

Vytvoření překladače kontraktů dat

Vytvoření překladače kontraktů dat zahrnuje implementaci dvou metod TryResolveType a ResolveName. Tyto dvě metody implementují zpětná volání, která se používají při serializaci a deserializaci v uvedeném pořadí. Metoda TryResolveType je vyvolána během serializace a přebírá datový typ kontraktu a mapuje ji na xsi:type název a obor názvů. Metoda ResolveName se vyvolá během deserializace a vezme xsi:type název a obor názvů a přeloží ji na typ datového kontraktu. Obě tyto metody mají knownTypeResolver parametr, který lze použít k použití výchozího známého překladače typů ve vaší implementaci.

Následující příklad ukazuje, jak implementovat DataContractResolver mapování na a z datového typu kontraktu pojmenovaného Customer z datového typu Personkontraktu .

public class MyCustomerResolver : DataContractResolver  
{  
    public override bool TryResolveType(Type dataContractType, Type declaredType, DataContractResolver knownTypeResolver, out XmlDictionaryString typeName, out XmlDictionaryString typeNamespace)  
    {  
        if (dataContractType == typeof(Customer))  
        {  
            XmlDictionary dictionary = new XmlDictionary();  
            typeName = dictionary.Add("SomeCustomer");  
            typeNamespace = dictionary.Add("http://tempuri.com");  
            return true;  
        }  
        else  
        {  
            return knownTypeResolver.TryResolveType(dataContractType, declaredType, null, out typeName, out typeNamespace);  
        }  
    }  
  
    public override Type ResolveName(string typeName, string typeNamespace, DataContractResolver knownTypeResolver)  
    {  
        if (typeName == "SomeCustomer" && typeNamespace == "http://tempuri.com")  
        {  
            return typeof(Customer);  
        }  
        else  
        {  
            return knownTypeResolver.ResolveName(typeName, typeNamespace, null);  
        }  
    }  
}  

Jakmile definujete, DataContractResolver můžete ho použít tak, že ho předáte konstruktoru DataContractSerializer , jak je znázorněno v následujícím příkladu.

XmlObjectSerializer serializer = new DataContractSerializer(typeof(Customer), null, Int32.MaxValue, false, false, null, new MyCustomerResolver());  

Můžete zadat DataContractResolver volání DataContractSerializer.ReadObject nebo DataContractSerializer.WriteObject metody, jak je znázorněno v následujícím příkladu.

MemoryStream ms = new MemoryStream();  
DataContractSerializer serializer = new DataContractSerializer(typeof(Customer));  
XmlDictionaryWriter writer = XmlDictionaryWriter.CreateDictionaryWriter(XmlWriter.Create(ms));  
serializer.WriteObject(writer, new Customer(), new MyCustomerResolver());  
writer.Flush();  
ms.Position = 0;  
Console.WriteLine(((Customer)serializer.ReadObject(XmlDictionaryReader.CreateDictionaryReader(XmlReader.Create(ms)), false, new MyCustomerResolver()));  

Nebo ho můžete nastavit na následujícím příkladu DataContractSerializerOperationBehavior .

ServiceHost host = new ServiceHost(typeof(MyService));  
  
ContractDescription cd = host.Description.Endpoints[0].Contract;  
OperationDescription myOperationDescription = cd.Operations.Find("Echo");  
  
DataContractSerializerOperationBehavior serializerBehavior = myOperationDescription.Behaviors.Find<DataContractSerializerOperationBehavior>();  
if (serializerBehavior == null)  
{  
    serializerBehavior = new DataContractSerializerOperationBehavior(myOperationDescription);  
    myOperationDescription.Behaviors.Add(serializerBehavior);  
}  
  
SerializerBehavior.DataContractResolver = new MyCustomerResolver();  

Překladač kontraktů dat můžete deklarativním způsobem určit implementací atributu, který lze použít pro službu. Další informace najdete v ukázce PoleAssemblyAttribute . Tato ukázka implementuje atribut s názvem "KnownAssembly", který do chování služby přidá překladač vlastních kontraktů dat.

Viz také