Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
Function to convert XML to JSON
/**
* Changes XML to JSON
* Modified version from here: http://davidwalsh.name/convert-xml-json
* @param {string} xml XML DOM tree
*/
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 all text nodes inside, get concatenated text from them.
var textNodes = [].slice.call(xml.childNodes).filter(function(node) {
return node.nodeType === 3;
});
if (xml.hasChildNodes() && xml.childNodes.length === textNodes.length) {
obj = [].slice.call(xml.childNodes).reduce(function(text, node) {
return text + node.nodeValue;
}, "");
} else 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;
}
/*
Usage:
1. If you have an XML file URL:
const response = await fetch('file_url');
const xmlString = await response.text();
var XmlNode = new DOMParser().parseFromString(xmlString, 'text/xml');
xmlToJson(XmlNode);
2. If you have an XML as string:
var XmlNode = new DOMParser().parseFromString(yourXmlString, 'text/xml');
xmlToJson(XmlNode);
3. If you have the XML as a DOM Node:
xmlToJson(YourXmlNode);
*/
@ScottBeeson

This comment has been minimized.

Copy link

commented May 17, 2016

I love you.

@lionel-augustelouis

This comment has been minimized.

Copy link

commented Jan 24, 2017

Hi,
First thank you for the code ;)

Maybe an update that could help.
line.23 : Just add this && !obj["@attributes"] to keep attributes when node is type === 3 (text)

@charith93

This comment has been minimized.

Copy link

commented Mar 3, 2017

Hi,

Need a help urgently.
I am getting an error as "xml.hasChildNodes is not a function".

Will be very thankful if you could help me.

@salshyn

This comment has been minimized.

Copy link

commented Apr 4, 2017

Having the same issue as @charith93.

@LuceroGera

This comment has been minimized.

Copy link

commented Apr 24, 2017

Hello,
I have the same issue as @charith93 & @salshyn, someone can help us please?

Thanks.

@vivekannan

This comment has been minimized.

Copy link

commented May 6, 2017

@charith93 @LuceroGera @salshyn my guess is you are passing a string instead of a XML-DOM obj. Try this instead,

var xml = "The XML as String";
var xmlDOM = new DOMParser().parseFromString(xml, 'text/xml');

and then,

xmlToJson(xmlDOM);

@jasminejeane

This comment has been minimized.

Copy link

commented May 31, 2017

@vivekannan worked like a charm. Thank you

@maxIrvine

This comment has been minimized.

Copy link

commented Jul 18, 2017

Super helpful! Thank you!

@vibhorejaiswal

This comment has been minimized.

Copy link

commented Jul 19, 2017

Thank you very much !!

It worked great !!

@ashishsurana

This comment has been minimized.

Copy link

commented Aug 28, 2017

Everything worked great but I was not able to parse it completely.
in XML i had data like <ekey pi="308309309">here_it_contains_the_ekey</ekey>
and in JSON, I'm getting the only {ekey : "here_it_contains_the_ekey"}
there is no existence of pi in parsed object

@theo-armour

This comment has been minimized.

Copy link

commented Sep 4, 2017

I had to delete the @ in front of attributes in order to get to the data using JavaScript objects dot notation

Otherwise, it just works. Bonus points for the code being almost simple enough for me to understand.

@ghost

This comment has been minimized.

Copy link

commented Sep 6, 2017

AAAAAAAHHHHHHHHH!!!
I can kiss you!

json.LE.math.image.textML.en is so much better than
xmlDoc.getElementsByTagName("LE")[0].getElementsByTagName("math")[0].getElementsByTagName("image")[0].getElementsByTagName("textML")[0].getElementsByTagName("en")[0].innerHTML

No fuss. It just worked also...

@baladkb

This comment has been minimized.

Copy link

commented Oct 12, 2017

Hi @chinchang, how we can convert XML file to JSON string?

@truongphucuong

This comment has been minimized.

Copy link

commented Oct 18, 2017

Hello @chinchang,
I have the same issue as @baladkb, how we can convert XML file to JSON string and convert JSON string to XML file ???
Help Me !!!

@linhnt2803

This comment has been minimized.

Copy link

commented Oct 30, 2017

Love you <3 <3

@satriowibowo123

This comment has been minimized.

Copy link

commented Oct 31, 2017

Thank You very much @chinchang

@demircancelebi

This comment has been minimized.

Copy link

commented Nov 21, 2017

In case someone needs it, here is the ES6 version:

https://gist.github.com/demircancelebi/f0a9c7e1f48be4ea91ca7ad81134459d

@chhonmeily

This comment has been minimized.

Copy link

commented Jun 7, 2018

THANK YOU SO MUCH!!! GOD BLESS YOU!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

@Teclogen

This comment has been minimized.

Copy link

commented Sep 5, 2018

Your Logic Building is strong. Keep it Up

@iPzard

This comment has been minimized.

Copy link

commented Nov 29, 2018

You're a lifesaver!

@IlkerKadir

This comment has been minimized.

Copy link

commented Jan 23, 2019

Worked like a charm

@mombe090

This comment has been minimized.

Copy link

commented Jan 24, 2019

Wow Wow Wow Wow Wow guy u are a king @loveUGuy

@varadekd

This comment has been minimized.

Copy link

commented Feb 22, 2019

I am using the same code But when I am using the same code inside try and catch it is failing. The code was working fine but after updating node to 11.10.0, npm 6.8.0 and appium 1.11

@obisi7

This comment has been minimized.

Copy link

commented Apr 24, 2019

Thanks for the code. I tried using the final version within a fetch call as shown below but I am getting this error: "Fetch TypeError: (0, _xmlTpJson.default) is undefined. I can't find any insight to the error or how to fix it. Please help and thanks.

` getNews() {
const link = "https://feeds.feedburner.com/morganstateu";

return fetch(link)
  .then(response => response.text())
  .then(response => {
    let resJson = xmlToJson(response);
    this.setState({
      data: resJson.rss.channel[0].item,
      isLoading: false,
      refreshing: false,
      error: response.error || null
    });
  })
  .catch(error => {
    this.setState({ error, isLoading: false });
    // Alert.alert("Error", "Sorry, something went wrong. Please try again");
    console.log('fetch', error)
  });

}`

@Parth-Agarwal

This comment has been minimized.

Copy link

commented Jun 19, 2019

I love you.
👍 😄

@chinchang

This comment has been minimized.

Copy link
Owner Author

commented Jun 19, 2019

Updated with examples of how to use the function.

@chinchang

This comment has been minimized.

Copy link
Owner Author

commented Jun 19, 2019

@obisi7
You need to convert the response string into DOM before passing to xmlToJson:

let node = new DOMParser().parseFromString(response, 'text/xml')
let resJson = xmlToJson(node);
@themikesam

This comment has been minimized.

Copy link

commented Jul 13, 2019

how if contains cdata in a tags?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.