Example
<library name="City">
<book id="1" available="true">
<title>Dune</title>
<year>1965</year>
</book>
<book id="2" available="false">
<title>Neuromancer</title>
<year>1984</year>
<note lang="en">Signed copy</note>
</book>
<manager/>
</library>
{
"library": {
"@name": "City",
"book": [
{
"@id": 1,
"@available": true,
"title": "Dune",
"year": 1965
},
{
"@id": 2,
"@available": false,
"title": "Neuromancer",
"year": 1984,
"note": {
"@lang": "en",
"#text": "Signed copy"
}
}
],
"manager": null
}
}
Conversion rules
| XML | JSON |
|---|---|
| Element with only text | String (or number / boolean) |
| Element with children or attributes | Object |
Attribute id="1" | "@id": "1" |
| Text next to attributes or children | "#text" key |
| Repeated element | Array |
Empty element <x/> | null |
| CDATA | Its text, unescaped |
Entities like & | Decoded characters |
| Comments, processing instructions | Dropped |
The single-element problem
With default settings, one <book> becomes an object, not an array:
{"library":{"book":{"title":"Dune"}}}
{"library":{"book":[{"title":["Dune"]}]}}
If your code loops over library.book, use Always use arrays, or normalize in code with
something like [].concat(library.book).
Convert XML to JSON in code
import { XMLParser } from 'fast-xml-parser';
const parser = new XMLParser({ ignoreAttributes: false, attributeNamePrefix: '@' });
const json = parser.parse(xml);
import json, xmltodict
data = xmltodict.parse(xml) # attributes as "@id", text as "#text"
print(json.dumps(data, indent=2))
These libraries use the same @ and #text conventions as this converter, so the output here
is a good preview of what your code will get. Need to tidy the XML first? Use the XML
formatter, then explore the JSON with the JSONPath tester.
Frequently asked questions
How do I convert XML to JSON?
Paste the XML into the converter above. Each element becomes a key, attributes become keys with an @ prefix, repeated elements become arrays and text becomes the value. Turn on Numbers and booleans to convert "42" and "true" into JSON numbers and booleans.
How are XML attributes represented in JSON?
As keys with a prefix, @ by default, so <book id="1"> becomes {"book": {"@id": "1"}}. The prefix keeps attributes apart from child elements with the same name. You can choose _ or no prefix to match what your code expects.
Why is an element sometimes an array and sometimes an object?
An element that appears once becomes a single value; one that repeats becomes an array. This means the JSON shape depends on the data: a list with one item looks different from a list with two. Turn on Always use arrays to make every child element an array so your code can handle both cases the same way.
What happens to an element with both attributes and text?
It becomes an object with the attributes as @ keys and the text under #text: <price currency="USD">9.99</price> becomes {"@currency": "USD", "#text": "9.99"}. An element with only text becomes a plain string, and an empty element becomes null.
Is the conversion reversible?
Mostly, but not exactly. JSON has no comments, processing instructions or ordering between different element names, and mixed content like <p>Hello <b>world</b></p> loses the position of the text relative to child elements. For data-style XML such as API responses and config files, nothing important is lost.