Convert XML to JSON with JavaScript
If you follow me on Twitter, you know that I've been working on a super top secret mobile application using Appcelerator Titanium. The experience has been great: using JavaScript to create easy to write, easy to test, native mobile apps has been fun. My mobile app connects to numerous social network APIs, some of which only provide an XML response. My mini "framework" uses JSON to dynamically create widgets so I've needed a way to turn XML into JSON. I found many solutions but none of them worked. After tweaking an existing function, I've found a solution that works great.
The JavaScript
It's important to point out that Titanium's Titanium.XML.DOMDocument object implements DOM2-level structures. Here's the magic XML to JSON code:
// Changes XML to JSON function xmlToJson(xml) { // Create the return object var obj = {}; if (xml.nodeType == 1) { // element // do attributes if (xml.attributes.length > 0) { obj["@attributes"] = {}; for (var j = 0; j < xml.attributes.length; j++) { var attribute = xml.attributes.item(j); obj["@attributes"][attribute.nodeName] = attribute.nodeValue; } } } else if (xml.nodeType == 3) { // text obj = xml.nodeValue; } // do children if (xml.hasChildNodes()) { for(var i = 0; i < xml.childNodes.length; i++) { var item = xml.childNodes.item(i); var nodeName = item.nodeName; if (typeof(obj[nodeName]) == "undefined") { obj[nodeName] = xmlToJson(item); } else { if (typeof(obj[nodeName].push) == "undefined") { var old = obj[nodeName]; obj[nodeName] = []; obj[nodeName].push(old); } obj[nodeName].push(xmlToJson(item)); } } } return obj; };
The major change I needed to implement was using attributes.item(j)
instead of the attributes[j]
that most of the scripts I found used. With this function, XML that looks like:
<ALEXA VER="0.9" URL="davidwalsh.name/" HOME="0" AID="="> <SD TITLE="A" FLAGS="" HOST="davidwalsh.name"> <TITLE TEXT="David Walsh Blog :: PHP, MySQL, CSS, Javascript, MooTools, and Everything Else"/> <LINKSIN NUM="1102"/> <SPEED TEXT="1421" PCT="51"/> </SD> <SD> <POPULARITY URL="davidwalsh.name/" TEXT="7131"/> <REACH RANK="5952"/> <RANK DELTA="-1648"/> </SD> </ALEXA>
...becomes workable a JavaScript object with the following structure:
{ "@attributes": { AID: "=", HOME: 0, URL: "davidwalsh.name/", VER: "0.9", }, SD = [ { "@attributes": { FLAGS: "", HOST: "davidwalsh.name", TITLE: A }, LINKSIN: { "@attributes": { NUM: 1102 } }, SPEED: { "@attributes": { PCT: 51, TEXT: 1421 } }, TITLE: { "@attributes": { TEXT: "David Walsh Blog :: PHP, MySQL, CSS, Javascript, MooTools, and Everything Else", } }, }, { POPULARITY: { "@attributes": { TEXT: 7131, URL: "davidwalsh.name/" } }, RANK: { "@attributes": { DELTA: "-1648" } }, REACH: { "@attributes": { RANK = 5952 } } } ] }
From here you can use the JavaScript object however you see fit. If you'd like the JavaScript in string JSON format, you can code:
// Assuming xmlDoc is the XML DOM Document var jsonText = JSON.stringify(xmlToJson(xmlDoc));
This function has been extremely useful in allowing me to quickly disregard XML and use JSON instead. The function works well when structuring attributes and arrays of nested child nodes. Keep this handy; at some point you may need to convert XML to JSON!
Nicely put. Good work!
Pretty good topic, i am working in a ios project that needed localization and all kinda of stuffs and coredata was a pain in the ass to make it work, so i have made a xml file for each language and for my surprise, nsxmlparser is a sax parser and it really sucks, so i converted my xml file in a json with this site: http://shlang.com/xml2json/
it worked and the json validated in the jsonlint.com
Your code example has several incorrect references to
$xmlToJson
.I took a stab at cleaning up the
xmlToJson
function here.Is there any reason you’re not using the YQL function in titanium to do this? I’ve found it worked a treat, only I’m not sure how efficient it is.