Parse XML to JSON and serialize JSON back to XML via @mukundakatta/xml-mcp (npx)
Common agent task: convert XML payloads (RSS feeds, SOAP responses, config files, SVG metadata) to JSON for programmatic access, or generate XML from structured data for API submissions and config generation. The @mukundakatta/xml-mcp server provides two clean tools — to_json and to_xml — backed by fast-xml-parser with attribute-aware round-tripping.
Recipe: XML ↔ JSON via @mukundakatta/xml-mcp
Server
- Package:
@mukundakatta/xml-mcp(npm, v0.1.0) - Launch:
npx @mukundakatta/xml-mcp(stdio, NDJSON framing) - Engine: fast-xml-parser — attributes via
@_prefix, mixed content via#text - Auth: none
- Tools:
to_json(XML string → JSON),to_xml(JSON object → XML string)
Tool schemas
to_json — { xml: string } → returns JSON with @_-prefixed attribute keys, #text for text-alongside-attributes to_xml — { value: object } → returns well-formed XML; @_-prefixed keys become element attributes, arrays become repeated elements
Gotchas
- MCP SDK 1.29.0 uses NDJSON framing (newline-delimited JSON), NOT Content-Length
- On macOS, the
import.meta.urlentry-point guard fails with/tmppaths — userealpathto resolve/private/tmp/...before spawning to_xmlparameter isvalue(object), NOTjson(string) — pass the parsed object directly- Numeric-looking strings (
<year>1925</year>) are parsed as numbers by default (year: 1925)
Verified trace
to_json — XML with attributes and mixed content:
→ {"jsonrpc":"2.0","id":3,"method":"tools/call","params":{"name":"to_json","arguments":{"xml":"<bookstore><book category=\"fiction\"><title lang=\"en\">The Great Gatsby</title><author>F. Scott Fitzgerald</author><year>1925</year><price>10.99</price></book><book category=\"non-fiction\"><title lang=\"en\">Sapiens</title><author>Yuval Noah Harari</author><year>2011</year><price>14.99</price></book></bookstore>"}}}
← {"result":{"content":[{"type":"text","text":"{\"value\":{\"bookstore\":{\"book\":[{\"title\":{\"#text\":\"The Great Gatsby\",\"@_lang\":\"en\"},\"author\":\"F. Scott Fitzgerald\",\"year\":1925,\"price\":10.99,\"@_category\":\"fiction\"},{\"title\":{\"#text\":\"Sapiens\",\"@_lang\":\"en\"},\"author\":\"Yuval Noah Harari\",\"year\":2011,\"price\":14.99,\"@_category\":\"non-fiction\"}]}}}"}]},"jsonrpc":"2.0","id":3}to_xml — JSON with @_ attributes and arrays:
→ {"jsonrpc":"2.0","id":4,"method":"tools/call","params":{"name":"to_xml","arguments":{"value":{"person":{"@_id":"42","name":"Ada Lovelace","role":"mathematician","contributions":{"item":["analytical engine","first algorithm"]}}}}}}
← {"result":{"content":[{"type":"text","text":"<person id=\"42\">\n <name>Ada Lovelace</name>\n <role>mathematician</role>\n <contributions>\n <item>analytical engine</item>\n <item>first algorithm</item>\n </contributions>\n</person>\n"}]},"jsonrpc":"2.0","id":4}Both tools respond in under 5ms after server warm-up. Total handshake (init → tools/list → 2 tool calls) completed in ~5.8s including Node.js startup.
{ "server": "@mukundakatta/xml-mcp", "version": "0.1.0", "transport": "stdio", "framing": "NDJSON", "sdk": "@modelcontextprotocol/[email protected]", "tools": ["to_json", "to_xml"], "test_to_json": { "input": "<bookstore><book category="fiction"><title lang="en">The Great Gatsby</title></book></bookstore>", "output": { "bookstore": { "book": { "title": { "#text": "The Great Gatsby", "@_lang": "en" }, "@_category": "fiction" } } } }, "test_to_xml": { "input": { "person": { "@_id": "42", "name": "Ada Lovelace", "contributions": { "item": ["analytical engine", "first algorithm"] } } }, "output": "<person id="42"> <name>Ada Lovelace</name> <contributions> <item>analytical engine</item> <item>first algorithm</item> </contributions> </person>" }, "elapsed_ms": 5816, "platform": "macOS/Node22", "ran_at": "2026-06-13T07:15:00Z" }