Excalidraw MCP服务器

一个通过标准化工具和资源暴露Excalidraw图表能力的MCP服务器,结合独立的React前端进行可视化编辑。

  • by whallysson
  • TypeScript
  • 本地部署
  • 1 星标
  • 更新于
在 GitHub 查看 whallysson/excalidraw-mcp

使用说明

排除MCP服务器

一个模型上下文协议(MCP)服务器,通过标准化的工具和资源公开Excalidraw图功能,并结合独立的React前端进行可视化编辑。

特性

  • 🎨 MCP协议集成:通过AI助手以编程方式控制Excalidraw
  • 🖥️ 独立前端:独立使用Excalidraw接口
  • 🔄 实时同步:前端和MCP服务器之间的WebSocket同步
  • 🐳 Docker支持:本地运行或通过Docker Compose运行
  • 📦 TypeScript:带Zod验证的全类型代码库
  • 🧪 测试良好:单元、集成和E2E测试覆盖率

快速开始

先决条件

  • Node.js 18+(建议使用LTS)
  • Docker和Docker Compose(可选,用于容器部署)

地方发展

选项1:用一个命令开始一切 (推荐)

# Install dependencies (first time only)
npm install
cd backend && npm install
cd ../frontend && npm install
cd ..

# Configure environment (first time only)
cp backend/.env.example backend/.env
cp frontend/.env.example frontend/.env

# Start EVERYTHING (MCP + HTTP/WebSocket + Frontend)
npm run dev:all

此单个命令启动:

  • [MCP] -后端的MCP服务器(stdio)
  • [HTTP] -端口3333上的HTTP/WebSocket服务器
  • [FRONTEND] -端口5173上的前端Vite开发服务器

打开浏览器 http://localhost:5173 并开始创建图表!

选项2:单独启动服务 (用于调试)

# Terminal 1: Backend MCP + HTTP/WebSocket Server
cd backend
npm run dev:all

# Terminal 2: Frontend
cd frontend
npm run dev

选项3:单个流程 (高级)

# Terminal 1: HTTP/WebSocket Server only
cd backend && npm run dev

# Terminal 2: MCP Server only (for Claude Desktop integration)
cd backend && npm run dev:mcp

# Terminal 3: Frontend
cd frontend && npm run dev

Docker部署(生产)

重要:Docker只启动 前端+HTTP/WebSocket服务器The MCP服务器 (stdio)必须运行 本地 用于与Claude Desktop通信。

单个集装箱

Docker现在使用 1个集装箱 它结合了:

  • ✅ 前端(React/Vite静态构建)
  • ✅ 后端HTTP服务器(Express+WebSocket)
  • ❌ MCP服务器stdio(在本地运行-见下文)

Docker命令

# Start application (Frontend + HTTP/WebSocket)
docker-compose up -d

# View logs
docker-compose logs -f

# Rebuild after changes
docker-compose down
docker-compose build
docker-compose up -d

# Stop application
docker-compose down

# Clean volumes (deletes canvas data)
docker-compose down -v

访问应用程序

  • 前端: http://localhost:3333
  • 健康检查: http://localhost:3333/health
  • API: http://localhost:3333/api/canvas/main

MCP服务器(本地运行)

MCP服务器使用stdio协议(stdin/stdout)和 不能 在Docker中运行。在本地运行它:

# Separate terminal: MCP Server for Claude Desktop
cd backend
npm run dev:mcp

Claude桌面配置 (claude_desktop_config.json):

{
  "mcpServers": {
    "excalidraw": {
      "command": "npx",
      "args": ["tsx", "/absolute/path/backend/src/index.ts"],
      "env": {
        "HTTP_SERVER_URL": "http://localhost:3333"
      }
    }
  }
}

完整架构

