I am looking for a JavaScript library that parses an XML string and converts it to a JavaScript object. What are some good ones?
5 Answers
The following function parses XML and returns a JavaScript object with a scheme that corresponds to the XML. XML siblings w/ the same name are collapsed into arrays. nodes with names that can be found in the arrayTags parameter (array of tag name strings) always yield arrays even in case of only one tag occurrence. arrayTags can be omitted. Text nodes with only spaces are discarded.
function parseXml(xml, arrayTags) {
    let dom = null;
    if (window.DOMParser) dom = (new DOMParser()).parseFromString(xml, "text/xml");
    else if (window.ActiveXObject) {
        dom = new ActiveXObject('Microsoft.XMLDOM');
        dom.async = false;
        if (!dom.loadXML(xml)) throw dom.parseError.reason + " " + dom.parseError.srcText;
    }
    else throw new Error("cannot parse xml string!");
    function parseNode(xmlNode, result) {
        if (xmlNode.nodeName == "#text") {
            let v = xmlNode.nodeValue;
            if (v.trim()) result['#text'] = v;
            return;
        }
        let jsonNode = {},
            existing = result[xmlNode.nodeName];
        if (existing) {
            if (!Array.isArray(existing)) result[xmlNode.nodeName] = [existing, jsonNode];
            else result[xmlNode.nodeName].push(jsonNode);
        }
        else {
            if (arrayTags && arrayTags.indexOf(xmlNode.nodeName) != -1) result[xmlNode.nodeName] = [jsonNode];
            else result[xmlNode.nodeName] = jsonNode;
        }
        if (xmlNode.attributes) for (let attribute of xmlNode.attributes) jsonNode[attribute.nodeName] = attribute.nodeValue;
        for (let node of xmlNode.childNodes) parseNode(node, jsonNode);
    }
    let result = {};
    for (let node of dom.childNodes) parseNode(node, result);
    return result;
}
    6 Comments
Here's a nice xml2json and json2xml converter:
- http://goessner.net/download/prj/jsonxml/
 - Related tutorial: http://www.xml.com/pub/a/2006/05/31/converting-between-xml-and-json.html
 
Here's another one:
Depending on your needs, you might be able to use a standard parser (see http://www.w3schools.com/XML/tryit.asp?filename=tryxml_parsertest2) and xpath (http://www.w3schools.com/xpath/default.asp) - here's an example:
and a few nice tutorials:
1 Comment
Going straight to the point (using node-xml2json):
npm install xml2json
Then, use it:
const parser = require('xml2json');
const obj = parser.toJson(xml, { object: true });
Example:
const parser = require('xml2json');
const xml = '<root><person><name>Bob Dylan</name></person></root>';
const obj = parser.toJson(xml, { object: true });
const { person } = obj.root;
person.name; // Bob Dylan
You can also convert from JSON to XML, and much more.
Comments
I wanted a simple Typescript version that didn't create additional #text objects and also disregarded attributes. If that's what you need, here's the code:
export class DomFuncs {
    static parseNode = (node: Node) => {    
        const childNodes = node.childNodes;
        if (childNodes.length === 0) {
            return node.nodeValue;
        } else if (childNodes.length === 1 && childNodes[0].nodeType === Node.TEXT_NODE) {
            return childNodes[0].nodeValue;
        } else {
            const obj = {};
            childNodes.forEach(childNode => {
                const childName = childNode.nodeName;
                const childValue = obj[childName];
                if (childValue !== undefined) {
                    if (Array.isArray(childValue)) {
                        childValue.push(DomFuncs.parseNode(childNode));
                    } else {
                        obj[childName] = [childValue, DomFuncs.parseNode(childNode)];
                    }
                } else {
                    obj[childName] = DomFuncs.parseNode(childNode);
                }
            });
            return obj;
        }
    };
    static xml2obj = (str: string) => {
        const dom = (new DOMParser()).parseFromString(str, 'text/xml')
        const result = {[dom.nodeName]: DomFuncs.parseNode(dom)};
        return result;
    }
}
To use it:
DomFuncs.xml2obj(xmlString);
This script currently disregards XML attributes since my converted object didn't require them. If you need that, let me know and I could update the code.
Comments
The xml2json javascript file from https://bitbucket.org/surenrao/xml2json is all you need to do this.
Here's the download link for quick download: https://bitbucket.org/surenrao/xml2json/get/0e0989dfe48e.zip
Once included in your project, here's some sample code to get you started:
var xmlStr = "<root><person><name>Bob Dylan</name></person></root>";
var jsObj = X2J.parseXml(xmlStr);
var result = jsObj[0].root[0].person[0].name[0].jValue; //Bob Dylan