我有一个简单的spring批处理程序,它从数据库表读取并使用下面的默认XStreamMarshaller编写器类形成输出XML
org.springframework.oxm.xstream.XStreamMarshaller
我读取输入的数据库表TOY包含两列:TOY_NAME,TOY_COLOR
对于单个TOY,可能有多个不同颜色的条目。
例如对于TOY CAR和TOY BUS,数据库条目如下:
TOY_NAME | TOY_COLOR
--------------------------
CAR | RED
CAR | YELLOW
CAR | BLUE
BUS | RED
BUS | YELLOW
--------------------------
将传递给ROW MAPPER的结果集将是5行,每行有两列即。 toy_name和color。
我的java域对象包含一个包含TOY对象列表的主对象TOYS。
TOY对象本身包含两个字段即。 toyName和String toyColor列表。
我的输出XML具有简单的读写配置如下:
<TOYS>
<TOY>
<NAME>CAR</NAME>
<COLORS>
<COLOR>RED</COLOR>
</COLORS>
</TOY>
<TOY>
<NAME>CAR</NAME>
<COLORS>
<COLOR>YELLOW</COLOR>
</COLORS>
</TOY>
<TOY>
<NAME>CAR</NAME>
<COLORS>
<COLOR>BLUE</COLOR>
</COLORS>
</TOY>
<TOY>
<NAME>BUS</NAME>
<COLORS>
<COLOR>RED</COLOR>
</COLORS>
</TOY>
<TOY>
<NAME>BUS</NAME>
<COLORS>
<COLOR>BLUE</COLOR>
</COLORS>
</TOY>
</TOYS>
从上面可以清楚地看到,对于结果集的每一行,都会创建一个单独的TOY节点。
但是,我想要输出如下:
<TOYS>
<TOY>
<NAME>CAR</NAME>
<COLORS>
<COLOR>RED</COLOR>
<COLOR>YELLOW</COLOR>
<COLOR>BLUE</COLOR>
</COLORS>
</TOY>
<TOY>
<NAME>BUS</NAME>
<COLORS>
<COLOR>RED</COLOR>
<COLOR>BLUE</COLOR>
</COLORS>
</TOY>
</TOYS>
即 - 对于每个TOY,只应创建一个包含该特定TOY的所有颜色的TOY节点。
如何根据我的结果集在READER(或ROW MAPPER)中处理此要求?
有没有办法调整我的阅读器sql以满足上述场景?
我当前的sql(生成第一个xml)是:
SELECT TOY_NAME, TOY_COLOR FROM TOY ORDER BY TOY_NAME
感谢阅读!
答案 0 :(得分:0)
我不会在您的域对象玩具中使用List,而是尝试使用带有key = name的Map。在你的读者和作者之间,我会实现一个ItemProcessor,试图从地图中获取玩具对象并将addColor()添加到它,然后将其放回地图中。
所以在你的例子中,你最终会得到
[car,[toy[name=car,colors={blue,red,yellow}]]
[bus,[toy[name=bus,colors={blue,red}]]
然后XStream将编写您需要的输出。 (您可能必须使用转换器)
这只适用于一个小的resultSet ......那么一个resultSet samller然后你的commit-interval。因为如果你的resultSet大于你的提交间隔,你将无法访问你的地图,你最终可能会有多个
<TOY><name="car">
这个合并之王的问题在于,在将其刷新到磁盘之前,必须在内存中构建所有XML文档!
如果我想到更好的东西,我会编辑。
编辑:哦,你也可以使用GROUP BY名称和CONCAT颜色
这会给你
car | blue,yellow,red
bus | red,blue
然后您可以使用ItemProcessor来获取此字符串:蓝色,黄色,红色并提取每种颜色以将其添加到您的域对象颜色列表中。
祝你好运