序列化列表产生 "Item" 个节点
Serializing a list produced "Item" nodes
我是一个相当简单的 java 对象模型。预订 class 有一个酒店列表作为成员。
(简化来源)
class Booking {
private Integer bookingId;
private List<Hotel> hotels;
}
我想通过为每个 class 使用 StdSerailizer 将预订序列化为 XML。
public class HotelTransform extends StdSerializer<Hotel> {
protected HotelTransform(Class<Hotel> t) {
super(t);
}
private static final long serialVersionUID = 4102379614389258553L;
@Override
public void serialize(Hotel value, JsonGenerator gen, SerializerProvider provider) throws IOException {
gen.writeStartObject();
gen.writeStringField("HName", value.getHotelName());
gen.writeStringField("Start", value.m_startDateLocal.toString());
gen.writeStringField("End", value.m_startDateLocal.toString());
gen.writeEndObject();
}
}
public class BookingTransform extends StdSerializer<Booking> {
protected BookingTransform(Class<Booking> t) {
super(t);
}
@Override
public void serialize(Booking value, JsonGenerator gen, SerializerProvider provider) throws IOException {
gen.writeStartObject();
gen.writeObjectField("Entries", value.getBookBookingEntry());
gen.writeEndObject();
}
}
序列化本身是用下面的测试代码完成的
public void simpleSmokeTest() {
Booking booking = new Booking();
booking.setBookingId(99);
Hotel aHotel = new Hotel();
aHotel.setHotelName("HEHotel");
aHotel.setStartDateLocal(LocalDateTime.now());
aHotel.setEndDateLocal(LocalDateTime.now());
booking.addhotel(aHotel);
Hotel aHotel2 = new Hotel();
aHotel2.setHotelName("HEHotel2");
aHotel2.setStartDateLocal(LocalDateTime.now());
aHotel2.setEndDateLocal(LocalDateTime.now());
booking.addhotel(aHotel2);
ObjectMapper mapper = new XmlMapper();
SimpleModule module = new SimpleModule();
module.addSerializer(new BookingTransform(Booking.class));
module.addSerializer(new HotelTransform(Hotel.class));
mapper.enable(SerializationFeature.INDENT_OUTPUT);
mapper.registerModule(module);
try {
String serialized = mapper.writeValueAsString(booking);
m_logger.debug("Serialized to: " + serialized);
} catch (JsonProcessingException e) {
e.printStackTrace();
}
}
生成的输出是:
<Booking>
<Entries>
<item>
<HName>HEHotel</HName>
<Start>2020-12-29T01:43:18.008480</Start>
<End>2020-12-29T01:43:18.008480</End>
</item>
<item>
<HName>HEHotel2</HName>
<Start>2020-12-29T01:43:18.009463</Start>
<End>2020-12-29T01:43:18.009463</End>
</item>
</Entries>
</Booking>
这已经接近我想要的,但我不想将我的酒店列表中的条目命名为“项目”,我希望它们被命名为“酒店”。像这样:
<Booking>
<Entries>
<Hotel>
<HName>HEHotel</HName>
<Start>2020-12-29T01:43:18.008480</Start>
<End>2020-12-29T01:43:18.008480</End>
</Hotel>
<Hotel>
<HName>HEHotel2</HName>
<Start>2020-12-29T01:43:18.009463</Start>
<End>2020-12-29T01:43:18.009463</End>
</Hotel>
</Entries>
</Booking>
我真的尝试了很多东西不。没有成功。
谁能解释我如何解决这个问题?
顺便说一句,在我的 POJO 中使用注释是不行的。
亲切的问候
哈里·E.
我认为问题是因为数组在 JSON 和 XML 中处理的方式不同。
下面是来自 XMLSerializerProvider._startRootArray()
的片段:
protected void _startRootArray(ToXmlGenerator xgen, QName rootName) throws IOException
{
xgen.writeStartObject();
// Could repeat root name, but what's the point? How to customize?
xgen.writeFieldName("item");
}
所以在 XML 的情况下,每个数组元素都被视为一个对象,默认字段名称为 item.
您当前用例的一个选择是使用特定于 XML 的 Transformer
,并在其中手动序列化 List
,如下所示:
@Override
public void serialize(Booking value, JsonGenerator gen, SerializerProvider provider) throws IOException {
gen.writeStartObject();
gen.writeFieldName("Entries");
gen.writeStartObject();
for (Hotel hotel : value.getBookBookingEntry()) {
gen.writeFieldName("Hotel");
gen.writeObject(hotel);
}
gen.writeEndObject();
gen.writeEndObject();
}
注意: 如果您将此序列化程序用于 JSON,它将导致对象 Entries
中名为 Hotel
的重复字段。
我是一个相当简单的 java 对象模型。预订 class 有一个酒店列表作为成员。 (简化来源)
class Booking {
private Integer bookingId;
private List<Hotel> hotels;
}
我想通过为每个 class 使用 StdSerailizer 将预订序列化为 XML。
public class HotelTransform extends StdSerializer<Hotel> {
protected HotelTransform(Class<Hotel> t) {
super(t);
}
private static final long serialVersionUID = 4102379614389258553L;
@Override
public void serialize(Hotel value, JsonGenerator gen, SerializerProvider provider) throws IOException {
gen.writeStartObject();
gen.writeStringField("HName", value.getHotelName());
gen.writeStringField("Start", value.m_startDateLocal.toString());
gen.writeStringField("End", value.m_startDateLocal.toString());
gen.writeEndObject();
}
}
public class BookingTransform extends StdSerializer<Booking> {
protected BookingTransform(Class<Booking> t) {
super(t);
}
@Override
public void serialize(Booking value, JsonGenerator gen, SerializerProvider provider) throws IOException {
gen.writeStartObject();
gen.writeObjectField("Entries", value.getBookBookingEntry());
gen.writeEndObject();
}
}
序列化本身是用下面的测试代码完成的
public void simpleSmokeTest() {
Booking booking = new Booking();
booking.setBookingId(99);
Hotel aHotel = new Hotel();
aHotel.setHotelName("HEHotel");
aHotel.setStartDateLocal(LocalDateTime.now());
aHotel.setEndDateLocal(LocalDateTime.now());
booking.addhotel(aHotel);
Hotel aHotel2 = new Hotel();
aHotel2.setHotelName("HEHotel2");
aHotel2.setStartDateLocal(LocalDateTime.now());
aHotel2.setEndDateLocal(LocalDateTime.now());
booking.addhotel(aHotel2);
ObjectMapper mapper = new XmlMapper();
SimpleModule module = new SimpleModule();
module.addSerializer(new BookingTransform(Booking.class));
module.addSerializer(new HotelTransform(Hotel.class));
mapper.enable(SerializationFeature.INDENT_OUTPUT);
mapper.registerModule(module);
try {
String serialized = mapper.writeValueAsString(booking);
m_logger.debug("Serialized to: " + serialized);
} catch (JsonProcessingException e) {
e.printStackTrace();
}
}
生成的输出是:
<Booking>
<Entries>
<item>
<HName>HEHotel</HName>
<Start>2020-12-29T01:43:18.008480</Start>
<End>2020-12-29T01:43:18.008480</End>
</item>
<item>
<HName>HEHotel2</HName>
<Start>2020-12-29T01:43:18.009463</Start>
<End>2020-12-29T01:43:18.009463</End>
</item>
</Entries>
</Booking>
这已经接近我想要的,但我不想将我的酒店列表中的条目命名为“项目”,我希望它们被命名为“酒店”。像这样:
<Booking>
<Entries>
<Hotel>
<HName>HEHotel</HName>
<Start>2020-12-29T01:43:18.008480</Start>
<End>2020-12-29T01:43:18.008480</End>
</Hotel>
<Hotel>
<HName>HEHotel2</HName>
<Start>2020-12-29T01:43:18.009463</Start>
<End>2020-12-29T01:43:18.009463</End>
</Hotel>
</Entries>
</Booking>
我真的尝试了很多东西不。没有成功。 谁能解释我如何解决这个问题? 顺便说一句,在我的 POJO 中使用注释是不行的。
亲切的问候 哈里·E.
我认为问题是因为数组在 JSON 和 XML 中处理的方式不同。
下面是来自 XMLSerializerProvider._startRootArray()
的片段:
protected void _startRootArray(ToXmlGenerator xgen, QName rootName) throws IOException
{
xgen.writeStartObject();
// Could repeat root name, but what's the point? How to customize?
xgen.writeFieldName("item");
}
所以在 XML 的情况下,每个数组元素都被视为一个对象,默认字段名称为 item.
您当前用例的一个选择是使用特定于 XML 的 Transformer
,并在其中手动序列化 List
,如下所示:
@Override
public void serialize(Booking value, JsonGenerator gen, SerializerProvider provider) throws IOException {
gen.writeStartObject();
gen.writeFieldName("Entries");
gen.writeStartObject();
for (Hotel hotel : value.getBookBookingEntry()) {
gen.writeFieldName("Hotel");
gen.writeObject(hotel);
}
gen.writeEndObject();
gen.writeEndObject();
}
注意: 如果您将此序列化程序用于 JSON,它将导致对象 Entries
中名为 Hotel
的重复字段。