Использование IExtensibleDataObject в клиентах
Я преобразовал свой веб-сервис в сервис wcf, который имеет некоторые контракты на передачу данных. Рекомендуется упомянуть и рекомендовать, чтобы DataContracts наследовался от IExtensibleDataObject. Я понимаю, что в случае добавления или удаления камер данных, IExtensibleDataObject полезен. Но я не могу понять, как клиенты получат доступ к удаленным пользователям. Вот мой код:
[ServiceContract(Namespace = "http://mycompany.com/2010/08/")]
public class MyWebService {
[OperationContract]
public Employee Add(Employee emp)
{
// Some Processing
}
}
[DataContract(Name = "Employee", Namespace = "http://mycompany.com/2010/08/")]
public class Employee : IExtensibleDataObject {
[DataMember] public string FirstName;
[DataMember] public string LastName;
public ExtensionDataObject ExtensionData { get; set; }
}
Теперь в моей следующей версии веб-сервиса я внес некоторые изменения в DataContract как
[DataContract(Name = "Employee", Namespace = "http://mycompany.com/2010/09/")]
public class Employee : IExtensibleDataObject {
[DataMember] public string FirstName;
[DataMember] public string LastName;
[DataMember(IsRequired = true)] public string MiddleName;
public ExtensionDataObject ExtensionData { get; set; }
}
Однако мой клиент, который обращается к моей более старой версии веб-службы, теперь получает ошибку из-за отсутствия поля MiddleName. Я все еще запутался в использовании IExtensionDataObject.
3 ответа
Боюсь, что это неправильное использование IExtensibleDataObject, интерфейс IExtensibleDataObject предназначен для поддержки циклического переключения версий, прочитайте эту статью MSDN о прямой совместимости:
http://msdn.microsoft.com/en-us/library/ms731083.aspx
А вот еще одна статья о лучших практиках управления версиями Data Contract в целом: http://msdn.microsoft.com/en-us/library/ms733832.aspx
Это неверное использование IExtensibleDataObject. Вы изменили контракт данных на стороне сервера и пометили новое поле как обязательное, так что это означает, что вы нарушили управление версиями, и ничто не поможет вам.
IExtensibleDataObject предназначен для другой цели. Предположим, что вы изменили свой клиент так, чтобы контракт данных на клиенте содержал MiddleName. Теперь вы устанавливаете MiddleName и используете операцию добавления сервиса. Какое значение MiddleName будет в возвращенном объекте Employee? Если вы не используете IExtensibleDataObject, значение будет нулевым, если вы используете IExtensibleDataObject, значение будет таким же, как вы указали для входного параметра.
При использовании DataContractSerializer WCF выбрасывает все непонятные параметры. IExtensibleDataObject позволяет избежать этого, сохраняя все эти параметры в специальной коллекции и отправляя их обратно клиенту.
Если вы хотите использовать контрактное управление версиями, забудьте о необходимых полях. Это первое, что сломает это.
С наилучшими пожеланиями, Ладислав
Сделайте свойство ExtensionData виртуальным, как показано ниже:
public virtual ExtensionDataObject ExtensionData
{
get { return theData; }
set { theData = value; }
}