mcp-excalidraw-server 1.0.5 → 1.0.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +383 -358
- package/dist/frontend/assets/Assistant-Bold-gm-uSS1B.woff2 +0 -0
- package/dist/frontend/assets/Assistant-Medium-DrcxCXg3.woff2 +0 -0
- package/dist/frontend/assets/Assistant-Regular-DVxZuzxb.woff2 +0 -0
- package/dist/frontend/assets/Assistant-SemiBold-SCI4bEL9.woff2 +0 -0
- package/dist/frontend/assets/Tableau10-B-NsZVaP.js +1 -0
- package/dist/frontend/assets/_commonjs-dynamic-modules-TDtrdbi3.js +1 -0
- package/dist/frontend/assets/advancedFormat-BB0p-EFm.js +1 -0
- package/dist/frontend/assets/ar-SA-G6X2FPQ2-DQjC7E2l.js +10 -0
- package/dist/frontend/assets/arc-DeeplnFI.js +1 -0
- package/dist/frontend/assets/array-BKyUJesY.js +1 -0
- package/dist/frontend/assets/az-AZ-76LH7QW2-i2mid_KF.js +1 -0
- package/dist/frontend/assets/band-dPffDWoQ.js +1 -0
- package/dist/frontend/assets/bg-BG-XCXSNQG7-DEeQGR6G.js +5 -0
- package/dist/frontend/assets/blockDiagram-38ab4fdb-ft3Qmbnk.js +118 -0
- package/dist/frontend/assets/blockDiagram-68f4deed-BhATEkwK.js +118 -0
- package/dist/frontend/assets/bn-BD-2XOGV67Q-Cyoi_9HX.js +5 -0
- package/dist/frontend/assets/c4Diagram-15b5d702-D9y4gbPI.js +10 -0
- package/dist/frontend/assets/c4Diagram-3d4e48cf-JFijLclV.js +10 -0
- package/dist/frontend/assets/ca-ES-6MX7JW3Y-BVVWU1rs.js +8 -0
- package/dist/frontend/assets/channel-Cb5NStnu.js +1 -0
- package/dist/frontend/assets/classDiagram-70f12bd4-Ca9Kd1Ds.js +2 -0
- package/dist/frontend/assets/classDiagram-d40c83e7-Bq3MDvmx.js +2 -0
- package/dist/frontend/assets/classDiagram-v2-d5a6b087-o29qZ8vi.js +2 -0
- package/dist/frontend/assets/classDiagram-v2-f2320105-C9ex7BCO.js +2 -0
- package/dist/frontend/assets/clone-90Lq8jWj.js +1 -0
- package/dist/frontend/assets/createText-2e5e7dd3-FTBPE3EK.js +5 -0
- package/dist/frontend/assets/createText-d213de94-5nVTf_jC.js +5 -0
- package/dist/frontend/assets/cs-CZ-2BRQDIVT-BhMjw9tI.js +11 -0
- package/dist/frontend/assets/cytoscape-cose-bilkent-D2omlyvD.js +331 -0
- package/dist/frontend/assets/da-DK-5WZEPLOC-MfLFmlD6.js +5 -0
- package/dist/frontend/assets/de-DE-XR44H4JA-JhYak0I3.js +8 -0
- package/dist/frontend/assets/directory-open-01563666-DWU9wJ6I.js +1 -0
- package/dist/frontend/assets/directory-open-4ed118d0-BzWybGaI.js +1 -0
- package/dist/frontend/assets/edges-332bd1c7-DRJZgTC2.js +4 -0
- package/dist/frontend/assets/edges-e0da2a9e-BDwG7z0K.js +4 -0
- package/dist/frontend/assets/el-GR-BZB4AONW-Cdt2Ptk6.js +10 -0
- package/dist/frontend/assets/elk.bundled-D6I4pvAp.js +26 -0
- package/dist/frontend/assets/erDiagram-880f2ed8-C8waXJ0r.js +51 -0
- package/dist/frontend/assets/erDiagram-9861fffd-F9WuyAYm.js +51 -0
- package/dist/frontend/assets/es-ES-U4NZUMDT-C2-CtGrr.js +9 -0
- package/dist/frontend/assets/eu-ES-A7QVB2H4-CU_zCaYP.js +11 -0
- package/dist/frontend/assets/fa-IR-HGAKTJCU-Ck3uNCF1.js +8 -0
- package/dist/frontend/assets/fi-FI-Z5N7JZ37-B095Plv2.js +6 -0
- package/dist/frontend/assets/file-open-002ab408-DIuFHtCF.js +1 -0
- package/dist/frontend/assets/file-open-7c801643-684qeFg4.js +1 -0
- package/dist/frontend/assets/file-save-3189631c-x92wctJd.js +1 -0
- package/dist/frontend/assets/file-save-745eba88-Bb9F9Kg7.js +1 -0
- package/dist/frontend/assets/flowDb-7c981674-DuBfksmG.js +10 -0
- package/dist/frontend/assets/flowDb-956e92f1-CeLnP8Y5.js +10 -0
- package/dist/frontend/assets/flowDiagram-66a62f08-Bm4RJknB.js +4 -0
- package/dist/frontend/assets/flowDiagram-cbd28bf7-DGIWJa28.js +4 -0
- package/dist/frontend/assets/flowDiagram-v2-96b9c2cf-FcyWkMPn.js +1 -0
- package/dist/frontend/assets/flowDiagram-v2-ffc7f31a-BpjLoFsq.js +1 -0
- package/dist/frontend/assets/flowchart-elk-definition-36e2d292-Dpo4AMxk.js +114 -0
- package/dist/frontend/assets/flowchart-elk-definition-4a651766-ChOn_l6T.js +114 -0
- package/dist/frontend/assets/fr-FR-RHASNOE6-BqyLXGYl.js +9 -0
- package/dist/frontend/assets/ganttDiagram-04f9e578-CkdnwMOW.js +257 -0
- package/dist/frontend/assets/ganttDiagram-c361ad54-CJzn5gXR.js +257 -0
- package/dist/frontend/assets/gitGraphDiagram-21fc4d3e-CIOFS-AG.js +70 -0
- package/dist/frontend/assets/gitGraphDiagram-72cf32ee-Bcto3HlW.js +70 -0
- package/dist/frontend/assets/gl-ES-HMX3MZ6V-B7bR1uHP.js +10 -0
- package/dist/frontend/assets/graph-BHaTz2pM.js +1 -0
- package/dist/frontend/assets/graph-DsUM2NHp.js +1 -0
- package/dist/frontend/assets/he-IL-6SHJWFNN-DwXoH57J.js +10 -0
- package/dist/frontend/assets/hi-IN-IWLTKZ5I-D7SfqhT6.js +4 -0
- package/dist/frontend/assets/hu-HU-A5ZG7DT2-GZMnh_86.js +7 -0
- package/dist/frontend/assets/id-ID-SAP4L64H-CKj2F_pf.js +10 -0
- package/dist/frontend/assets/image-blob-reduce.esm-B6b2_-a4.js +7 -0
- package/dist/frontend/assets/index-3862675e-Bsb9vcL0.js +1 -0
- package/dist/frontend/assets/index-6079d271-Bvcb58DE.js +1 -0
- package/dist/frontend/assets/index-B9Rh8YyQ.css +1 -0
- package/dist/frontend/assets/index-C1JelwHC.js +349 -0
- package/dist/frontend/assets/index-CkitXLJb.js +87 -0
- package/dist/frontend/assets/index-DGmpr33w.js +3 -0
- package/dist/frontend/assets/infoDiagram-4a4f5b27-DYMh8eXF.js +7 -0
- package/dist/frontend/assets/infoDiagram-f8f76790-B2YXmH0v.js +7 -0
- package/dist/frontend/assets/init-Gi6I4Gst.js +1 -0
- package/dist/frontend/assets/it-IT-JPQ66NNP-woTcXUdD.js +11 -0
- package/dist/frontend/assets/ja-JP-DBVTYXUO-CGJZIn_N.js +8 -0
- package/dist/frontend/assets/journeyDiagram-29694f62-20n3n2ey.js +139 -0
- package/dist/frontend/assets/journeyDiagram-49397b02-Df2fBEZG.js +139 -0
- package/dist/frontend/assets/kaa-6HZHGXH3-BtBBG4jh.js +1 -0
- package/dist/frontend/assets/kab-KAB-ZGHBKWFO-CbxAj5W8.js +8 -0
- package/dist/frontend/assets/katex-ChWnQ-fc.js +261 -0
- package/dist/frontend/assets/kk-KZ-P5N5QNE5-fS-Upvvh.js +1 -0
- package/dist/frontend/assets/km-KH-HSX4SM5Z-BA1j7Xmb.js +11 -0
- package/dist/frontend/assets/ko-KR-MTYHY66A-CFvLJngn.js +9 -0
- package/dist/frontend/assets/ku-TR-6OUDTVRD-BkE-_tGQ.js +9 -0
- package/dist/frontend/assets/layout-D3_N-32k.js +1 -0
- package/dist/frontend/assets/layout-D56ApGxy.js +1 -0
- package/dist/frontend/assets/line-Dq_sNFvr.js +1 -0
- package/dist/frontend/assets/linear-BaWzW4O4.js +1 -0
- package/dist/frontend/assets/lt-LT-XHIRWOB4-BSnb0UTH.js +3 -0
- package/dist/frontend/assets/lv-LV-5QDEKY6T-CLjiMRc2.js +7 -0
- package/dist/frontend/assets/mindmap-definition-ac74a2e8-BY3Tg6Pe.js +95 -0
- package/dist/frontend/assets/mindmap-definition-fc14e90a-CLKKSvyA.js +95 -0
- package/dist/frontend/assets/mr-IN-CRQNXWMA-D9DBZK36.js +13 -0
- package/dist/frontend/assets/my-MM-5M5IBNSE-DpU38Yme.js +1 -0
- package/dist/frontend/assets/nb-NO-T6EIAALU-C510_VhX.js +10 -0
- package/dist/frontend/assets/nl-NL-IS3SIHDZ-CTxHa7fQ.js +8 -0
- package/dist/frontend/assets/nn-NO-6E72VCQL-BrJEF_cT.js +8 -0
- package/dist/frontend/assets/oc-FR-POXYY2M6-BQ6jh9ah.js +8 -0
- package/dist/frontend/assets/ordinal-Cboi1Yqb.js +1 -0
- package/dist/frontend/assets/pa-IN-N4M65BXN-DHhO4NEC.js +4 -0
- package/dist/frontend/assets/path-CbwjOpE9.js +1 -0
- package/dist/frontend/assets/pica-CofPkJ36.js +7 -0
- package/dist/frontend/assets/pie-lyWsw7iq.js +1 -0
- package/dist/frontend/assets/pieDiagram-421022e6-CT-muZCn.js +35 -0
- package/dist/frontend/assets/pieDiagram-8a3498a8-DtYj6G3V.js +35 -0
- package/dist/frontend/assets/pl-PL-T2D74RX3-CwxEKsFG.js +9 -0
- package/dist/frontend/assets/pt-BR-5N22H2LF-MbElHXpG.js +9 -0
- package/dist/frontend/assets/pt-PT-UZXXM6DQ-DM4vWcwF.js +9 -0
- package/dist/frontend/assets/quadrantDiagram-0957ecba-CblbtN7K.js +7 -0
- package/dist/frontend/assets/quadrantDiagram-120e2f19-jzz3ehZq.js +7 -0
- package/dist/frontend/assets/requirementDiagram-23d650b8-C-JoH6A7.js +52 -0
- package/dist/frontend/assets/requirementDiagram-deff3bca-Ctl4rNQu.js +52 -0
- package/dist/frontend/assets/ro-RO-JPDTUUEW-DdMtPkP_.js +11 -0
- package/dist/frontend/assets/roundRect-0PYZxl1G.js +1 -0
- package/dist/frontend/assets/ru-RU-B4JR7IUQ-DFOiB9Jg.js +9 -0
- package/dist/frontend/assets/sankeyDiagram-04a897e0-CUAS8b8U.js +8 -0
- package/dist/frontend/assets/sankeyDiagram-23345273-CjwxDsME.js +8 -0
- package/dist/frontend/assets/sankeyLinkHorizontal-DgqkLiUE.js +1 -0
- package/dist/frontend/assets/selectAll-BMyQi_9w.js +1 -0
- package/dist/frontend/assets/sequenceDiagram-17ac3bff-BhnIexBX.js +122 -0
- package/dist/frontend/assets/sequenceDiagram-704730f1-DZhrMzp5.js +122 -0
- package/dist/frontend/assets/si-LK-N5RQ5JYF-CoNWh4qU.js +1 -0
- package/dist/frontend/assets/sk-SK-C5VTKIMK-Cv5NV02v.js +6 -0
- package/dist/frontend/assets/sl-SI-NN7IZMDC-C_vlgIOB.js +6 -0
- package/dist/frontend/assets/stateDiagram-587899a1-CACHP_Jt.js +1 -0
- package/dist/frontend/assets/stateDiagram-9c5f0230-DsuPkPjh.js +1 -0
- package/dist/frontend/assets/stateDiagram-v2-51a3dcff-B5h534aI.js +1 -0
- package/dist/frontend/assets/stateDiagram-v2-d93cdb3a-Dm93b3N0.js +1 -0
- package/dist/frontend/assets/styles-2ab5d517-DsYBO0WP.js +116 -0
- package/dist/frontend/assets/styles-5f03d8d2-LS13RtPA.js +160 -0
- package/dist/frontend/assets/styles-6aaf32cf-KUcsVvLX.js +207 -0
- package/dist/frontend/assets/styles-9a916d00-BjTkeUBK.js +160 -0
- package/dist/frontend/assets/styles-c10674c1-0477ds-x.js +116 -0
- package/dist/frontend/assets/styles-edf9a4b0-DxfsUCVO.js +207 -0
- package/dist/frontend/assets/subset-shared.chunk.js +84 -0
- package/dist/frontend/assets/subset-worker.chunk.js +1 -0
- package/dist/frontend/assets/sv-SE-XGPEYMSR-BILGi8-a.js +10 -0
- package/dist/frontend/assets/svgDrawCommon-08f97a94-DK3eIkMD.js +1 -0
- package/dist/frontend/assets/svgDrawCommon-3ba9043b-CnkFvHbE.js +1 -0
- package/dist/frontend/assets/ta-IN-2NMHFXQM-B2-G7tUs.js +9 -0
- package/dist/frontend/assets/th-TH-HPSO5L25-BaOUPhiZ.js +2 -0
- package/dist/frontend/assets/timeline-definition-7e6b55e7-ChAZUdsQ.js +61 -0
- package/dist/frontend/assets/timeline-definition-85554ec2-FT1qcwfh.js +61 -0
- package/dist/frontend/assets/tr-TR-DEFEU3FU-_3NLP7we.js +7 -0
- package/dist/frontend/assets/uk-UA-QMV73CPH-e9ZZsONo.js +6 -0
- package/dist/frontend/assets/union-j7EoioKl.js +1 -0
- package/dist/frontend/assets/vi-VN-M7AON7JQ-Bl1etnNc.js +5 -0
- package/dist/frontend/assets/xml-BOsq7VnW.js +1 -0
- package/dist/frontend/assets/xychartDiagram-b6496bcd-DpRHtxW2.js +7 -0
- package/dist/frontend/assets/xychartDiagram-e933f94c-CePJDM-w.js +7 -0
- package/dist/frontend/assets/zh-CN-LNUGB5OW-BVkMlvEs.js +10 -0
- package/dist/frontend/assets/zh-HK-E62DVLB3-BMvPopwA.js +1 -0
- package/dist/frontend/assets/zh-TW-RAJ6MFWO-D_Eu0QQx.js +9 -0
- package/dist/frontend/assets/zipObject-DKSN1jwq.js +1 -0
- package/dist/frontend/index.html +285 -0
- package/dist/index.d.ts +4 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +2058 -0
- package/dist/index.js.map +1 -0
- package/dist/server.d.ts +3 -0
- package/dist/server.d.ts.map +1 -0
- package/dist/server.js +1122 -0
- package/dist/server.js.map +1 -0
- package/dist/types.d.ts +228 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +53 -0
- package/dist/types.js.map +1 -0
- package/dist/utils/logger.d.ts +4 -0
- package/dist/utils/logger.d.ts.map +1 -0
- package/dist/utils/logger.js +23 -0
- package/dist/utils/logger.js.map +1 -0
- package/package.json +48 -14
- package/src/index.ts +2330 -0
- package/src/server.ts +1286 -0
- package/src/types.ts +338 -0
- package/src/utils/logger.ts +33 -0
- package/src/index.js +0 -1027
- package/src/types.js +0 -35
- package/src/utils/logger.js +0 -27
package/README.md
CHANGED
|
@@ -1,479 +1,504 @@
|
|
|
1
|
-
# MCP
|
|
1
|
+
# Excalidraw MCP Server & Agent Skill
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
[](https://github.com/yctimlin/mcp_excalidraw/actions/workflows/ci.yml)
|
|
4
|
+
[](https://github.com/yctimlin/mcp_excalidraw/actions/workflows/docker.yml)
|
|
5
|
+
[](https://www.npmjs.com/package/mcp-excalidraw-server)
|
|
6
|
+
[](LICENSE)
|
|
4
7
|
|
|
5
|
-
|
|
8
|
+
Run a live Excalidraw canvas and control it from AI agents. This repo provides:
|
|
6
9
|
|
|
7
|
-
|
|
10
|
+
- **MCP Server**: Connect via Model Context Protocol (Claude Desktop, Cursor, Codex CLI, etc.)
|
|
11
|
+
- **Agent Skill**: Portable skill for Claude Code, Codex CLI, and other skill-enabled agents
|
|
8
12
|
|
|
9
|
-
|
|
10
|
-
- **Location**: Main directory (`src/index.js`, `src/types.js`)
|
|
11
|
-
- **Purpose**: Standalone MCP server that can be published as an npm package
|
|
12
|
-
- **Features**: Creates elements locally, optional canvas sync
|
|
13
|
-
- **Dependencies**: Minimal (only MCP SDK, dotenv, node-fetch, winston, zod)
|
|
13
|
+
Keywords: Excalidraw agent skill, Excalidraw MCP server, AI diagramming, Claude Code skill, Codex CLI skill, Claude Desktop MCP, Cursor MCP, Mermaid to Excalidraw.
|
|
14
14
|
|
|
15
|
-
|
|
16
|
-
- **Location**: `frontend/` directory
|
|
17
|
-
- **Purpose**: Real-time canvas interface with WebSocket synchronization
|
|
18
|
-
- **Features**: Live canvas, WebSocket updates, RESTful API
|
|
19
|
-
- **Dependencies**: React, Excalidraw, Express, WebSocket
|
|
15
|
+
## Demo
|
|
20
16
|
|
|
21
|
-
|
|
22
|
-
┌─────────────────┐ ┌──────────────────┐ ┌─────────────────┐
|
|
23
|
-
│ AI Agent │───▶│ MCP Server │───▶│ Canvas Server │
|
|
24
|
-
│ (Claude) │ │ (src/index.js) │ │ (frontend/) │
|
|
25
|
-
└─────────────────┘ └──────────────────┘ └─────────────────┘
|
|
26
|
-
│ │ │
|
|
27
|
-
│ │ ▼
|
|
28
|
-
│ │ ┌─────────────────┐
|
|
29
|
-
│ │ │ Frontend │
|
|
30
|
-
│ │ │ (React + WS) │
|
|
31
|
-
│ │ └─────────────────┘
|
|
32
|
-
│ │
|
|
33
|
-
│ ▼
|
|
34
|
-
│ ┌─────────────────┐
|
|
35
|
-
│ │ Local Storage │
|
|
36
|
-
│ │ (elements) │
|
|
37
|
-
│ └─────────────────┘
|
|
38
|
-
│
|
|
39
|
-
└─────────────────────────────────────────────────────────┘
|
|
40
|
-
(Works standalone without frontend)
|
|
41
|
-
```
|
|
42
|
-
|
|
43
|
-
## 🚀 What This System Does
|
|
44
|
-
|
|
45
|
-
- **🎨 Live Canvas**: Real-time Excalidraw canvas accessible via web browser (with frontend)
|
|
46
|
-
- **🤖 AI Integration**: MCP server allows AI agents (like Claude) to create visual diagrams
|
|
47
|
-
- **⚡ Real-time Sync**: Elements created via MCP API appear instantly on the canvas (with frontend)
|
|
48
|
-
- **🔄 WebSocket Updates**: Live synchronization across multiple connected clients (with frontend)
|
|
49
|
-
- **🏗️ Standalone Mode**: MCP server works independently for local element creation
|
|
50
|
-
|
|
51
|
-
## 🎥 Demo Video
|
|
17
|
+

|
|
52
18
|
|
|
53
|
-
|
|
19
|
+
*AI agent creates a complete architecture diagram from a single prompt (4x speed). [Watch full video on YouTube](https://youtu.be/ufW78Amq5qA)*
|
|
54
20
|
|
|
55
|
-
|
|
21
|
+
## Table of Contents
|
|
56
22
|
|
|
57
|
-
|
|
23
|
+
- [Demo](#demo)
|
|
24
|
+
- [What It Is](#what-it-is)
|
|
25
|
+
- [How We Differ from the Official Excalidraw MCP](#how-we-differ-from-the-official-excalidraw-mcp)
|
|
26
|
+
- [What's New](#whats-new)
|
|
27
|
+
- [Quick Start (Local)](#quick-start-local)
|
|
28
|
+
- [Quick Start (Docker)](#quick-start-docker)
|
|
29
|
+
- [Configure MCP Clients](#configure-mcp-clients)
|
|
30
|
+
- [Claude Desktop](#claude-desktop)
|
|
31
|
+
- [Claude Code](#claude-code)
|
|
32
|
+
- [Cursor](#cursor)
|
|
33
|
+
- [Codex CLI](#codex-cli)
|
|
34
|
+
- [OpenCode](#opencode)
|
|
35
|
+
- [Antigravity (Google)](#antigravity-google)
|
|
36
|
+
- [Agent Skill (Optional)](#agent-skill-optional)
|
|
37
|
+
- [MCP Tools (26 Total)](#mcp-tools-26-total)
|
|
38
|
+
- [Testing](#testing)
|
|
39
|
+
- [Troubleshooting](#troubleshooting)
|
|
40
|
+
- [Known Issues / TODO](#known-issues--todo)
|
|
41
|
+
- [Development](#development)
|
|
58
42
|
|
|
59
|
-
##
|
|
43
|
+
## What It Is
|
|
60
44
|
|
|
61
|
-
|
|
62
|
-
- Works independently without frontend dependencies
|
|
63
|
-
- Creates and manages elements locally
|
|
64
|
-
- Optional canvas synchronization when frontend is available
|
|
65
|
-
- Can be published as an npm package
|
|
45
|
+
This repo contains two separate processes:
|
|
66
46
|
|
|
67
|
-
|
|
68
|
-
-
|
|
69
|
-
- WebSocket-based real-time synchronization
|
|
70
|
-
- Multi-client support with live updates
|
|
47
|
+
- Canvas server: web UI + REST API + WebSocket updates (default `http://127.0.0.1:3000`)
|
|
48
|
+
- MCP server: exposes MCP tools over stdio; syncs to the canvas via `EXPRESS_SERVER_URL`
|
|
71
49
|
|
|
72
|
-
|
|
73
|
-
- Clean, minimal UI with connection status
|
|
74
|
-
- Simple "Clear Canvas" functionality
|
|
75
|
-
- No development clutter or debug information
|
|
50
|
+
## How We Differ from the Official Excalidraw MCP
|
|
76
51
|
|
|
77
|
-
|
|
78
|
-
- **Element Creation**: rectangles, ellipses, diamonds, arrows, text, lines
|
|
79
|
-
- **Element Management**: update, delete, query with filters
|
|
80
|
-
- **Batch Operations**: create multiple elements in one call
|
|
81
|
-
- **Advanced Features**: grouping, alignment, distribution, locking
|
|
52
|
+
Excalidraw now has an [official MCP](https://github.com/excalidraw/excalidraw-mcp) — it's great for quick, prompt-to-diagram generation rendered inline in chat. We solve a different problem.
|
|
82
53
|
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
54
|
+
| | Official Excalidraw MCP | This Project |
|
|
55
|
+
|---|---|---|
|
|
56
|
+
| **Approach** | Prompt in, diagram out (one-shot) | Programmatic element-level control (26 tools) |
|
|
57
|
+
| **State** | Stateless — each call is independent | Persistent live canvas with real-time sync |
|
|
58
|
+
| **Element CRUD** | No | Full create / read / update / delete per element |
|
|
59
|
+
| **AI sees the canvas** | No | `describe_scene` (structured text) + `get_canvas_screenshot` (image) |
|
|
60
|
+
| **Iterative refinement** | No — regenerate the whole diagram | Draw → look → adjust → look again, element by element |
|
|
61
|
+
| **Layout tools** | No | `align_elements`, `distribute_elements`, `group / ungroup` |
|
|
62
|
+
| **File I/O** | No | `export_scene` / `import_scene` (.excalidraw JSON) |
|
|
63
|
+
| **Snapshot & rollback** | No | `snapshot_scene` / `restore_snapshot` |
|
|
64
|
+
| **Mermaid conversion** | No | `create_from_mermaid` |
|
|
65
|
+
| **Shareable URLs** | Yes | Yes — `export_to_excalidraw_url` |
|
|
66
|
+
| **Design guide** | `read_me` cheat sheet | `read_diagram_guide` (colors, sizing, layout, anti-patterns) |
|
|
67
|
+
| **Viewport control** | Camera animations | `set_viewport` (zoom-to-fit, center on element, manual zoom) |
|
|
68
|
+
| **Live canvas UI** | Rendered inline in chat | Standalone Excalidraw app synced via WebSocket |
|
|
69
|
+
| **Multi-agent** | Single user | Multiple agents can draw on the same canvas concurrently |
|
|
70
|
+
| **Works without MCP** | No | Yes — REST API fallback via agent skill |
|
|
88
71
|
|
|
89
|
-
|
|
72
|
+
**TL;DR** — The official MCP generates diagrams. We give AI agents a full canvas toolkit to build, inspect, and iteratively refine diagrams — including the ability to see what they drew.
|
|
90
73
|
|
|
91
|
-
|
|
74
|
+
## What's New
|
|
92
75
|
|
|
93
|
-
|
|
76
|
+
### v2.0 — Canvas Toolkit
|
|
94
77
|
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
npm start
|
|
105
|
-
```
|
|
78
|
+
- 13 new MCP tools (26 total): `get_element`, `clear_canvas`, `export_scene`, `import_scene`, `export_to_image`, `duplicate_elements`, `snapshot_scene`, `restore_snapshot`, `describe_scene`, `get_canvas_screenshot`, `read_diagram_guide`, `export_to_excalidraw_url`, `set_viewport`
|
|
79
|
+
- **Closed feedback loop**: AI can now inspect the canvas (`describe_scene`) and see it (`get_canvas_screenshot` returns an image) — enabling iterative refinement
|
|
80
|
+
- **Design guide**: `read_diagram_guide` returns best-practice color palettes, sizing rules, layout patterns, and anti-patterns — dramatically improves AI-generated diagram quality
|
|
81
|
+
- **Shareable URLs**: `export_to_excalidraw_url` encrypts and uploads the scene to excalidraw.com, returns a shareable link anyone can open
|
|
82
|
+
- **Viewport control**: `set_viewport` with `scrollToContent`, `scrollToElementId`, or manual zoom/offset — agents can auto-fit diagrams after creation
|
|
83
|
+
- **File I/O**: export/import full `.excalidraw` JSON files
|
|
84
|
+
- **Snapshots**: save and restore named canvas states
|
|
85
|
+
- **Skill fallback**: Agent skill auto-detects MCP vs REST API mode, gracefully falls back to HTTP endpoints when MCP server isn't configured
|
|
86
|
+
- Fixed all previously known issues: `align_elements` / `distribute_elements` fully implemented, points type normalization, removed invalid `label` type, removed HTTP transport dead code, `ungroup_elements` now errors on failure
|
|
106
87
|
|
|
107
|
-
|
|
88
|
+
### v1.x
|
|
108
89
|
|
|
109
|
-
|
|
90
|
+
- Agent skill: `skills/excalidraw-skill/` (portable instructions + helper scripts for export/import and repeatable CRUD)
|
|
91
|
+
- Better testing loop: MCP Inspector CLI examples + browser screenshot checks (`agent-browser`)
|
|
92
|
+
- Bugfixes: batch create now preserves element ids (fixes update/delete after batch); frontend entrypoint fixed (`main.tsx`)
|
|
110
93
|
|
|
111
|
-
|
|
94
|
+
## Quick Start (Local)
|
|
112
95
|
|
|
113
|
-
|
|
114
|
-
```bash
|
|
115
|
-
git clone https://github.com/yctimlin/mcp_excalidraw.git
|
|
116
|
-
cd mcp_excalidraw
|
|
117
|
-
npm install
|
|
118
|
-
```
|
|
96
|
+
Prereqs: Node >= 18, npm
|
|
119
97
|
|
|
120
|
-
#### **2. Setup Frontend**
|
|
121
98
|
```bash
|
|
122
|
-
|
|
123
|
-
npm install
|
|
99
|
+
npm ci
|
|
124
100
|
npm run build
|
|
125
101
|
```
|
|
126
102
|
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
##### **Option A: Production Mode (Recommended)**
|
|
103
|
+
Terminal 1: start the canvas
|
|
130
104
|
```bash
|
|
131
|
-
|
|
132
|
-
cd frontend
|
|
133
|
-
npm start
|
|
134
|
-
|
|
135
|
-
# Terminal 2: Start MCP server (in main directory)
|
|
136
|
-
cd ..
|
|
137
|
-
npm start
|
|
105
|
+
PORT=3000 npm run canvas
|
|
138
106
|
```
|
|
139
107
|
|
|
140
|
-
|
|
141
|
-
```bash
|
|
142
|
-
# Terminal 1: Start frontend in dev mode
|
|
143
|
-
cd frontend
|
|
144
|
-
npm run dev
|
|
108
|
+
> **Security note:** The server defaults to binding on `127.0.0.1` only. If you need to expose it on a network interface (e.g. Docker, remote access), set `HOST=0.0.0.0` — but ensure you have network-level access controls in place, as the API has no built-in authentication.
|
|
145
109
|
|
|
146
|
-
|
|
147
|
-
cd ..
|
|
148
|
-
npm start
|
|
149
|
-
```
|
|
110
|
+
Open `http://127.0.0.1:3000`.
|
|
150
111
|
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
http://localhost:3000
|
|
112
|
+
Terminal 2: run the MCP server (stdio)
|
|
113
|
+
```bash
|
|
114
|
+
EXPRESS_SERVER_URL=http://127.0.0.1:3000 node dist/index.js
|
|
155
115
|
```
|
|
156
116
|
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
Use Docker Compose to run both components:
|
|
117
|
+
## Quick Start (Docker)
|
|
160
118
|
|
|
119
|
+
Canvas server:
|
|
161
120
|
```bash
|
|
162
|
-
docker-
|
|
121
|
+
docker run -d -p 3000:3000 --name mcp-excalidraw-canvas ghcr.io/yctimlin/mcp_excalidraw-canvas:latest
|
|
163
122
|
```
|
|
164
123
|
|
|
165
|
-
|
|
124
|
+
MCP server (stdio) is typically launched by your MCP client (Claude Desktop/Cursor/etc.). If you want a local container for it, use the image `ghcr.io/yctimlin/mcp_excalidraw:latest` and set `EXPRESS_SERVER_URL` to point at the canvas.
|
|
125
|
+
|
|
126
|
+
## Configure MCP Clients
|
|
166
127
|
|
|
167
|
-
|
|
128
|
+
The MCP server runs over stdio and can be configured with any MCP-compatible client. Below are configurations for both **local** (requires cloning and building) and **Docker** (pull-and-run) setups.
|
|
168
129
|
|
|
169
|
-
###
|
|
170
|
-
| Script | Description |
|
|
171
|
-
|--------|-------------|
|
|
172
|
-
| `npm start` | Start MCP server (`src/index.js`) |
|
|
130
|
+
### Environment Variables
|
|
173
131
|
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
| `
|
|
178
|
-
| `npm run build` | Build React frontend for production |
|
|
179
|
-
| `npm run dev` | Start Express + Vite dev server |
|
|
180
|
-
| `npm run preview` | Preview built frontend |
|
|
132
|
+
| Variable | Description | Default |
|
|
133
|
+
|----------|-------------|---------|
|
|
134
|
+
| `EXPRESS_SERVER_URL` | URL of the canvas server | `http://127.0.0.1:3000` |
|
|
135
|
+
| `ENABLE_CANVAS_SYNC` | Enable real-time canvas sync | `true` |
|
|
181
136
|
|
|
182
|
-
|
|
137
|
+
---
|
|
183
138
|
|
|
184
|
-
###
|
|
185
|
-
1. Open the canvas at `http://localhost:3000` (if using frontend)
|
|
186
|
-
2. Check connection status (should show "Connected")
|
|
187
|
-
3. AI agents can now create diagrams that appear in real-time
|
|
188
|
-
4. Use "Clear Canvas" to remove all elements
|
|
139
|
+
### Claude Desktop
|
|
189
140
|
|
|
190
|
-
|
|
191
|
-
|
|
141
|
+
Config location:
|
|
142
|
+
- macOS: `~/Library/Application Support/Claude/claude_desktop_config.json`
|
|
143
|
+
- Windows: `%APPDATA%\Claude\claude_desktop_config.json`
|
|
144
|
+
- Linux: `~/.config/Claude/claude_desktop_config.json`
|
|
192
145
|
|
|
193
|
-
|
|
194
|
-
```
|
|
195
|
-
// Create a rectangle
|
|
146
|
+
**Local (node)**
|
|
147
|
+
```json
|
|
196
148
|
{
|
|
197
|
-
"
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
149
|
+
"mcpServers": {
|
|
150
|
+
"excalidraw": {
|
|
151
|
+
"command": "node",
|
|
152
|
+
"args": ["/absolute/path/to/mcp_excalidraw/dist/index.js"],
|
|
153
|
+
"env": {
|
|
154
|
+
"EXPRESS_SERVER_URL": "http://127.0.0.1:3000",
|
|
155
|
+
"ENABLE_CANVAS_SYNC": "true"
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
}
|
|
205
159
|
}
|
|
206
160
|
```
|
|
207
161
|
|
|
208
|
-
|
|
209
|
-
```
|
|
162
|
+
**Docker**
|
|
163
|
+
```json
|
|
210
164
|
{
|
|
211
|
-
"
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
165
|
+
"mcpServers": {
|
|
166
|
+
"excalidraw": {
|
|
167
|
+
"command": "docker",
|
|
168
|
+
"args": [
|
|
169
|
+
"run", "-i", "--rm",
|
|
170
|
+
"-e", "EXPRESS_SERVER_URL=http://host.docker.internal:3000",
|
|
171
|
+
"-e", "ENABLE_CANVAS_SYNC=true",
|
|
172
|
+
"ghcr.io/yctimlin/mcp_excalidraw:latest"
|
|
173
|
+
]
|
|
174
|
+
}
|
|
175
|
+
}
|
|
217
176
|
}
|
|
218
177
|
```
|
|
219
178
|
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
179
|
+
---
|
|
180
|
+
|
|
181
|
+
### Claude Code
|
|
182
|
+
|
|
183
|
+
Use the `claude mcp add` command to register the MCP server.
|
|
184
|
+
|
|
185
|
+
**Local (node)** - User-level (available across all projects):
|
|
186
|
+
```bash
|
|
187
|
+
claude mcp add excalidraw --scope user \
|
|
188
|
+
-e EXPRESS_SERVER_URL=http://127.0.0.1:3000 \
|
|
189
|
+
-e ENABLE_CANVAS_SYNC=true \
|
|
190
|
+
-- node /absolute/path/to/mcp_excalidraw/dist/index.js
|
|
231
191
|
```
|
|
232
192
|
|
|
233
|
-
|
|
234
|
-
```
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
"x": 100,
|
|
240
|
-
"y": 100,
|
|
241
|
-
"width": 120,
|
|
242
|
-
"height": 60,
|
|
243
|
-
"backgroundColor": "#fff3e0",
|
|
244
|
-
"strokeColor": "#ff9800"
|
|
245
|
-
},
|
|
246
|
-
{
|
|
247
|
-
"type": "text",
|
|
248
|
-
"x": 130,
|
|
249
|
-
"y": 125,
|
|
250
|
-
"text": "Start",
|
|
251
|
-
"fontSize": 16
|
|
252
|
-
}
|
|
253
|
-
]
|
|
254
|
-
}
|
|
193
|
+
**Local (node)** - Project-level (shared via `.mcp.json`):
|
|
194
|
+
```bash
|
|
195
|
+
claude mcp add excalidraw --scope project \
|
|
196
|
+
-e EXPRESS_SERVER_URL=http://127.0.0.1:3000 \
|
|
197
|
+
-e ENABLE_CANVAS_SYNC=true \
|
|
198
|
+
-- node /absolute/path/to/mcp_excalidraw/dist/index.js
|
|
255
199
|
```
|
|
256
200
|
|
|
257
|
-
|
|
201
|
+
**Docker**
|
|
202
|
+
```bash
|
|
203
|
+
claude mcp add excalidraw --scope user \
|
|
204
|
+
-- docker run -i --rm \
|
|
205
|
+
-e EXPRESS_SERVER_URL=http://host.docker.internal:3000 \
|
|
206
|
+
-e ENABLE_CANVAS_SYNC=true \
|
|
207
|
+
ghcr.io/yctimlin/mcp_excalidraw:latest
|
|
208
|
+
```
|
|
209
|
+
|
|
210
|
+
**Manage servers:**
|
|
211
|
+
```bash
|
|
212
|
+
claude mcp list # List configured servers
|
|
213
|
+
claude mcp remove excalidraw # Remove a server
|
|
214
|
+
```
|
|
258
215
|
|
|
259
|
-
|
|
216
|
+
---
|
|
260
217
|
|
|
261
|
-
|
|
218
|
+
### Cursor
|
|
262
219
|
|
|
220
|
+
Config location: `.cursor/mcp.json` in your project root (or `~/.cursor/mcp.json` for global config)
|
|
221
|
+
|
|
222
|
+
**Local (node)**
|
|
263
223
|
```json
|
|
264
224
|
{
|
|
265
225
|
"mcpServers": {
|
|
266
226
|
"excalidraw": {
|
|
267
227
|
"command": "node",
|
|
268
|
-
"args": ["/absolute/path/to/mcp_excalidraw/
|
|
228
|
+
"args": ["/absolute/path/to/mcp_excalidraw/dist/index.js"],
|
|
229
|
+
"env": {
|
|
230
|
+
"EXPRESS_SERVER_URL": "http://127.0.0.1:3000",
|
|
231
|
+
"ENABLE_CANVAS_SYNC": "true"
|
|
232
|
+
}
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
```
|
|
237
|
+
|
|
238
|
+
**Docker**
|
|
239
|
+
```json
|
|
240
|
+
{
|
|
241
|
+
"mcpServers": {
|
|
242
|
+
"excalidraw": {
|
|
243
|
+
"command": "docker",
|
|
244
|
+
"args": [
|
|
245
|
+
"run", "-i", "--rm",
|
|
246
|
+
"-e", "EXPRESS_SERVER_URL=http://host.docker.internal:3000",
|
|
247
|
+
"-e", "ENABLE_CANVAS_SYNC=true",
|
|
248
|
+
"ghcr.io/yctimlin/mcp_excalidraw:latest"
|
|
249
|
+
]
|
|
269
250
|
}
|
|
270
251
|
}
|
|
271
252
|
}
|
|
272
253
|
```
|
|
273
254
|
|
|
274
|
-
|
|
255
|
+
---
|
|
256
|
+
|
|
257
|
+
### Codex CLI
|
|
275
258
|
|
|
276
|
-
|
|
259
|
+
Use the `codex mcp add` command to register the MCP server.
|
|
277
260
|
|
|
278
|
-
|
|
261
|
+
**Local (node)**
|
|
262
|
+
```bash
|
|
263
|
+
codex mcp add excalidraw \
|
|
264
|
+
--env EXPRESS_SERVER_URL=http://127.0.0.1:3000 \
|
|
265
|
+
--env ENABLE_CANVAS_SYNC=true \
|
|
266
|
+
-- node /absolute/path/to/mcp_excalidraw/dist/index.js
|
|
267
|
+
```
|
|
268
|
+
|
|
269
|
+
**Docker**
|
|
270
|
+
```bash
|
|
271
|
+
codex mcp add excalidraw \
|
|
272
|
+
-- docker run -i --rm \
|
|
273
|
+
-e EXPRESS_SERVER_URL=http://host.docker.internal:3000 \
|
|
274
|
+
-e ENABLE_CANVAS_SYNC=true \
|
|
275
|
+
ghcr.io/yctimlin/mcp_excalidraw:latest
|
|
276
|
+
```
|
|
277
|
+
|
|
278
|
+
**Manage servers:**
|
|
279
|
+
```bash
|
|
280
|
+
codex mcp list # List configured servers
|
|
281
|
+
codex mcp remove excalidraw # Remove a server
|
|
282
|
+
```
|
|
283
|
+
|
|
284
|
+
---
|
|
285
|
+
|
|
286
|
+
### OpenCode
|
|
287
|
+
|
|
288
|
+
Config location: `~/.config/opencode/opencode.json` or project-level `opencode.json`
|
|
289
|
+
|
|
290
|
+
**Local (node)**
|
|
279
291
|
```json
|
|
280
292
|
{
|
|
281
|
-
"
|
|
293
|
+
"$schema": "https://opencode.ai/config.json",
|
|
294
|
+
"mcp": {
|
|
282
295
|
"excalidraw": {
|
|
283
|
-
"
|
|
284
|
-
"
|
|
296
|
+
"type": "local",
|
|
297
|
+
"command": ["node", "/absolute/path/to/mcp_excalidraw/dist/index.js"],
|
|
298
|
+
"enabled": true,
|
|
299
|
+
"environment": {
|
|
300
|
+
"EXPRESS_SERVER_URL": "http://127.0.0.1:3000",
|
|
301
|
+
"ENABLE_CANVAS_SYNC": "true"
|
|
302
|
+
}
|
|
285
303
|
}
|
|
286
304
|
}
|
|
287
305
|
}
|
|
288
306
|
```
|
|
289
|
-
*Currently debugging tool registration - let us know if you encounter issues!*
|
|
290
307
|
|
|
291
|
-
|
|
308
|
+
**Docker**
|
|
292
309
|
```json
|
|
293
310
|
{
|
|
294
|
-
"
|
|
311
|
+
"$schema": "https://opencode.ai/config.json",
|
|
312
|
+
"mcp": {
|
|
295
313
|
"excalidraw": {
|
|
296
|
-
"
|
|
297
|
-
"
|
|
314
|
+
"type": "local",
|
|
315
|
+
"command": ["docker", "run", "-i", "--rm", "-e", "EXPRESS_SERVER_URL=http://host.docker.internal:3000", "-e", "ENABLE_CANVAS_SYNC=true", "ghcr.io/yctimlin/mcp_excalidraw:latest"],
|
|
316
|
+
"enabled": true
|
|
298
317
|
}
|
|
299
318
|
}
|
|
300
319
|
}
|
|
301
320
|
```
|
|
302
|
-
*Canvas sync improvements in progress.*
|
|
303
321
|
|
|
304
|
-
|
|
322
|
+
---
|
|
305
323
|
|
|
306
|
-
###
|
|
324
|
+
### Antigravity (Google)
|
|
307
325
|
|
|
308
|
-
|
|
326
|
+
Config location: `~/.gemini/antigravity/mcp_config.json`
|
|
309
327
|
|
|
328
|
+
**Local (node)**
|
|
310
329
|
```json
|
|
311
330
|
{
|
|
312
331
|
"mcpServers": {
|
|
313
332
|
"excalidraw": {
|
|
314
333
|
"command": "node",
|
|
315
|
-
"args": ["/absolute/path/to/mcp_excalidraw/
|
|
334
|
+
"args": ["/absolute/path/to/mcp_excalidraw/dist/index.js"],
|
|
335
|
+
"env": {
|
|
336
|
+
"EXPRESS_SERVER_URL": "http://127.0.0.1:3000",
|
|
337
|
+
"ENABLE_CANVAS_SYNC": "true"
|
|
338
|
+
}
|
|
316
339
|
}
|
|
317
340
|
}
|
|
318
341
|
}
|
|
319
342
|
```
|
|
320
343
|
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
For VS Code MCP extension, add to your settings:
|
|
324
|
-
|
|
344
|
+
**Docker**
|
|
325
345
|
```json
|
|
326
346
|
{
|
|
327
|
-
"
|
|
328
|
-
"
|
|
329
|
-
"
|
|
330
|
-
|
|
331
|
-
"
|
|
332
|
-
|
|
347
|
+
"mcpServers": {
|
|
348
|
+
"excalidraw": {
|
|
349
|
+
"command": "docker",
|
|
350
|
+
"args": [
|
|
351
|
+
"run", "-i", "--rm",
|
|
352
|
+
"-e", "EXPRESS_SERVER_URL=http://host.docker.internal:3000",
|
|
353
|
+
"-e", "ENABLE_CANVAS_SYNC=true",
|
|
354
|
+
"ghcr.io/yctimlin/mcp_excalidraw:latest"
|
|
355
|
+
]
|
|
333
356
|
}
|
|
334
357
|
}
|
|
335
358
|
}
|
|
336
359
|
```
|
|
337
360
|
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
###
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
-
|
|
398
|
-
-
|
|
399
|
-
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
- Check `ENABLE_CANVAS_SYNC=true` in environment
|
|
422
|
-
- Verify canvas server is accessible at `EXPRESS_SERVER_URL`
|
|
423
|
-
|
|
424
|
-
### **WebSocket Connection Issues**
|
|
425
|
-
- Check browser console for WebSocket errors
|
|
426
|
-
- Ensure no firewall blocking WebSocket connections
|
|
427
|
-
- Try refreshing the browser page
|
|
428
|
-
|
|
429
|
-
### **Build Errors**
|
|
430
|
-
- Delete `node_modules` and run `npm install`
|
|
431
|
-
- Check Node.js version (requires 16+)
|
|
432
|
-
- Ensure all dependencies are installed
|
|
433
|
-
|
|
434
|
-
## 📋 Project Structure
|
|
361
|
+
---
|
|
362
|
+
|
|
363
|
+
### Notes
|
|
364
|
+
|
|
365
|
+
- **Docker networking**: Use `host.docker.internal` to reach the canvas server running on your host machine. On Linux, you may need `--add-host=host.docker.internal:host-gateway` or use `172.17.0.1`.
|
|
366
|
+
- **Canvas server**: Must be running before the MCP server connects. Start it with `npm run canvas` (local) or `docker run -d -p 3000:3000 ghcr.io/yctimlin/mcp_excalidraw-canvas:latest` (Docker).
|
|
367
|
+
- **Absolute paths**: When using local node setup, replace `/absolute/path/to/mcp_excalidraw` with the actual path where you cloned and built the repo.
|
|
368
|
+
- **In-memory storage**: The canvas server stores elements in memory. Restarting the server will clear all elements. Use the export/import scripts if you need persistence.
|
|
369
|
+
|
|
370
|
+
## Agent Skill (Optional)
|
|
371
|
+
|
|
372
|
+
This repo includes a skill at `skills/excalidraw-skill/` that provides:
|
|
373
|
+
|
|
374
|
+
- **Workflow playbook** (`SKILL.md`): step-by-step guidance for drawing, refining, and exporting diagrams
|
|
375
|
+
- **Cheatsheet** (`references/cheatsheet.md`): MCP tool and REST API reference
|
|
376
|
+
- **Helper scripts** (`scripts/*.cjs`): export, import, clear, healthcheck, CRUD operations
|
|
377
|
+
|
|
378
|
+
The skill complements the MCP server by giving your AI agent structured workflows to follow.
|
|
379
|
+
|
|
380
|
+
### Install The Skill (Codex CLI example)
|
|
381
|
+
|
|
382
|
+
```bash
|
|
383
|
+
mkdir -p ~/.codex/skills
|
|
384
|
+
cp -R skills/excalidraw-skill ~/.codex/skills/excalidraw-skill
|
|
385
|
+
```
|
|
386
|
+
|
|
387
|
+
To update an existing installation, remove the old folder first (`rm -rf ~/.codex/skills/excalidraw-skill`) then re-copy.
|
|
388
|
+
|
|
389
|
+
### Install The Skill (Claude Code)
|
|
390
|
+
|
|
391
|
+
**User-level** (available across all your projects):
|
|
392
|
+
```bash
|
|
393
|
+
mkdir -p ~/.claude/skills
|
|
394
|
+
cp -R skills/excalidraw-skill ~/.claude/skills/excalidraw-skill
|
|
395
|
+
```
|
|
396
|
+
|
|
397
|
+
**Project-level** (scoped to a specific project, can be committed to the repo):
|
|
398
|
+
```bash
|
|
399
|
+
mkdir -p /path/to/your/project/.claude/skills
|
|
400
|
+
cp -R skills/excalidraw-skill /path/to/your/project/.claude/skills/excalidraw-skill
|
|
401
|
+
```
|
|
402
|
+
|
|
403
|
+
Then invoke the skill in Claude Code with `/excalidraw-skill`.
|
|
404
|
+
|
|
405
|
+
To update an existing installation, remove the old folder first then re-copy.
|
|
406
|
+
|
|
407
|
+
### Use The Skill Scripts
|
|
408
|
+
|
|
409
|
+
All scripts respect `EXPRESS_SERVER_URL` (default `http://127.0.0.1:3000`) or accept `--url`.
|
|
410
|
+
|
|
411
|
+
```bash
|
|
412
|
+
EXPRESS_SERVER_URL=http://127.0.0.1:3000 node skills/excalidraw-skill/scripts/healthcheck.cjs
|
|
413
|
+
EXPRESS_SERVER_URL=http://127.0.0.1:3000 node skills/excalidraw-skill/scripts/export-elements.cjs --out diagram.elements.json
|
|
414
|
+
EXPRESS_SERVER_URL=http://127.0.0.1:3000 node skills/excalidraw-skill/scripts/import-elements.cjs --in diagram.elements.json --mode batch
|
|
415
|
+
```
|
|
416
|
+
|
|
417
|
+
### When The Skill Is Useful
|
|
418
|
+
|
|
419
|
+
- Repository workflow: export elements as JSON, commit it, and re-import later.
|
|
420
|
+
- Reliable refactors: clear + re-import in `sync` mode to make canvas match a file.
|
|
421
|
+
- Automated smoke tests: create/update/delete a known element to validate a deployment.
|
|
422
|
+
- Repeatable diagrams: keep a library of element JSON snippets and import them.
|
|
423
|
+
|
|
424
|
+
See `skills/excalidraw-skill/SKILL.md` and `skills/excalidraw-skill/references/cheatsheet.md`.
|
|
425
|
+
|
|
426
|
+
## MCP Tools (26 Total)
|
|
427
|
+
|
|
428
|
+
| Category | Tools |
|
|
429
|
+
|---|---|
|
|
430
|
+
| **Element CRUD** | `create_element`, `get_element`, `update_element`, `delete_element`, `query_elements`, `batch_create_elements`, `duplicate_elements` |
|
|
431
|
+
| **Layout** | `align_elements`, `distribute_elements`, `group_elements`, `ungroup_elements`, `lock_elements`, `unlock_elements` |
|
|
432
|
+
| **Scene Awareness** | `describe_scene`, `get_canvas_screenshot` |
|
|
433
|
+
| **File I/O** | `export_scene`, `import_scene`, `export_to_image`, `export_to_excalidraw_url`, `create_from_mermaid` |
|
|
434
|
+
| **State Management** | `clear_canvas`, `snapshot_scene`, `restore_snapshot` |
|
|
435
|
+
| **Viewport** | `set_viewport` |
|
|
436
|
+
| **Design Guide** | `read_diagram_guide` |
|
|
437
|
+
| **Resources** | `get_resource` |
|
|
438
|
+
|
|
439
|
+
Full schemas are discoverable via `tools/list` or in `skills/excalidraw-skill/references/cheatsheet.md`.
|
|
440
|
+
|
|
441
|
+
## Testing
|
|
442
|
+
|
|
443
|
+
### Canvas Smoke Test (HTTP)
|
|
435
444
|
|
|
445
|
+
```bash
|
|
446
|
+
curl http://127.0.0.1:3000/health
|
|
436
447
|
```
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
│ └── index.html # HTML template
|
|
443
|
-
├── src/
|
|
444
|
-
│ ├── index.js # MCP server
|
|
445
|
-
│ ├── server.js # Canvas server (Express + WebSocket)
|
|
446
|
-
│ ├── types.js # Shared types and utilities
|
|
447
|
-
│ └── utils/
|
|
448
|
-
│ └── logger.js # Logging utility
|
|
449
|
-
├── dist/ # Built frontend (generated)
|
|
450
|
-
├── vite.config.js # Vite build configuration
|
|
451
|
-
├── package.json # Dependencies and scripts
|
|
452
|
-
└── README.md # This file
|
|
448
|
+
|
|
449
|
+
### Local Bind Regression Test
|
|
450
|
+
|
|
451
|
+
```bash
|
|
452
|
+
npm run test:bind
|
|
453
453
|
```
|
|
454
454
|
|
|
455
|
-
|
|
455
|
+
### MCP Smoke Test (MCP Inspector)
|
|
456
456
|
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
-
|
|
457
|
+
List tools:
|
|
458
|
+
```bash
|
|
459
|
+
npx @modelcontextprotocol/inspector --cli \
|
|
460
|
+
-e EXPRESS_SERVER_URL=http://127.0.0.1:3000 \
|
|
461
|
+
-e ENABLE_CANVAS_SYNC=true -- \
|
|
462
|
+
node dist/index.js --method tools/list
|
|
463
|
+
```
|
|
461
464
|
|
|
462
|
-
|
|
465
|
+
Create a rectangle:
|
|
466
|
+
```bash
|
|
467
|
+
npx @modelcontextprotocol/inspector --cli \
|
|
468
|
+
-e EXPRESS_SERVER_URL=http://127.0.0.1:3000 \
|
|
469
|
+
-e ENABLE_CANVAS_SYNC=true -- \
|
|
470
|
+
node dist/index.js --method tools/call --tool-name create_element \
|
|
471
|
+
--tool-arg type=rectangle --tool-arg x=100 --tool-arg y=100 \
|
|
472
|
+
--tool-arg width=300 --tool-arg height=200
|
|
473
|
+
```
|
|
463
474
|
|
|
464
|
-
|
|
475
|
+
### Frontend Screenshots (agent-browser)
|
|
465
476
|
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
477
|
+
If you use `agent-browser` for UI checks:
|
|
478
|
+
```bash
|
|
479
|
+
agent-browser install
|
|
480
|
+
agent-browser open http://127.0.0.1:3000
|
|
481
|
+
agent-browser wait --load networkidle
|
|
482
|
+
agent-browser screenshot /tmp/canvas.png
|
|
483
|
+
```
|
|
484
|
+
|
|
485
|
+
## Troubleshooting
|
|
486
|
+
|
|
487
|
+
- Canvas not updating: confirm `EXPRESS_SERVER_URL` points at the running canvas server.
|
|
488
|
+
- Updates/deletes fail after batch creation: ensure you are on a build that includes the batch id preservation fix (merged via PR #34).
|
|
489
|
+
|
|
490
|
+
## Known Issues / TODO
|
|
471
491
|
|
|
472
|
-
|
|
492
|
+
All previously listed bugs have been fixed in v2.0. Remaining items:
|
|
473
493
|
|
|
474
|
-
|
|
494
|
+
- [ ] **Persistent storage**: Elements are stored in-memory — restarting the server clears everything. Use `export_scene` / snapshots as a workaround.
|
|
495
|
+
- [ ] **Image export requires a browser**: `export_to_image` and `get_canvas_screenshot` rely on the frontend doing the actual rendering. The canvas UI must be open in a browser.
|
|
475
496
|
|
|
476
|
-
|
|
497
|
+
Contributions welcome!
|
|
477
498
|
|
|
478
|
-
|
|
479
|
-
|
|
499
|
+
## Development
|
|
500
|
+
|
|
501
|
+
```bash
|
|
502
|
+
npm run type-check
|
|
503
|
+
npm run build
|
|
504
|
+
```
|