Executive brief
xmldom is a popular JavaScript XML/DOM library used to build and serialize XML documents. When applications construct DOM elements from untrusted input (via `createElement()`), an attacker can inject malicious attributes and event handlers that execute as JavaScript when the serialized XML is consumed by a browser—a cross-site scripting (XSS) attack. The library's recommended security control (`requireWellFormed: true`) was supposed to block this but did not, leaving applications relying on that mitigation unprotected.
Technical details
The vulnerability is an element-name injection flaw in the `Document.createElement()` method. `createElement()` accepts arbitrary strings as the `tagName` parameter without validation, storing the raw input directly on the element node. When `XMLSerializer.serializeToString()` is called, the tag name is emitted verbatim into the serialized output (e.g., `<img src=x onerror="alert(1)"/>`). The XML and DOM specifications require element names to conform to the `Name` and `QName` productions, but this validation was missing from both the creation and serialization paths. Although `createElementNS()` and the `requireWellFormed: true` serializer option performed validation on qualified names, they did not validate element names in `createElement()`, creating a bypass. The fix adds QName validation to the serializer's `requireWellFormed: true` code path, throwing `InvalidStateError` before emitting malformed names; however, this protection is opt-in and does not validate at element-creation time.
Affected products
- xmldom @xmldom/xmldom >= 0.9.0, <= 0.9.10; >= 0.7.0, <= 0.8.13
- xmldom xmldom <= 0.6.0
Timeline
- 2026-09-08: disclosed: Vulnerability published by GitHub Advisory Database
- 2026-09-08: patched: Fixed in @xmldom/xmldom 0.9.11 and 0.8.14 under requireWellFormed: true option (opt-in)