内容
AutoCAD MCP 服务器 — 生产 README
=====================================
## 架构
一个模型上下文协议(MCP)服务器,通过 COM 自动化直接将一个 LLM(Gemini CLI,Claude Desktop)连接到正在运行的 AutoCAD 实例。AI 可以读取绘图状态,绘制建筑元素,注释,标注,管理文件,并撤销自己的错误。
```
LLM 代理(Gemini/Claude)
↕ JSON-RPC (stdio)
FastMCP 服务器(server.py)
↕
AutoCAD COM 客户端(autocad_client.py)
↕ win32com VARIANT 安全数组
AutoCAD 2022-2025(Windows)
↕
模拟 CAD 引擎(macOS/离线备用)
```
## 快速入门
### macOS / Linux (开发模式)
```bash
# 安装依赖项
pip3 install mcp pyyaml pytest
# 在模拟/模拟模式下运行
AUTOCAD_MOCK=1 python server.py
```
### Windows (实时 AutoCAD)
```bash
# 安装 Windows COM 依赖项
pip install pywin32 mcp pyyaml
# 运行 - 将自动连接到正在运行的 AutoCAD
python server.py
```
### Gemini CLI 配置
添加到 `~/.gemini/config.yaml`:
```yaml
mcpServers:
autocad:
command: python
args:
- /path/to/autocad_mcp_server/server.py
env:
AUTOCAD_MOCK: "0" # "1" 用于离线测试
```
## 可用工具(共 40 个)
### 上下文和查询
| 工具 | 描述 |
|------|-------------|
| `get_drawing_summary` | 绘图图层,实体数量,范围,单位信息 |
| `get_drawing_units` | 当前单位系统(毫米/英寸/英尺)和转换因子 |
| `query_entities` | 读取模型空间实体,带图层/类型过滤 |
| `query_entities_fast` | 大型绘图的高速选择集查询 |
| `get_spatial_summary` | 绘图的鸟瞰网格地图,用于 LLM 空间推理 |
### 绘图图元
| 工具 | 描述 |
|------|-------------|
| `draw_line` | 单线实体 |
| `draw_polyline` | 多顶点多线段 |
| `draw_circle` | 通过中心 + 半径绘制圆 |
| `draw_arc` | 通过中心,半径,起始/结束角度绘制弧 |
| `draw_rectangle` | 轴对齐矩形(闭合多线段) |
### 语义架构
| 工具 | 描述 |
|------|-------------|
| `draw_wall` | 双线墙(中心轴 + 厚度) |
| `create_room` | 完整房间:4 面墙 + 门 + 窗户 + 标签 |
| `cleanup_wall_junctions` | 修复重叠的墙角(L/T/十字交叉点) |
| `calculate_room_area` | 平方米和平方英尺的地板面积 |
| `label_room` | 在质心处放置房间名称 + 面积 |
| `apply_architectural_template` | 配置 AIA 标准图层 |
### 块管理
| 工具 | 描述 |
|------|-------------|
| `insert_architectural_block` | 插入门/窗/柱/家具块 |
| `snap_block_to_grid` | 捕捉到结构网格然后插入块 |
| `align_block_to_wall_segment` | 沿墙轴放置门/窗 |
| `list_available_blocks` | 查看库和绘图中的所有块 |
| `load_block_from_file` | 从外部 .dwg 文件导入块 |
### 修改
| 工具 | 描述 |
|------|-------------|
| `modify_entity` | 通过句柄移动/缩放/旋转/删除/重新图层 |
| `copy_entity` | 通过位移矢量复制 |
| `array_entity_rectangular` | 创建复制的矩形阵列 |
| `mirror_entity` | 跨线镜像 |
### 注释
| 工具 | 描述 |
|------|-------------|
| `add_text` | 单行文本实体 |
| `add_mtext` | 带换行的多行文本 |
| `add_linear_dimension` | 线性水平/垂直标注 |
| `add_aligned_dimension` | 对齐标注(跟随角度) |
| `add_hatch` | 填充图案(ANSI31,AR-CONC 等) |
### 图层和样式
| 工具 | 描述 |
|------|-------------|
| `set_layer_properties` | 颜色(ACI),线型,线宽,冻结/锁定 |
| `load_linetype` | 从 acad.lin 加载 DASHED/CENTER/HIDDEN |
### 文件 I/O
| 工具 | 描述 |
|------|-------------|
| `save_drawing` | 保存活动文档 |
| `save_drawing_as` | 保存到新路径(dwg/dxf/dwt) |
| `open_drawing` | 打开 .dwg 文件 |
| `new_drawing` | 创建新绘图(可选模板) |
| `export_to_pdf` | 导出到 PDF |
### 撤销/重做
| 工具 | 描述 |
|------|-------------|
| `undo_last_action` | 原子撤销最后一次 AI 工具调用 |
| `redo_last_action` | 重做上一次撤销的操作 |
### 维护
| 工具 | 描述 |
|------|-------------|
| `purge_drawing` | 清除未使用的绘图定义 |
## 配置
编辑服务器目录中的 `config.yaml`:
```yaml
units:
preferred_input: "mm" # 单位 LLM 应用于尺寸
fallback_drawing_unit: "mm" # 如果 INSUNITS=0(无单位绘图)
architecture:
default_wall_thickness: 200.0 # 毫米
default_door_width: 900.0
default_window_width: 1200.0
block_library:
search_paths:
- "./blocks/" # 本地块库目录
- "${AUTOCAD_BLOCK_LIB}" # 可选环境变量路径
```
## 标准图层(AIA 惯例)
| 图层 | 颜色 | 用途 |
|-------|-------|---------|
| `A-WALL` | 黄色(2) | 建筑墙 |
| `A-DOOR` | 青色(4) | 门 |
| `A-GLAZ` | 绿色(3) | 窗户/玻璃 |
| `S-COLS` | 红色(1) | 结构柱 |
| `S-GRID` | 灰色(8) | 结构网格线 |
| `A-ANNO-DIMS` | 洋红色(6) | 尺寸 |
| `A-ANNO-TEXT` | 白色(7) | 文本和标签 |
| `A-WALL-PATT` | 灰色(9) | 墙填充图案 |
| `I-FURN` | 蓝色(5) | 室内家具 |
## 运行测试
```bash
# 单元测试(不需要 AutoCAD)
AUTOCAD_MOCK=1 python -m pytest tests/ -v
# 特定测试文件
python -m pytest tests/test_coordinate_utils.py -v
python -m pytest tests/test_unit_engine.py -v
python -m pytest tests/test_wall_solver.py -v
python -m pytest tests/test_tools_mock.py -v
# 带有覆盖率报告
AUTOCAD_MOCK=1 python -m pytest tests/ -v --cov=. --cov-report=html
```
## 文件结构
```
autocad_mcp_server/
├── server.py — MCP 工具定义(~40 个工具)
├── autocad_client.py — COM 客户端 + 模拟 CAD 引擎
├── com_helpers.py — VARIANT 类型转换 + 线程锁
├── coordinate_utils.py — 几何数学,捕捉,墙角
├── unit_engine.py — 单位检测和转换
├── block_library.py — 块文件发现和导入
├── wall_solver.py — 墙交叉点清理算法
├── undo_manager.py — 撤销/重做组管理器
├── config.py — YAML 配置加载器
├── config.yaml — 默认配置
├── blocks/ — 块 .dwg 文件库
├── tests/
│ ├── test_coordinate_utils.py
│ ├── test_unit_engine.py
│ ├── test_wall_solver.py
│ └── test_tools_mock.py
└── requirements.txt
```
## 应用的关键错误修复(vs. v1.0)
| 错误 | 文件 | 修复 |
|-----|------|-----|
| B1: `math` 未导入 | `server.py` | 已添加 `import math` |
| B2: `math.to_degrees` 猴子补丁 | `coordinate_utils.py` | 已修复链式赋值 |
| B3: COM VARIANT 类型不匹配 | `autocad_client.py` | 所有坐标参数使用 `to_variant_point()` |
| B4: 缺失 `functools.wraps` | `autocad_client.py` | 已添加 `@functools.wraps(func)` |
| B5: 冗余 `CoInitialize` | `autocad_client.py` | COM 在 `connect()` 中初始化一次 |
## 已知限制
- 通过 SendCommand 导出 PDF 可能需要某些 AutoCAD 版本的用户交互。
替代方案:使用 `save_drawing_as` 和 DXF 格式进行承包商交换。
- 填充图案 AppendOuterLoop 在 AutoCAD 2022+ 中具有版本特定的行为。
在生产中,请使用 Windows 上的 AutoCAD 2024 验证。
- 弧/圆捕捉模式未在 `snap_to_entities` 中实现,用于端点/象限捕捉。