Here is a brief outline of how one would “naively” transform Almost Universal API‘s (AUAPI) JSON into XML. We say “naive” because in general one wants to make a transformation into a specific XML application: Atom, RSS, OPML, KML, etc.. In those cases, one has to rename and rework certain elements first for standards compliance, then complete the naive transformation for remaining elements.
Walking
Walking JSON objects is done depth first. Most of the complexity involved is in handling dictionaries, which can be valued as being comprised of ( key, value ) pairs. For each dictionary, we are creating an XML node whose properties are defined as follows:
- keys beginning with
@@ are ignored
- the key
@ means “the text” of the node (the examples will make this more clear)
- other keys beginning with
@ are attributes of the node
- all other keys are defining children of the node
There are number of complexities that have to be addressed; for this I suggest looking at the examples or source code.
Namespace handling
- collect all the namespaces used in the JSON and add to the root XML node
- if any JSON element has a namespace, assume that namespace is inherited by its children
Code
You can see the code for this in the AUAPI source base in api.py in XMLAPIWriter.TranscribeNode.
Example 1
{
"numbers" : [ 1, -0.23, ],
"strings" : [ "bob", "caf\xe9", ],
"booleanish" : [ True, False, None, ],
}
<root>
<numbers>1</numbers>
<numbers>-0.23</numbers>
<booleanish>True</booleanish>
<booleanish>False</booleanish>
<booleanish />
<strings>bob</strings>
<strings>caf\xc3\xa9</strings>
</root>
Example 2
{
"a1" : {
"b1" : 1,
"b2" : 2,
},
"a2" : {
"b3" : "hi",
"b4" : "there",
},
}
<root>
<a1>
<b1>1</b1>
<b2>2</b2>
</a1>
<a2>
<b4>there</b4>
<b3>hi</b3>
</a2>
</root>
Example 3
{
"@attribute" : "hello",
"@bttribute" : "there",
"a" : "some string",
},
<root attribute="hello" bttribute="there">
<a>some string</a>
</root>