-
Notifications
You must be signed in to change notification settings - Fork 499
Mermaid v11 diagrams render empty nodes — DOMParser('image/svg+xml') strips foreignObject HTML content #37
Description
Bug
The Mermaid zoom/pan JS pattern in references/css-patterns.md uses DOMParser.parseFromString(svg, 'image/svg+xml') to insert rendered Mermaid SVGs into the DOM. This silently destroys all node labels when using Mermaid v11+.
Root cause
Mermaid v11 renders node labels using <foreignObject> containing HTML <div> elements (not <text> elements). When DOMParser parses this SVG string as image/svg+xml, the HTML namespace content inside <foreignObject> is treated as invalid XML and stripped. The result:
- Subgraph cluster frames render (their labels use a different mechanism)
- Individual nodes render as empty boxes with no labels
- Edges render but without visible connections to invisible nodes
- The SVG has a valid viewBox and dimensions — it looks like a partial render
Reproduction
const result = await mermaid.render(id, 'graph LR\n A["Hello"] --> B["World"]');
// BUG: 0 nodes visible — foreignObject HTML stripped
const parser = new DOMParser();
const doc = parser.parseFromString(result.svg, 'image/svg+xml');
console.log(doc.querySelectorAll('parsererror').length); // 1
console.log(doc.querySelectorAll('.node').length); // 0 or 1
// FIX: 2 nodes visible — mixed namespaces preserved
container.innerHTML = result.svg;
const svg = container.querySelector('svg');
console.log(svg.querySelectorAll('.node').length); // 2Affected code
In references/css-patterns.md, the render function around the "JavaScript" section under "Mermaid Zoom Controls":
// CURRENT (broken with Mermaid v11)
const { svg } = await mermaid.render(id, code);
const parser = new DOMParser();
const doc = parser.parseFromString(svg, 'image/svg+xml');
canvas.appendChild(document.adoptNode(doc.documentElement));
// FIX
const { svg } = await mermaid.render(id, code);
canvas.innerHTML = svg;
const svgEl = canvas.querySelector('svg');Verified with
- Chrome 146 (headless + headed)
- Mermaid v11 via CDN (
https://cdn.jsdelivr.net/npm/mermaid@11/dist/mermaid.min.js) - Diagnosed using WebDriverIO automation: before fix = 1 node/0 edges, after fix = 17 nodes/19 edges on a complex diagram with 6 subgraphs
Impact
Every diagram generated by the skill's template has invisible node labels. Only subgraph cluster titles are visible, making diagrams appear mostly empty.