XML → JSON Converter
Convert XML to JSON online
Paste XML on the left and get clean, ready-to-use JSON on the right — attributes preserved, numbers parsed, repeated tags turned into arrays. Validated live, all in your browser.
🔒 100% private — conversion happens entirely in your browser. Nothing is uploaded or stored.
Turn XML into usable JSON instantly
Indentio parses your XML and emits tidy JSON the moment the input is well-formed. If a tag is unclosed or mismatched, the exact line and column is highlighted on the left so you can fix it before converting.
This is the more common direction of travel — a SOAP response, an RSS feed, a vendor export, or a legacy config that has to be consumed by JavaScript or stored in a document database. It is also the lossier direction, because XML can express several things JSON has no room for. The sections below spell out exactly what changes, so you can check the output rather than assume it.
The mapping rules
- Elements → JSON keys, nested to match the document.
- Attributes → keys prefixed with
@_. - Repeated sibling tags → JSON arrays.
- Element text alongside attributes → a
#textkey. - Numbers & booleans → real JSON numbers and booleans, not strings.
- Empty elements → an empty string.
- Comments and processing instructions → dropped.
A worked example
<order id="A-417" currency="EUR">
<!-- placed by the web checkout -->
<customer>Ada Lovelace</customer>
<item sku="X1"><qty>2</qty></item>
<item sku="X2"><qty>1</qty></item>
</order>becomes:
{
"order": {
"@_id": "A-417",
"@_currency": "EUR",
"customer": "Ada Lovelace",
"item": [
{ "@_sku": "X1", "qty": 2 },
{ "@_sku": "X2", "qty": 1 }
]
}
}The comment is gone, the two <item> elements collapsed into an array, and<qty>2</qty> became the number 2 rather than the string"2".
The single-element array trap
This is the bug that bites almost everyone who consumes converted XML in production, and it is worth understanding before you ship anything against this output. XML represents a list by repeating a tag — but a list of one is just one tag, indistinguishable from a plain single element. So the same document shape produces two different JSON shapes depending on how much data it happens to contain:
<!-- two items --> "item": [ {…}, {…} ] ← array
<!-- one item --> "item": {…} ← object, not an array!
<!-- no items --> (key absent entirely)Code written as data.order.item.map(…) works perfectly against a test fixture with two items and throws “item.map is not a function” in production the first time an order contains one. It is not a flaw in the conversion — the information genuinely is not present in the XML — but it is a trap. Defend against it by normalising at the boundary:
const items = [].concat(data.order.item ?? []);That one line gives you an array in all three cases. If you control the schema instead, wrapping repeated elements in a container such as<items><item/></items> makes the intent explicit and removes the ambiguity at the source.
Automatic type conversion, and when to distrust it
Turning <qty>2</qty> into a number is usually what you want. XML has no types of its own, so the converter has to guess from the text — and there are strings where guessing is wrong:
| XML text | Becomes | Why it can be wrong |
|---|---|---|
007 | 7 | Leading zeros are lost — bad for account codes and zero-padded ids. |
+441234567890 | 441234567890 | Phone numbers lose the leading plus. |
1.10 | 1.1 | A version string silently becomes a different version. |
00123456789012345678 | imprecise | Beyond 253 a JSON number loses precision. |
1e5 | 100000 | A product code in scientific-looking form gets expanded. |
NO | "NO" | Norway’s country code stays a string here — but beware libraries that coerce it to false. |
If any of these appear in your data, treat the affected fields as strings downstream rather than relying on the converted value.
What XML has that JSON does not
- Comments and processing instructions — no JSON equivalent, so they are dropped. If a document carries meaning in comments, convert with that in mind.
- The attribute/element distinction — real and meaningful in XML, flattened to a naming convention in JSON.
<a id="1"/>and<a><id>1</id></a>are different documents that differ only by a prefix once converted. - Document order across different element names — JSON objects preserve insertion order in practice, but a schema that depends on interleaved ordering has no reliable JSON representation.
- Mixed content — text and elements side by side, as in
<p>See <b>this</b> page</p>, cannot be represented faithfully. The text and the child element end up as separate keys and the interleaving is lost. This is why RSS descriptions containing HTML are conventionally wrapped in CDATA and treated as one opaque string. - Namespaces — the prefix survives inside the key name, but the binding to its URI does not, so two documents using different prefixes for the same namespace convert to different JSON.
- CDATA — the contents survive; the fact that it was a CDATA section does not.
Good to know
- The input must be well-formed XML — invalid input is pinpointed with a red underline before any conversion happens.
- Works with any XML dialect: SVG, RSS, Atom, XSD, WSDL, sitemaps,
pom.xml, and more. - Whitespace-only text between elements is discarded, so indented input does not produce noise in the output.
- Need the reverse? Use the JSON to XML converter, which uses the same
@_convention.
Go deeper
Frequently asked questions
How do I convert XML to JSON?
Paste your XML on the left. As soon as it’s well-formed, the JSON appears on the right automatically. Then click Copy result or Download.
How are XML attributes represented in JSON?
Attributes become keys prefixed with @_ (for example id="1" becomes "@_id": 1), and element text becomes the value or a #text key when an element also has attributes.
Does it parse numbers and booleans?
Yes. Values that look like numbers or booleans are converted to real JSON numbers and booleans, so <price>9.95</price> becomes "price": 9.95.
What about repeated tags?
Repeated sibling elements with the same name become a JSON array automatically. Be aware that an element appearing only once becomes a plain object rather than a one-item array — see the section on this above, because it is the most common source of bugs in code that consumes converted XML.
Are comments and namespaces preserved?
Comments and processing instructions are dropped — JSON has no way to represent them. Namespace prefixes are kept as part of the key name, so <dc:creator> becomes the key "dc:creator".
Is my XML kept private?
Yes — everything runs locally in your browser. Your XML is never uploaded or stored.