MCP Media Forge
MCP server that generates diagrams, charts, HTML pages, and slide decks from text DSLs -- designed for AI coding agents to embed into Markdown.
LLM agents call tools like render_mermaid, render_html_page, or render_slides with text input, and get back file paths to assets ready to embed in docs.
Output Gallery
Mermaid Flowchart
Mermaid Sequence Diagram
D2 Architecture Diagram
Graphviz Dependency Graph
Vega-Lite Bar Chart
Tools
Diagram & Chart Renderers (Docker)
HTML Generators (No Docker)
Utilities
Quick Start
1. Start the rendering container (for diagram tools)
cd docker
docker compose up -d
HTML page and slide tools work without Docker.
2. Install the MCP server
Option A -- npx (no install)
npx mcp-media-forge
Option B -- Clone and build
git clone https://github.com/PavelGuzenfeld/mcp-media-forge.git
cd mcp-media-forge
npm install
npm run build
3. Register with your MCP client
Any MCP-compatible client (Claude Code, Cursor, VS Code + Copilot, Cline, etc.) can use this server. The standard config:
{
"mcpServers": {
"media-forge": {
"command": "node",
"args": ["/path/to/mcp-media-forge/dist/index.js"],
"env": {
"PROJECT_ROOT": "/path/to/your/project"
}
}
}
}
Where to add this depends on your client:
- Claude Code:
~/.claude/settings.json - Cursor: MCP settings panel
- VS Code (Copilot):
.vscode/mcp.json - Cline: MCP server configuration
4. Use it
Ask your AI assistant to generate diagrams, pages, or presentations:
"Create a sequence diagram showing the OAuth2 flow and embed it in the README"
"Generate an HTML page summarizing the API architecture with KPI cards"
"Make a slide deck with our Q1 metrics and architecture overview"
The agent calls the appropriate tool, gets back a file path, and embeds it in your markdown.
How It Works
AI Agent (any MCP client)
|
| MCP Protocol (JSON-RPC over stdio)
v
MCP Media Forge (Node.js on host)
|
|--- Diagrams: docker exec (sandboxed, no network)
| |
| v
| Rendering Container
| ├── mmdc (Mermaid CLI + Chromium)
| ├── d2 (D2 diagrams)
| ├── dot/neato (Graphviz)
| └── vl2svg (Vega-Lite via vl-convert)
|
|--- HTML/Slides: template engine (no Docker)
| |
| v
| CSS Design System (4 themes, depth tiers, components)
|
v
docs/generated/
mermaid-a1b2c3.svg
d2-7f8e9a.svg
html_page-d4e5f6.html
slides-8b9c0d.html
Key design decisions:
- Text in, file path out -- returns relative paths, never base64 blobs
- Content-hash naming -- same input = same file = free caching + git-friendly
- SVG preferred -- vector format, small files, diffs cleanly in git
- Docker-contained -- diagram renderers run in a sandboxed container with
network_mode: none - Self-contained HTML -- pages and slides have zero external dependencies (inline CSS/JS)
- Input pre-validation -- catches common mistakes before Docker round-trips
- Structured errors -- error responses include
error_type,error_message, andsuggestionto enable LLM self-correction
Tool Reference
get_tool_guide
Get usage guide for any tool before rendering. Returns examples, anti-patterns to avoid, complexity limits, and tips.
{ "tool_name": "mermaid" }
Available guides: mermaid, d2, graphviz, vegalite, html_page, slides, or all for a summary.
render_mermaid
{
"code": "flowchart TD\n A[Start] --> B{Decision}\n B -->|Yes| C[Done]",
"format": "svg",
"theme": "default"
}
Pre-validation catches: missing diagram type, semicolons, HTML in labels, >25 nodes.
render_d2
{
"code": "client -> server -> database",
"format": "svg",
"layout": "dagre"
}
Pre-validation catches: Mermaid/D2 syntax confusion, unbalanced braces, >3 nesting depth.
render_graphviz
{
"dot_source": "digraph G { A -> B -> C }",
"engine": "dot",
"format": "svg"
}
Pre-validation catches: missing graph wrapper, -> in undirected graphs, unbalanced braces.
render_chart
{
"spec_json": "{\"$schema\":\"https://vega.github.io/schema/vega-lite/v5.json\",\"data\":{\"values\":[{\"x\":1,\"y\":10}]},\"mark\":\"bar\",\"encoding\":{\"x\":{\"field\":\"x\"},\"y\":{\"field\":\"y\"}}}",
"format": "svg"
}
Pre-validation catches: invalid JSON, missing $schema/data/mark, >500 inline data rows.
render_html_page
Generates a self-contained themed HTML page. No Docker required.
{
"title": "System Overview",
"body_html": "<section id=\"metrics\"><h2>Metrics</h2><div class=\"mf-grid mf-grid-3\">...</div></section>",
"theme": "swiss",
"description": "Q1 architecture overview",
"nav_sections": ["Metrics", "Architecture", "Roadmap"]
}
Design system CSS classes:
Themes:
render_slides
Generates a self-contained HTML slide deck with keyboard/touch navigation. No Docker required.
{
"title": "Q1 Review",
"slides": "[{\"title\":\"Q1 Review\",\"content\":\"Engineering update\",\"type\":\"title\"},{\"title\":\"Metrics\",\"content\":\"<ul><li>99.9% uptime</li></ul>\",\"type\":\"content\"}]",
"theme": "midnight",
"author": "Engineering Team"
}
Slide types:
Navigation: Arrow keys, Space, PageUp/PageDown, Home/End. Touch: swipe left/right. Click dots to jump.
list_assets
{ "directory": "" }
Returns a JSON array of all generated files with name, path, size, and modification time.
Error Handling
All tools return structured errors that help LLMs self-correct:
{
"status": "error",
"error_type": "syntax_error",
"error_message": "First line must declare diagram type. Got: \"A --> B\"",
"suggestion": "Start with: flowchart TD, sequenceDiagram, erDiagram, ... See https://mermaid.js.org/syntax/"
}
Error types: syntax_error, rendering_error, dependency_missing.
Pre-validation catches common LLM mistakes before hitting the renderer:
- Mermaid: missing diagram type, semicolons, HTML tags, legacy
graphsyntax - D2: Mermaid syntax confusion (
-->,subgraph), unbalanced braces - Graphviz: missing
digraph/graphwrapper,->in undirected graphs - Vega-Lite: invalid JSON, missing required fields, oversized inline data
Environment Variables
Development
npm install
npm run build # Build with tsup
npm run dev # Watch mode
npm test # Run all tests (95 total)
npm run test:unit # Unit tests only (no Docker needed)
npm run test:component # Integration tests (Docker tools need container)
npm run lint # Type-check with tsc
Running integration tests
cd docker && docker compose up -d # Start renderer (diagram tools only)
cd .. && npm run test:component # All integration tests
HTML page and slide integration tests run without Docker.
Examples
See examples/ for sample input files:
See examples/README.md for MCP tool call examples and expected responses.