Джексон не должен игнорировать тег корневого элемента в многокорневом xml-содержимом

#java #jackson #jackson-dataformat-xml

Вопрос:

У меня есть следующий xml-контент, который я хочу десериализовать в JSON,

Входное содержимое

 <TransmissionAck>
    <EchoedTransmissionHeader>
        <TransmissionHeader>
            <ReferenceTransmissionNo>26218</ReferenceTransmissionNo>
        </TransmissionHeader>
    </EchoedTransmissionHeader>
</TransmissionAck>
 

Ожидаемый результат

 {
  "TransmissionAck": {
     "EchoedTransmissionHeader":{
        "TransmissionHeader":{
          "ReferenceTransmissionNo":"26177"
         }
      }
  }
}
 

Фактический Объем Производства

  {
  "EchoedTransmissionHeader":{
    "EchoedTransmissionHeader":{
        "TransmissionHeader":{
           "ReferenceTransmissionNo":"26177"
         }
  }}}
 

Я передаю динамический контент из RestController(весенняя загрузка)

 Mono<ResponseEntity<String>> otmXmlResponse = webRequestsService
                .handlePost(Files.readString(Paths.get(outputFile.getAbsolutePath()), StandardCharsets.US_ASCII));
String body = otmXmlResponse.block().getBody();
String r = testXmlResponse(body);

============

public <T> T testXmlResponse(String xml) throws JsonMappingException, JsonProcessingException {

        ObjectMapper objectMapper = new ObjectMapper();
        XmlMapper xmlMapper = new XmlMapper();
        xmlMapper.registerModule(new SimpleModule().addDeserializer(JsonNode.class,
                new JsonNodeDeserializer() {
                    private static final long serialVersionUID = -5947022035338738709L;

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

        JsonNode entries = xmlMapper.readTree(inputFile);
        String json = objectMapper.writerWithDefaultPrettyPrinter().writeValueAsString(entries);
        return (T) json;
}
 

Когда я запускаю модульный тест, я получаю ожидаемый результат, но когда я вызываю метод десериализации, как указано выше, с динамическим содержимым из контроллера, элемент подкорня берется как корневой. Я не могу использовать POJO для отображения. Есть идеи, как я могу получить ожидаемый результат с помощью библиотеки Джексона? Спасибо.

Ответ №1:

Попробуй это, я использовал

  <dependency>
   <groupId>org.json</groupId>
   <artifactId>json</artifactId>
   <version>20140107</version>
 </dependency>

import org.json.*;

public class ConvertXML {
public static String xml = "<TransmissionAck>rn"   "    <EchoedTransmissionHeader>rn"
          "        <TransmissionHeader>rn"
          "            <ReferenceTransmissionNo>26218</ReferenceTransmissionNo>rn"
          "        </TransmissionHeader>rn"   "    </EchoedTransmissionHeader>rn"   "</TransmissionAck>";

public static void main(String[] args) {
    try {
        JSONObject json = XML.toJSONObject(xml);
        String jsonString = json.toString(4);
        System.out.println(jsonString);

    } catch (JSONException e) {
        System.out.println(e.toString());
    }

 }
}