osglworks / java-tool

Some simple common Java utilities
Apache License 2.0
52 stars 18 forks source link

Improve XML to JSON convert logic #243

Open greenlaw110 opened 3 years ago

greenlaw110 commented 3 years ago

The introducing of #240 brought in an error that it cannot handle simple XML without attributes conversion correctly.

This CR is to improve XML to JSON convert logic to handle XML with or without attributes correctly.

Case 1.1 - simple XML without attributes

<root>
<parent>
  <child>123</child>
</parent>
</root>

converted ($.convert(xmlDoc).to(JSONObject.class)) into

{
  "parent": {
    "child": 123
  }
}

Case 1.2 - simple XML list without attributes

<root>
<parent>
  <child>123</child>
</parent>
<parent>
  <child>456</child>
</parent>
</root>

converted into

JSON without MERGE_MAP hint:

{
  "parent": [
    {
      "child": 123
    },
    {
      "child": 456
    }
  ]
}

JSON with MERGE_MAP hint ($.convert(xmlDoc).hint(XmlToJson.HINT_MERGE_MAP).to(JSONObject.class)) turned on:

{
  "parent": {
    "child": [123, 456]
  }
}

Case 1.3 - simple mixed XML list without attributes

<root>
<parent>
  <child>123</child>
</parent>
<parent>
  <child>456</child>
</parent>
<parent2>
  <child>789</child>
</parent2>
<someone>abc</someone>
</root>

converted into

JSON without MERGE_MAP hint:

{
  "parent": [
    {
      "child": 123
    },
    {
      "child": 456
    }
  ],
  "parent2": {
    "child": 789
  },
  "someone": "abc"
}

JSON with MERGE_MAP hint turned on

{
  "parent": {
    "child": [123, 456]
  },
  "parent2": {
    "child": 789
  },
  "someone": "abc"
}

Case 2.1 - XML with attributes and no text

<root>
<parent>
  <child value="123"/>
</parent>
</root>

converted into

{
  "parent": {
    "child": {
       "value": 123
    }
  }
}

Case three - XML with attributes and value

<root>
<parent>
  <child value="123">abc</child>
</parent>
</root>

converted into

{
  "parent": {
    "child": {
       "value": 123,
       "innerValue": "abc"
    }
  }
}

Note

OSGL tool XML to JSON convert tool require at least one ELEMENT type node inside the root node, otherwise it returns an empty JSONObject.

E.g. converting the following xml document will return an empty JSONObject:

<root>abc</root>
greenlaw110 commented 3 years ago

Refer: https://github.com/osglworks/java-tool/blob/master/src/test/java/org/osgl/util/XMLTest.java#L32