An MCP-powered AI diagramming app built with CopilotKit and modified Excalidraw MCP server. Describe anything in chat and get a fully editable Excalidraw diagram back in seconds.
ExcalidrawStudio.mp4
- Diagrams render as actual Excalidraw elements via MCP Apps
- Every result opens as a full editable local canvas - drag, reshape, annotate freely
- Every diagram auto-saves to disk - no database needed, Redis supported for Vercel if you wish to deploy
- Workspaces page to browse, rename, and delete all your saved diagrams
- One click to push any diagram live to Excalidraw straight from chat
# install dependencies
npm install
cd server && npm install && npm run build && cd ..
# run
npm run dev # → http://localhost:3000
cd server && npm run serve # → http://localhost:3001Create .env.local in the root and add your OpenAI API key.
OPENAI_API_KEY=sk-proj-...
If you want to use a different LLM, pass the model string to BuiltInAgent in src/app/api/copilotkit/route.ts. Everything else stays the same.
// Anthropic
const builtInAgent = new BuiltInAgent({ model: "anthropic:claude-sonnet-4-6" });
// Google
const builtInAgent = new BuiltInAgent({ model: "google:gemini-2.5-flash" });Add the matching API key to .env.local and you are done (for instance ANTHROPIC_API_KEY=sk-ant-). For Azure OpenAI, AWS Bedrock, Ollama and other providers, see the model selection docs.
├── src/
│ └── app/
│ ├── page.tsx ← chat UI and welcome screen
│ ├── workspace/[id]/ ← full Excalidraw editor
│ ├── workspaces/ ← saved diagrams list
│ ├── api/copilotkit/ ← CopilotKit runtime and agent
│ ├── api/checkpoints/ ← list all saved checkpoints
│ └── api/checkpoint/[id]/ ← get, update, delete a checkpoint
└── server/
└── src/
├── main.ts ← HTTP server, REST endpoints
├── server.ts ← MCP tools (read_me, create_view)
└── checkpoint-store.ts ← file, memory, and Redis storage
The agent calls create_view on the MCP server with a JSON array of Excalidraw elements. The server saves them as a checkpoint and returns an iframe URL. CopilotKit renders that iframe in chat via the MCP Apps protocol. The widget turns the elements into an SVG using exportToSvg and updates it live with morphdom as new elements arrive.
Each checkpoint is a JSON file on disk (default) or in Redis (Vercel), keyed by an 18-char ID. Opening a diagram in Workspace loads that checkpoint via REST and mounts the full editable Excalidraw canvas. Edits debounce-save back automatically.
| Chat UI | CopilotKit v2 - CopilotChat, MCPAppsMiddleware |
| Agent | BuiltInAgent connecting directly to LLM |
| Diagram rendering | @excalidraw/excalidraw - exportToSvg + morphdom |
| MCP transport | @modelcontextprotocol/sdk Streamable HTTP |
| Storage | File system (local) / Upstash Redis (Vercel) |
| Frontend | Next.js 15, Tailwind CSS 4 |
| Variable | Default | |
|---|---|---|
OPENAI_API_KEY |
required | |
MCP_SERVER_URL |
http://localhost:3001/mcp |
MCP server endpoint |
KV_REST_API_URL |
Upstash Redis URL for Vercel | |
KV_REST_API_TOKEN |
Upstash Redis token for Vercel |
The Next.js app deploys to Vercel out of the box. The MCP server runs as a separate service on Docker, Railway, or Render. For Vercel deployments, use the included api/mcp.ts handler with createVercelStore() for Redis-backed persistence.
MIT