使用Jackson将具有重复元素的XML转换为JSON

6
我有一些简单的XML格式数据,需要将其转换为JSON,并能够将JSON转换回相同的XML字符串。但是我在使用现有的Jackson(版本2.0.6)库时遇到了问题。
以下是类似结构的XML数据示例:
<channels>
  <channel>A</channel>
  <channel>B</channel>
  <channel>C</channel>
</channels>

为了能够将其转换回原始XML,我希望JSON看起来像这样。
{
  "channels": {
    "channel": [
      "A",
      "B",
      "C"
    ]
  }
}

然而,Jackson让我感到困惑。
{"channel":"C"}

根元素名称未被保留,而是创建了通道数组,最后一个覆盖了之前的。

查看com.fasterxml.jackson.databind.deser.std.BaseNodeDeserializer的源代码,我发现该库不支持此功能,但允许覆盖和更改行为。

/**
 * Method called when there is a duplicate value for a field.
 * By default we don't care, and the last value is used.
 * Can be overridden to provide alternate handling, such as throwing
 * an exception, or choosing different strategy for combining values
 * or choosing which one to keep.
 *
 * @param fieldName Name of the field for which duplicate value was found
 * @param objectNode Object node that contains values
 * @param oldValue Value that existed for the object node before newValue
 *   was added
 * @param newValue Newly added value just added to the object node
 */
protected void _handleDuplicateField(String fieldName, ObjectNode objectNode,
                                     JsonNode oldValue, JsonNode newValue)
    throws JsonProcessingException
{
    // By default, we don't do anything
    ;
}

所以我的问题是

  1. 是否有人编写了自定义反序列化程序来支持此功能?或者还有其他方法可以解决这个问题。
  2. 如何保留根元素名称?

以下是一个测试示例

import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.dataformat.xml.XmlMapper;
public class Test {
  public static void main(String[] args) throws Exception {
    String xml="<channels><channel>A</channel><channel>B</channel><channel>C</channel></channels>";

    XmlMapper xmlMapper = new XmlMapper();
    JsonNode node=xmlMapper.readValue(xml,JsonNode.class);
    System.out.println(node.toString());
  }
}

就此而言,_handleDuplicateField不是解决此问题的方法-- 它只是一个错误处理机制。同时,你不能有效地使用树形模型来处理这个问题-- XML数据绑定需要一些解决方法,它们不能在没有Java类提供的类型信息的情况下应用。 - StaxMan
我意识到自己可能走错了方向。感谢您为我澄清这一点 :)最好为我创建一些POJO,以便能够序列化和反序列化我所拥有的少数变量,至少在jackson库在2.1版本中对此有适当支持之前。 - alternative4
1个回答

2

这里真正重要的是你的类——仅仅展示XML本身并不能提供足够的信息来知道发生了什么。

我猜想你需要Jackson 2.1(一两周后发布),因为它最终支持“未打包列表”正确地工作。在此之前,只有“已打包”列表能够正确工作。


好的,谢谢你的回答,我会在更新版本发布后进行检查。我只是惊讶于这个问题在 jackson-dataformat-xml 的概述页面上没有提到。 - alternative4
顺便提一下,我忘了说我目前正在使用 jackson 库的 2.0.6 版本(jackson-dataformat-xml 的版本为 2.0.5)。 - alternative4
同意 intro 页面不完整——缺少对“非封装”数组的支持是一个很大的问题,这可能会轻易地影响到任何期望完全符合 JAXB 兼容性的人。 - StaxMan

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接