WebService, WebMethod и Inheritance - PullRequest
       20

WebService, WebMethod и Inheritance

3 голосов
/ 04 марта 2009

В контексте веб-службы у меня есть следующий класс, который наследуется от класса Mammal. Класс Mammal определен в прокси. Я не могу изменить определение этого класса. Поскольку мне нужно добавить некоторые методы в класс Mammal на стороне клиента, я унаследовал Mammal и создал Giraffe.

namespace TestApplication
{  
    public class Giraffe : Mammal
    {
        public Giraffe()
        {
        }
    }
}

Когда я вызываю WebMethod, который ожидает объект типа Mammal, я получаю следующее исключение, говорящее мне, что Жираф не ожидается.

  Error: System.InvalidOperationException: There was an error generating the XML document. ---> System.InvalidOperationException: The type Giraffe was not expected. Use the XmlInclude or SoapInclude attribute to specify types that are not known statically.
   at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriterPaymentRequestAuthorization.Write6_Tender(String n, String ns, Tender o, Boolean isNullable, Boolean needType)
   at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriterPaymentRequestAuthorization.Write12_PaymentRequestAuthorization(String n, String ns, PaymentRequestAuthorization o, Boolean isNullable, Boolean needType)
   at Microsoft.Xml.Serialization.GeneratedAssembly.XmlSerializationWriterPaymentRequestAuthorization.Write13_PaymentRequestAuthorization(Object o)
   --- End of inner exception stack trace ---

Есть ли обходной путь? Я не могу добавить XmlInclude ...

Ответы [ 4 ]

2 голосов
/ 10 марта 2011

Если вы просто хотите добавить методы в класс, который вы не можете изменить, просто создайте методы расширения.

public static class MammalExt {
public static void ExtraMethod(this Mammal mammal) {...}}

Хотя, если млекопитающее является прокси-генерируемым классом, оно должно быть частичным классом.

2 голосов
/ 04 марта 2009

Чтобы добавить методы, вы должны использовать частичные классы. Попробуйте добавить файл второго класса с помощью (в правом пространстве имен и т. Д.):

partial class Mammal {
    public void ExtraMethod() {...}
}

Ключевое слово partial указывает компилятору разрешить разделение класса на несколько файлов - идеально для сценариев генерации кода. Однако он требует ключевого слова partial в каждом файле; члены просто объединяются (за исключением частичных методов в C # 3.0, которые имеют свое тонкое поведение). Я надеюсь , что wsdl.exe (или что-то еще) включает это!

1 голос
/ 10 марта 2011

Правильный ответ - использовать частичный класс. Когда вы открываете клиентский проект и генерируете веб-ссылку, Visual Studio анализирует WSDL и генерирует для вас класс с именем Mammal. Этот класс виден только клиентскому проекту, поэтому вам не нужно беспокоиться о серверной стороне вещей.

Допустим, у вас есть веб-справка MyWebService. Тогда будет класс с именем MyWebService.Mammal. Чтобы добавить членов в этот класс, все, что вам нужно сделать, это создать новый исходный файл, содержащий это:

namespace MyWebService {
    public partial class Mammal {
        public void ExtraMethod() { ... }
    }
}

Когда вы вызываете метод в вашей веб-службе, который возвращает Mammal, код веб-ссылки создаст новый экземпляр вашего «улучшенного» класса Mammal и скопирует значения из xml на проводе в экземпляр.

1 голос
/ 03 августа 2009

Вы должны использовать XmlInclude. Это твой единственный выбор. Вы должны сообщить сериализатору, какой класс вы будете сериализовать, поскольку он должен сгенерировать код для сериализации.

Когда я писал это, меня просто поразило, что вам может не понравиться, когда Giraffe реализует IXmlSerializable, но это еще больше работы.

...