Arhn - архитектура программирования

С# - Как десериализовать ответ xml

Я получаю данные xml из веб-API и десериализую данные в объекты.:

<Result>
  <VendorInfo xml:lang="xx">
    <Vendor vname="A" cpe="B">
      <Product pname="C" cpe="D"/>
    </Vendor>
    <Vendor vname="E" cpe="F">
      <Product pname="G" cpe="H"/>
    </Vendor>
    <Vendor vname="I" cpe="J">
      <Product pname="K" cpe="L"/>
      <Product pname="M" cpe="N"/>
    </Vendor>
  </VendorInfo>
  <Status keyword="hoge" feed="bar"/>
</Result>

Мой текущий код таков:

[XmlRoot(ElementName = "Product")]
public class Product
{
    [XmlAttribute(AttributeName = "pname")]
    public string Pname { get; set; }
    [XmlAttribute(AttributeName = "cpe")]
    public string Cpe { get; set; }
}

[XmlRoot(ElementName = "Vendor")]
public class Vendor
{
    [XmlArrayItem(ElementName = "Product")]
    public List<Product> Product { get; set; }
    [XmlAttribute(AttributeName = "vname")]
    public string Vname { get; set; }
    [XmlAttribute(AttributeName = "cpe")]
    public string Cpe { get; set; }
}

[XmlRoot(ElementName = "VendorInfo")]
public class VendorInfo
{
    [XmlElement(ElementName = "Vendor")]
    public List<Vendor> Vendor { get; set; }
    [XmlAttribute(AttributeName = "lang")]
    public string Lang { get; set; }
}

[XmlRoot(ElementName = "Status")]
public class Status
{
    [XmlAttribute(AttributeName = "feed")]
    public string Feed { get; set; }
    [XmlAttribute(AttributeName = "keyword")]
    public string Keyword { get; set; }
}

[XmlRoot(ElementName = "Result")]
public class Result
{
    [XmlElement(ElementName = "VendorInfo")]
    public VendorInfo VendorInfo { get; set; }
    [XmlElement(ElementName = "Status")]
    public Status Status { get; set; }
}

Но этот код работает неправильно. Десериализуются только первые 2 элемента Vendor, элемент Product не десериализуется. Что я делаю не так?

с уважением



Ответы:


1

Вам нужно позаботиться о нескольких вещах.

Сделайте только один элемент XmlRoot. Перейдите по ссылке ниже и найдите «Управление сериализацией классов с помощью XmlRootAttribute и XmlTypeAttribute».

https://docs.microsoft.com/en-us/dotnet/standard/serialization/controlling-xml-serialization-using-attributes

Здесь, в вашем случае, класс «Результат» является корневым.

Отдохните все XmlType.

В классе поставщика вместо «XmlArrayItem» сделайте просто «XmlElement».

Вот рабочий код.

    [XmlType("Product")]
    public class Product
    {
        [XmlAttribute(AttributeName = "pname")]
        public string Pname { get; set; }
        [XmlAttribute(AttributeName = "cpe")]
        public string Cpe { get; set; }
    }

    [XmlType("Vendor")]
    public class Vendor
    {
        [XmlElement(ElementName = "Product")]
        public List<Product> Product { get; set; }
        [XmlAttribute(AttributeName = "vname")]
        public string Vname { get; set; }
        [XmlAttribute(AttributeName = "cpe")]
        public string Cpe { get; set; }
    }

    [XmlType("VendorInfo")]
    public class VendorInfo
    {
        [XmlElement(ElementName = "Vendor")]
        public List<Vendor> Vendor { get; set; }
        [XmlAttribute(AttributeName = "xml:lang")]
        public string Lang { get; set; }
    }

    [XmlType("Status")]
    public class Status
    {
        [XmlAttribute(AttributeName = "feed")]
        public string Feed { get; set; }
        [XmlAttribute(AttributeName = "keyword")]
        public string Keyword { get; set; }
    }

    [XmlRoot(ElementName = "Result")]
    public class Result
    {
        [XmlElement(ElementName = "VendorInfo")]
        public VendorInfo VendorInfo { get; set; }
        [XmlElement(ElementName = "Status")]
        public Status Status { get; set; }
    }
14.05.2018
  • XmlRoot правильный. Единственное, что нужно изменить, — это XmlArrayItem. 15.05.2018
  • Да.... но ссылка на документацию, которую я предоставил, четко говорит не использовать.... XmlRoot для более чем одного класса.... 15.05.2018
  • Сначала в документации говорится XmlRootAtrribute, а не XmlRoot. Во-вторых, я использовал XmlRoot много раз, это более одного класса, и это работает. Веб-страницы Microsoft и, как известно, содержат множество ошибок. Microsoft, вероятно, наняла технических писателей для написания этих веб-страниц, которые никогда не программировали. Не верьте всему, что говорит Microsoft. 15.05.2018
  • Новые материалы

    Коллекции публикаций по глубокому обучению
    Последние пару месяцев я создавал коллекции последних академических публикаций по различным подполям глубокого обучения в моем блоге https://amundtveit.com - эта публикация дает обзор 25..

    Представляем: Pepita
    Фреймворк JavaScript с открытым исходным кодом Я знаю, что недостатка в фреймворках JavaScript нет. Но я просто не мог остановиться. Я хотел написать что-то сам, со своими собственными..

    Советы по коду Laravel #2
    1-) Найти // You can specify the columns you need // in when you use the find method on a model User::find(‘id’, [‘email’,’name’]); // You can increment or decrement // a field in..

    Работа с временными рядами спутниковых изображений, часть 3 (аналитика данных)
    Анализ временных рядов спутниковых изображений для данных наблюдений за большой Землей (arXiv) Автор: Рольф Симоэс , Жильберто Камара , Жильберто Кейрос , Фелипе Соуза , Педро Р. Андраде ,..

    3 способа решить квадратное уравнение (3-й мой любимый) -
    1. Методом факторизации — 2. Используя квадратичную формулу — 3. Заполнив квадрат — Давайте поймем это, решив это простое уравнение: Мы пытаемся сделать LHS,..

    Создание VR-миров с A-Frame
    Виртуальная реальность (и дополненная реальность) стали главными модными терминами в образовательных технологиях. С недорогими VR-гарнитурами, такими как Google Cardboard , и использованием..

    Демистификация рекурсии
    КОДЕКС Демистификация рекурсии Упрощенная концепция ошеломляющей О чем весь этот шум? Рекурсия, кажется, единственная тема, от которой у каждого начинающего студента-информатика..