获取Jackson XMLMapper以读取根元素名称

时间:2016-03-30 18:42:48

标签: jackson jackson-dataformat-xml

如何在反序列化时让Jackson的XMLMapper读取根xml元素的名称?

我将输入XML反序列化为通用Java类,LinkedHashMap,然后再反转为JSON。我想动态地将反序列化的输入XML的根元素读取到LinkedHashMap。

代码

   
XmlMapper xmlMapper = new XmlMapper();
Map entries = xmlMapper.readValue(new File("source.xml"), LinkedHashMap.class);
ObjectMapper jsonMapper = new ObjectMapper();
String json = jsonMapper.writer().writeValueAsString(entries);
System.out.println(json);

输入XML

<?xml version="1.0" encoding="ISO-8859-1"?>
<File>
  <NumLeases>1</NumLeases>
  <NEDOCO>18738</NEDOCO>
  <NWUNIT>0004</NWUNIT>
  <FLAG>SUCCESS</FLAG>
  <MESSAGE>Test Upload</MESSAGE>
  <Lease>
     <LeaseVersion>1</LeaseVersion>
     <F1501B>
        <NEDOCO>18738</NEDOCO>
        <NWUNIT>0004</NWUNIT>
        <NTRUSTRECORDKEY>12</NTRUSTRECORDKEY>
     </F1501B>
  </Lease>
</File>

实际输出

{"NumLeases":"1","NEDOCO":"18738","NWUNIT":"0004","FLAG":"SUCCESS","MESSAGE":"Test Upload","Lease":{"LeaseVersion":"1","F1501B":{"NEDOCO":"18738","NWUNIT":"0004","NTRUSTRECORDKEY":"12"}}}  

预期输出(注意:JSON中存在名为“File”的根元素)

{"File":{"NumLeases":"1","NEDOCO":"18738","NWUNIT":"0004","FLAG":"SUCCESS","MESSAGE":"Test Upload","Lease":{"LeaseVersion":"1","F1501B":{"NEDOCO":"18738","NWUNIT":"0004","NTRUSTRECORDKEY":"12"}}}}

可能有某些开关设置它。任何帮助都应该受到赞赏。

1 个答案:

答案 0 :(得分:2)

可悲的是,没有标志。可以使用com.fasterxml.jackson.databind.deser.std.JsonNodeDeserializer的自定义实现来完成。 (Jackson How-To: Custom Deserializers):

import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.databind.*;
import com.fasterxml.jackson.databind.deser.std.JsonNodeDeserializer;
import com.fasterxml.jackson.databind.module.SimpleModule;
import com.fasterxml.jackson.dataformat.xml.XmlMapper;
import com.fasterxml.jackson.dataformat.xml.deser.FromXmlParser;
import java.io.File;
import java.io.IOException;
//...
XmlMapper xmlMapper = new XmlMapper();
xmlMapper.registerModule(new SimpleModule().addDeserializer(JsonNode.class, 

    new JsonNodeDeserializer() {

        @Override
        public JsonNode deserialize(JsonParser p, DeserializationContext ctxt) throws IOException {
            String rootName = ((FromXmlParser)p).getStaxReader().getLocalName();
            return ctxt.getNodeFactory()
                    .objectNode().set(rootName, super.deserialize(p, ctxt));
        }
    }));

JsonNode entries = xmlMapper.readTree(new File("source.xml"));
System.out.println(entries);