Spring Boot XML сериализация списка запросов - PullRequest
1 голос
/ 01 февраля 2020

Я пытаюсь вернуть XML из @RestController. XML - это сериализованный List из Car.

. Сериализация XML работает не так, как я ожидал. Сериализация не использует имя объекта в качестве имени элемента <Car>...</Car>, она просто использует <item>...</item>. И я не могу понять, как изменить это поведение.

Простой пример:

Я включил следующую зависимость в POM:

<dependency>
    <groupId>com.fasterxml.jackson.dataformat</groupId>
    <artifactId>jackson-dataformat-xml</artifactId>
</dependency>

Класс автомобиля:

import lombok.Data;

@Data
public class Car
{
    private final long id;
    private final String make;
    private final String model;
}

Класс CarService:

@Service
public class CarService
{
    public List<Car> findAll()
    {
        var cars = new ArrayList<Car>();

        cars.add(new Car(1, "Ford", "Fiesta"));
        cars.add(new Car(2, "Ford", "Mustang"));
        cars.add(new Car(3, "Ford", "GT40"));

        return cars;
    }
}

Класс CarController:

@RestController
public class CarController
{
    private final CarService carService;

    public CarController(CarService carService)
    {
        this.carService = carService;
    }

    @GetMapping(value="/cars")
    public List<Car> getCars()
    {
        return carService.findAll();
    }
}

HTTP-запрос:

GET http://localhost:8080/cars
Accept: application/xml

Я получаю:

<List>
    <item>
        <id>1</id>
        <make>Ford</make>
        <model>Fiesta</model>
    </item>
    <item>
        <id>2</id>
        <make>Ford</make>
        <model>Mustang</model>
    </item>
    <item>
        <id>3</id>
        <make>Ford</make>
        <model>GT40</model>
    </item>
</List>

И я ожидаю:

<List>
    <Car>
        <id>1</id>
        <make>Ford</make>
        <model>Fiesta</model>
    </Car>
    <Car>
        <id>2</id>
        <make>Ford</make>
        <model>Mustang</model>
    </Car>
    <Car>
        <id>3</id>
        <make>Ford</make>
        <model>GT40</model>
    </Car>
</List>

Я также пытался изменить класс Car на этот, но это не имело никакого эффекта:

import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlRootElement;
import lombok.Data;

@Data
@JacksonXmlRootElement(localName="car")
public class Car
{
    private final long id;
    private final String make;
    private final String model;
}

Также в идеале я хочу, чтобы элемент root был <Cars></Cars>, но я не могу даже получить предметы с правильной оберткой в ​​данный момент. У меня такое ощущение, что я упускаю что-то очень простое, но не вижу, что.

Проект начальной загрузки, созданный с этими параметрами

Простой пример проекта на GitHub

1 Ответ

1 голос
/ 02 февраля 2020

Я проверил ваш проект и добавил упаковщик для списка автомобилей, который должен быть установлен как JacksonXmlRootElement, и определил список автомобилей как атрибут этого класса:

Класс автомобилей:

@Data
@JacksonXmlRootElement(localName = "Cars")
public class Cars {
    @JacksonXmlElementWrapper(useWrapping = false)
    @JacksonXmlProperty(localName = "Car")
    private List<Car> cars;
}

@Data
class Car {
    private final long id;
    private final String make;
    private final String model;
}

Сервис:

@Service
public class CarService {
    public Cars findAll() {
        var cars = new Cars();

        cars.setCars(
                List.of(
                        new Car(1, "Ford", "Fiesta"),
                        new Car(2, "Ford", "Mustang"),
                        new Car(3, "Ford", "GT40"))
        );

        return cars;
    }
}

Контроллер:

@RestController
public class CarController
{
    private final CarService carService;

    public CarController(CarService carService)
    {
        this.carService = carService;
    }

    @GetMapping(value="/cars")
    public Cars getCars()
    {
        return carService.findAll();
    }
}

Выход:

<Cars>
    <Car>
        <id>1</id>
        <make>Ford</make>
        <model>Fiesta</model>
    </Car>
    <Car>
        <id>2</id>
        <make>Ford</make>
        <model>Mustang</model>
    </Car>
    <Car>
        <id>3</id>
        <make>Ford</make>
        <model>GT40</model>
    </Car>
</Cars>

Я использовал @JacksonXmlElementWrapper(useWrapping = false), чтобы не допустить того, чтобы список автомобилей также был включен в элемент.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...