┌─────────────────────────────────────────┐
│ Docker Container (excalidraw-mcp)      │
│                                         │
│  ┌──────────────┐   ┌────────────────┐ │
│  │   Frontend   │   │  HTTP Server   │ │
│  │ (Static Files)│◄──┤ Express + WS   │ │
│  └──────────────┘   └────────────────┘ │
│                                         │
│  Port: 3333                             │
└─────────────────────────────────────────┘
                  ▲
                  │ HTTP POST /api/canvas/*/broadcast
                  │
┌─────────────────┴───────────────────────┐
│ Local Process (MCP Server)              │
│                                         │
│  ┌──────────────────────────────────┐  │
│  │ MCP Server (stdio)               │  │
│  │ JSON-RPC 2.0 Protocol            │  │
│  └──────────────────────────────────┘  │
│                  ▲                      │
│                  │ stdin/stdout         │
│                  │                      │
│  ┌───────────────┴──────────────────┐  │
│  │     Claude Desktop (MCP Client)  │  │
│  └──────────────────────────────────┘  │
└─────────────────────────────────────────┘

完成测试

运行自动化测试:

# Test Docker (Frontend, HTTP, API, Health)
./test-complete-flow.sh

# View detailed results
cat DOCKER_TEST_RESULTS.md

项目结构

├── backend/              # MCP server
│   ├── src/
│   │   ├── mcp/         # MCP tools and resources
│   │   ├── services/    # Canvas management, WebSocket, storage
│   │   ├── types/       # TypeScript definitions
│   │   └── utils/       # Logger, validation helpers
│   └── tests/           # Unit and integration tests
├── frontend/             # React frontend
│   ├── src/
│   │   ├── hooks/       # WebSocket client
│   │   ├── services/    # API client
│   │   └── utils/       # Element validation, conversion
│   └── tests/           # E2E tests
└── docker-compose.yml    # Orchestration

安装

后端依赖关系

cd backend
npm install

前端依赖关系

cd frontend
npm install

本地设置

步骤1:安装依赖项

安装后端和前端的依赖关系:

# Backend
cd backend
npm install

# Frontend
cd ../frontend
npm install

步骤2:配置环境变量

复制示例环境文件并对其进行配置:

# Backend environment
cp backend/.env.example backend/.env

# Frontend environment
cp frontend/.env.example frontend/.env

后端 .env 配置:

PORT=3333
WS_PORT=3333
NODE_ENV=development
LOG_LEVEL=debug
CANVAS_DATA_DIR=./data
SERVER_NAME=excalidraw-mcp-server
SERVER_VERSION=1.0.0

前端 .env 配置:

VITE_MCP_SERVER_URL=http://localhost:3333
VITE_WS_SERVER_URL=ws://localhost:3333

步骤3:启动后端服务器

后端需要 两个过程 运行:

  1. MCP服务器 (stdio)-处理MCP协议命令
  2. HTTP/WebSocket服务器 -提供前端服务并管理WebSocket连接

选项A:使用单个命令运行两个进程 (推荐):

npm run dev:all

这将以彩色输出同时启动两台服务器:

[HTTP] 🚀 Excalidraw MCP Server
[HTTP]    HTTP: http://localhost:3333
[HTTP]    WebSocket: ws://localhost:3333
[HTTP]    Health: http://localhost:3333/health
[MCP] MCP server started successfully
[MCP] Tools registered: element_create, element_update, element_delete, get_canvas_state

选项B:单独运行进程 (用于调试):

# Terminal 1: HTTP/WebSocket Server
npm run dev

# Terminal 2: MCP Server (for Claude Desktop integration)
npm run dev:mcp

可用MCP工具(共12个):

元件操作:

  • element_create -创建新元素(矩形、椭圆、菱形、箭头、文本、自由绘制、图像、框架等)
  • element_update -更新现有元素属性(位置、大小、颜色、文本等)
  • element_delete -软删除元素(标记为已删除,不从存储中删除)
  • batch_create_elements -在一次操作中高效地创建多个元素

画布操作:

  • get_canvas_state -获取所有活动元素和画布状态
  • clear_canvas -从画布中删除所有元素
  • canvas_export -以JSON或Excalidraw格式导出画布数据
  • canvas_import -将元素导入画布(合并或替换模式)

组和布局:

  • group_create -将元素组合在一起作为一个单元移动
  • group_ungroup -取消对以前分组的元素的分组

元素状态:

  • lock_elements -锁定元件,防止意外修改
  • unlock_elements -解锁以前锁定的元素

可用MCP资源:

  • canvas://main/state -读取画布状态和元素
  • health://check -服务器健康指标

步骤4:启动前端(可选)

前端是可选的,独立运行:

cd frontend
npm run dev

前端将在以下网址提供: http://localhost:5173

步骤5:测试MCP命令

使用curl或MCP客户端测试MCP服务器:

# Health check
curl http://localhost:3333/health

# Create a rectangle via MCP
curl -X POST http://localhost:3333/mcp \
  -H "Content-Type: application/json" \
  -d '{
    "jsonrpc": "2.0",
    "id": 1,
    "method": "tools/call",
    "params": {
      "name": "element_create",
      "arguments": {
        "type": "rectangle",
        "x": 100,
        "y": 100,
        "width": 200,
        "height": 150,
        "strokeColor": "#c92a2a",
        "backgroundColor": "#ffd43b"
      }
    }
  }'

# Query all elements
curl -X POST http://localhost:3333/mcp \
  -H "Content-Type: application/json" \
  -d '{
    "jsonrpc": "2.0",
    "id": 2,
    "method": "tools/call",
    "params": {
      "name": "element_query",
      "arguments": {}
    }
  }'

# Read canvas state
curl -X POST http://localhost:3333/mcp \
  -H "Content-Type: application/json" \
  -d '{
    "jsonrpc": "2.0",
    "id": 3,
    "method": "resources/read",
    "params": {
      "uri": "canvas://main/state"
    }
  }'

故障排除

问题:端口3333已在使用中

# Change PORT in backend/.env
PORT=3334
WS_PORT=3334

# Update frontend/.env
VITE_MCP_SERVER_URL=http://localhost:3334
VITE_WS_SERVER_URL=ws://localhost:3334

问题:未找到模块错误

# Clean install
rm -rf node_modules package-lock.json
npm install

问题:TypeScript编译错误

# Rebuild
npm run build

Docker部署

使用Docker Compose运行整个系统,并支持热重载开发。

先决条件

  • Docker 20.10+和Docker Compose 1.29+
  • 端口3333(后端)和8080(前端)可用

快速开始

启动所有服务:

docker-compose up

前端: http://localhost:8080 后端: http://localhost:3333

随着重建 (代码更改后):

docker-compose up --build

分离模式 (在后台运行):

docker-compose up -d

查看日志:

# All services
docker-compose logs -f

# Specific service
docker-compose logs -f backend
docker-compose logs -f frontend

停止服务:

docker-compose down

停止并删除卷 (删除持久化的画布数据):

docker-compose down -v

建筑

服务:

  1. 后端:Node.js 18 Alpine(MCP服务器+WebSocket+REST API)
  2. 前端:Nginx Alpine(静态反应SPA)

卷:

  • canvas-data:持久画布存储(容器重启后仍能生存)
  • ./backend/src:后端开发的热重新加载(只读装载)

网络:

  • 自定义网桥网络 excalidraw-network
  • 前端依赖于后端健康检查
  • 服务通过服务名称进行通信

健康检查

这两项服务都有内置的健康检查:

# Check backend health
curl http://localhost:3333/health

# Check frontend health
curl http://localhost:8080/health

Docker会自动重启不健康的容器。

开发vs生产

发展 (热重新加载):

# docker-compose.yml - backend volumes section
volumes:
  - canvas-data:/app/data
  - ./backend/src:/app/src:ro  # Enabled

生产 (无热重新加载):

volumes:
  - canvas-data:/app/data
  # - ./backend/src:/app/src:ro  # Disabled

评论生产中的热再装载量,以获得更好的性能。

环境变量

覆盖默认值 docker-compose.yml:

environment:
  - PORT=3333
  - WS_PORT=3333
  - NODE_ENV=production
  - LOG_LEVEL=info
  - VITE_MCP_SERVER_URL=http://localhost:3333
  - VITE_WS_SERVER_URL=ws://localhost:3333

数据持久层

Canvas数据保存在Docker卷中 canvas-data:

# Inspect volume
docker volume inspect excalidraw-mcp_canvas-data

# Backup data
docker run --rm -v excalidraw-mcp_canvas-data:/data -v $(pwd):/backup alpine tar czf /backup/canvas-backup.tar.gz -C /data .

# Restore data
docker run --rm -v excalidraw-mcp_canvas-data:/data -v $(pwd):/backup alpine tar xzf /backup/canvas-backup.tar.gz -C /data

故障排除

问题:端口3333或8080已在使用中

# Change ports in docker-compose.yml
ports:
  - "3334:3333"  # backend
  - "8081:80"    # frontend

问题:服务无法启动

# Check logs
docker-compose logs

# Rebuild from scratch
docker-compose down -v
docker-compose build --no-cache
docker-compose up

问题:前端无法连接到后端

# Ensure backend is healthy
docker-compose ps

# Check backend logs
docker-compose logs backend

# Verify network
docker network inspect excalidraw-mcp_excalidraw-network

问题:更改未反映(热重新加载不起作用)

# Ensure volume mount is correct
docker-compose config | grep volumes

# Restart services
docker-compose restart

自定义Dockerfile构建

仅后端:

cd backend
docker build -t excalidraw-mcp-backend .
docker run -p 3333:3333 -v canvas-data:/app/data excalidraw-mcp-backend

仅限前端:

cd frontend
docker build -t excalidraw-mcp-frontend .
docker run -p 8080:80 excalidraw-mcp-frontend

前端独立使用

前端可以使用 独立地 没有后端MCP服务器。所有数据都持久化到浏览器本地存储。

启动前端

cd frontend
npm run dev

前端将在以下网址提供: http://localhost:5173

特性

主题管理

  • 点击左上角的菜单图标(☰)
  • 选择 主题 → 选择亮、暗或系统
  • 主题首选项已保存到本地存储

绘图

  • 使用左侧的工具栏选择形状(矩形、圆形、菱形、箭头、直线、文本、自由绘制)
  • 在画布上单击并拖动以创建元素
  • 选择要编辑属性(颜色、笔划、大小)的元素
  • 使用鼠标滚轮或捏手势进行缩放
  • 单击并拖动画布进行平移

持久性

  • Canvas每秒自动保存到本地存储
  • 视口位置(滚动、缩放)也会保持不变
  • 刷新页面以验证持久性

导出选项

  • 点击菜单图标(☰)→ 出口
  • 导出为PNG:高质量光栅图像
  • 导出为SVG:矢量格式(可缩放、可编辑)
  • 导出为JSON:完整的Excalidraw格式(.excalidraw 文件)

透明画布

  • 点击菜单图标(☰)→ 画布 → 透明画布
  • 删除所有元素前确认
  • 同时清除本地存储

键盘快捷键

标准Excalidraw快捷方式可用:

  • V -选择工具
  • R -矩形
  • D -钻石
  • O -椭圆
  • A -箭
  • L -线路
  • T -文本
  • Delete -删除所选元素
  • Ctrl+Z / Cmd+Z -撤消
  • Ctrl+Shift+Z / Cmd+Shift+Z -重做
  • Ctrl+D / Cmd+D -重复
  • Ctrl+A / Cmd+A -全选

与后端集成

前端可以通过WebSocket实时与后端同步。看 实时同步 请参阅下面的部分以获取完整详细信息。

用法

MCP工具

# Example: Create a rectangle
curl -X POST http://localhost:3333/mcp \
  -H "Content-Type: application/json" \
  -d '{
    "jsonrpc": "2.0",
    "id": 1,
    "method": "tools/call",
    "params": {
      "name": "element_create",
      "arguments": {
        "type": "rectangle",
        "x": 100,
        "y": 100,
        "width": 200,
        "height": 150
      }
    }
  }'

更多使用示例请参见 快速入门指南.

IDE的MCP服务器配置

将Excalidraw MCP服务器与AI驱动的IDE集成,用于程序化图表控制。

先决条件

确保您的后端服务器正在运行:

# Option 1: Development mode
npm run dev:all

# Option 2: Production build
npm run build && npm run start:all

MCP服务器将在 标准 (stdin/stdout),以及上的HTTP/WebSocket服务器 http://localhost:3333.

快速参考

IDE 配置文件 位置
克劳德桌面 claude_desktop_config.json 特定平台(见下文)
克劳德代码 .mcp.json 项目根
光标 mcp.json .cursor/ 目录

Claude桌面配置

配置文件位置:

  • macOS: ~/Library/Application Support/Claude/claude_desktop_config.json
  • 视窗: %APPDATA%\Claude\claude_desktop_config.json
  • Linux: ~/.config/Claude/claude_desktop_config.json

地方发展(推荐):

{
  "mcpServers": {
    "excalidraw": {
      "command": "node",
      "args": ["/absolute/path/to/excalidraw-mcp/backend/dist/index.js"],
      "env": {
        "CANVAS_DATA_DIR": "/absolute/path/to/excalidraw-mcp/backend/data",
        "LOG_LEVEL": "info"
      }
    }
  }
}

重要提示: 替换 /absolute/path/to/excalidraw-mcp 根据您的实际项目路径。

Docker(替代方案):

{
  "mcpServers": {
    "excalidraw": {
      "command": "docker",
      "args": [
        "run",
        "-i",
        "--rm",
        "-v", "/path/to/canvas-data:/app/data",
        "excalidraw-mcp-backend"
      ]
    }
  }
}

首先构建Docker镜像:

cd backend
docker build -t excalidraw-mcp-backend .

Claude代码的配置

创建或编辑 .mcp.json 在你的 项目根:

地方发展(推荐):

{
  "mcpServers": {
    "excalidraw": {
      "command": "node",
      "args": ["backend/dist/index.js"],
      "env": {
        "CANVAS_DATA_DIR": "./backend/data",
        "LOG_LEVEL": "info"
      }
    }
  }
}

使用Claude CLI:

# Project-scoped (recommended)
claude mcp add --scope project --transport stdio excalidraw \
  -- node backend/dist/index.js

# User-scoped (available across all projects)
claude mcp add --scope user --transport stdio excalidraw \
  -- node /absolute/path/to/excalidraw-mcp/backend/dist/index.js

Cursor IDE的配置

编辑 .cursor/mcp.json:

{
  "mcpServers": {
    "excalidraw": {
      "command": "node",
      "args": ["/absolute/path/to/excalidraw-mcp/backend/dist/index.js"],
      "env": {
        "CANVAS_DATA_DIR": "/absolute/path/to/excalidraw-mcp/backend/data",
        "LOG_LEVEL": "info"
      }
    }
  }
}

环境变量

变量 默认值 描述
CANVAS_DATA_DIR ./data 画布持久性目录
LOG_LEVEL info 日志记录级别(调试、信息、警告、错误)
SERVER_NAME excalidraw-mcp-server MCP服务器标识符
SERVER_VERSION 1.0.0 服务器版本

验证

配置IDE后:

  1. 重新启动IDE 加载新的MCP服务器配置
  2. 打开新对话 在AI助手中
  3. 测试连接 通过询问:
Create a simple diagram with a rectangle and circle using Excalidraw MCP

AI应使用MCP工具创建出现在前端的元素(如果正在运行)。

故障排除

问题:未检测到MCP服务器

# Verify the backend is built
cd backend && npm run build

# Check the dist folder exists
ls -la backend/dist/

# Test MCP server directly
echo '{"jsonrpc":"2.0","method":"initialize","id":1}' | node backend/dist/index.js

问题:权限被拒绝

# Ensure the backend is executable
chmod +x backend/dist/index.js

# Verify Node.js is in PATH
which node

问题:画布数据不持久

# Check data directory exists and is writable
mkdir -p backend/data
chmod 755 backend/data

实时同步

前端和后端通过WebSocket双向同步,实现多客户端协作和持久性。

运作原理

建筑:

Frontend (Browser)  ←→  WebSocket  ←→  Backend (Node.js)  ←→  JSON Storage
     ↓                                        ↓
localStorage                          MCP Tools (stdio)

连接流程:

  1. 前端连接到 ws://localhost:3333 页面加载
  2. 后端发送初始画布状态
  3. 前端启用自动同步(在菜单中切换)
  4. 更改实时传播到所有连接的客户端

来源追踪 (防止回声循环):

  • 每条消息都有 source: 'mcp' | 'frontend'
  • 客户端忽略来自自己来源的消息
  • 防止无限更新循环

特性

自动同步(在菜单中切换):

  • 开:每3秒自动更改同步(限制)
  • 关闭:独立模式(仅限本地存储)
  • 连接状态指示灯在连接时显示绿色

手动同步:

  • Menu → 同步 → 立即同步到后端:强制立即同步
  • Menu → 同步 → 从后端加载:从后端提取最新信息

多客户端支持:

  1. 在多个浏览器选项卡/窗口中打开前端
  2. 在一个选项卡中绘制
  3. 实时观察其他选项卡中的更改

离线处理:

  • WebSocket通过指数回退自动重新连接
  • 脱机时的消息缓冲区(最多100个)
  • 重新连接时发送缓冲消息

测试实时同步

步骤1:启动两台服务器

# Terminal 1: Backend
cd backend && npm run dev

# Terminal 2: Frontend
cd frontend && npm run dev

第二步:打开多个标签页

# Open http://localhost:5173 in 2+ browser tabs

步骤3:启用自动同步

  • 在每个选项卡中:菜单(☰)→ 同步 → 自动同步:关闭 → 单击以转动 开
  • 连接指示灯应显示绿色“已连接”

第四步:绘制并观察

  • 在选项卡1中绘制矩形
  • 在3秒内看到它出现在选项卡2中
  • 更改会自动保留到后端

步骤5:测试MCP集成

# Create element via MCP while frontend is open
curl -X POST http://localhost:3333/mcp \
  -H "Content-Type: application/json" \
  -d '{
    "jsonrpc": "2.0",
    "id": 1,
    "method": "tools/call",
    "params": {
      "name": "element_create",
      "arguments": {
        "type": "ellipse",
        "x": 300,
        "y": 300,
        "width": 100,
        "height": 100,
        "strokeColor": "#5f3dc4"
      }
    }
  }'

# Element appears in ALL open frontend tabs immediately

API终点

HTTP REST API:

  • GET /api/canvas/main -获取当前画布状态
  • POST /api/canvas/main/sync -将元素同步到后端
  • GET /health -使用指标进行健康检查

WebSocket消息:

  • sync_request -请求完整画布同步
  • sync_to_backend -发送要持久化的元素
  • sync_response -接收更新的元素
  • element_created -广播新元素
  • element_updated -广播元素更改
  • element_deleted -广播元素删除

故障排除

问题:连接指示灯显示红色“断开”

# Check backend is running
curl http://localhost:3333/health

# Check WebSocket port
lsof -i :3333

# Restart backend
cd backend && npm run dev

问题:选项卡之间的更改不同步

# Ensure auto-sync is enabled in ALL tabs
# Menu → Sync → Auto-Sync: ON

# Check browser console for WebSocket errors
# Open DevTools → Console tab

问题:“同步失败”错误

# Check backend logs
tail -f backend/logs/combined.log

# Verify canvas data directory exists
ls -la backend/data/

# Ensure write permissions
chmod 755 backend/data

测试

# Backend tests
cd backend
npm test

# Frontend tests
cd frontend
npm test

# Integration tests
cd backend
npm run test:integration

贡献

欢迎投稿!请看 贡献.md 作为指导方针。

许可证

MIT许可证-请参阅 许可证 了解详情。

支持