dsh-unified-desktop
Provides DOM-based reading of the active Firefox tab via the read_webpage tool, allowing agents to extract webpage content from Firefox.
Click on "Deploy Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@dsh-unified-desktopclick the Save button in the open Notepad window"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
dsh-unified-desktop
两个 Windows 桌面自动化 MCP,44 个工具,其中 15 个是重复或危险的。
这个插件把它们合成一个:29 个工具,一个命名空间,内建危险调用拦截。
不是简单的代理转发。它知道 click 该用哪个后端(wincu 走 UIA Invoke,不抢焦点),
ocr 只有一边有,read_webpage 的 DOM 模式只有另一边有,
而 PowerShell / Registry / FileSystem / Process 两边都不该暴露。
合并的是 dsh-computer-use-win(UI Automation + OCR + 元素级语义操作) 与 Windows-MCP(浏览器 DOM + 区域截图 + 应用启动)。 每个取舍的理由见 能力归属矩阵。
它解决的问题
单独装这两个插件,模型会看到 44 个工具、两份互相打架的说明:
问题 | 具体表现 |
能力重复 |
|
上下文吃紧 | 两套 schema 合计 61,599 tokens(实测),光工具定义就吃掉大半上下文 |
危险工具裸露 | windows-mcp 默认暴露 |
无统一入口 | 两个 MCP server 各自启动,工具命名空间分裂成两个 |
Related MCP server: guarded-computer-use-mcp
合并后的变化
分开装 | 本插件 | |
MCP server 数 | 2 | 1 |
工具数 | 44 | 29 |
重复能力 | 10 组 | 已去重 |
危险工具 | 全部裸露 | 内建守卫拦截 |
工具命名空间 | 分裂成两个 | 统一 |
工具数与去重结果由 lib/catalog.mjs 的 CATALOG / EXCLUDED 定义,
node test/catalog-test.mjs 会校验一致性(43 项断言)。
关于上下文占用的说明:44 个工具的实测基线是 61,599 tokens,
数据在 docs/tool-footprint.json(2026-10-22 从两个后端实时拉 tools/list 后统计)。
合并后只保留 29 个工具的 schema,但具体数值随上游 schema 体积变化,本项目未持续测量——
本插件只做去重与重命名,不裁剪单个工具的 schema。
想在自己的环境里量,可以跑 node test/aggregate-e2e.mjs,它会打印当前工具面的字符数与估算 token。
和通用 MCP 网关有什么不同
GitHub 上已有成熟的多 MCP 聚合方案(1MCP 525★、 IBM mcp-context-forge 4.7k★、 MCP-Gateway 155★)。它们是横向的:接任意 N 个 server,靠配置里的 filter 规则裁剪工具面。
本项目是纵向的:只为两个特定后端服务,靠一张能力归属表做语义级去重——
它知道 Snapshot 该拆成「树模式用 wincu、DOM 模式并入 read_webpage」,
而通用网关只能按名字过滤,不知道这两个工具其实是同一件事的不同实现。
如果你要接的是别的 MCP server,用上面那些通用网关更合适。 如果你就在 Windows 上用这两个后端,这张归属表是为你写的。
这张图由
node scripts/gen-dedup-svg.mjs从lib/catalog.mjs生成, 数字与代码永远一致,不会随文档改动而失同步。
架构
DSH ──stdio──> [aggregate.mjs] ──stdio──> wincu server.mjs
└─stdio──> windows-mcp.exe聚合层负责三件事:
合并工具面 —— 从两个后端拉
tools/list,按目录去重合并路由调用 ——
tools/call按目录映射到对应后端内建守卫 —— 危险参数在转发前拦截
能力分工
一句话概括:交互类全给 wincu,系统与浏览器类全给 windows-mcp。
选 wincu 的(它更强):
能力 | 为什么用 wincu |
| UIA 树 + RuntimeId 精确元素定位 |
| 只有 wincu 有,Windows.Media.Ocr 字级坐标 |
| 优先走 UIA Invoke 模式,不抢焦点 |
| 只有 wincu 有,UIA 语义操作 |
| 剪贴板路径支持中文,且恢复原剪贴板 |
窗口管理 | activate / close / move |
选 windows-mcp 的(wincu 没有):
能力 | 用途 |
| 浏览器 DOM 模式,读当前标签页,绕开反爬 |
| 区域截图 |
| 按开始菜单名启动应用 |
| Windows toast 通知 |
| 读写剪贴板 |
| 显示器信息、桌面控制权 |
不暴露的工具
风险类(内建守卫,且 DSH 原生工具已覆盖):
工具 | 排除原因 |
| 任意命令执行;DSH 原生 |
| 直接改注册表,风险过高 |
| DSH 原生 |
|
|
重复类(已由 wincu 的更强实现替代):
Click、Type、Move、Scroll、Shortcut、Wait、WaitFor、Snapshot、MultiSelect、MultiEdit
完整清单见 lib/catalog.mjs 的 EXCLUDED。
每一项「为什么留这个、为什么砍那个」的完整推导,见 docs/capability-matrix.md。
工具清单(29 个)
观察
snapshot screenshot read_tree element_info find ocr list_windows read_webpage display_info control_status health
鼠标键盘
click double_click type_text keypress scroll move_mouse drag set_value invoke focus
窗口
activate_window close_window move_window launch_app
等待
wait wait_for
系统
notify clipboard
安装
前置:
# 1. wincu(提供 UIA + OCR)
dsh plugin --profile web add dsh-computer-use-win
# 2. windows-mcp(提供 DOM + 应用启动)
uv tool install windows-mcp --python 3.14安装本插件:
dsh plugin --profile web add <本目录路径>打后端补丁(重要):
node scripts/patch-backend.mjs不打补丁的话,windows-mcp 会要求你连续空闲 10 秒才允许操作,
否则 screenshot / read_webpage / launch_app 等全部返回 USER_CONTROL。
详见 docs/backend-patch.md。
⚠️ 这个补丁会直接修改你本机的 windows-mcp 安装
scripts/patch-backend.mjs不是插件,它改写uv tool安装目录下的windows_mcp/desktop/control.py与control_hooks.py源文件。执行前请知悉:
重要:本插件已聚合 wincu 的能力,需禁用独立挂载的 wincu避免工具重复。
在 profile 的 cordis.patch.yml 加:
- id: mcp-dsh-computer-use-win
disabled: true重启 DSH,工具以 mcp__desk__* 出现。
设置项
项 | 默认 | 说明 |
| 全部 29 个 | 暴露哪些工具 |
|
| 策略守卫开关 |
|
| 写审计日志 |
|
| windows-mcp 桌面控制门的空闲阈值(秒) |
| 自动探测 | wincu server.mjs 路径 |
| 自动探测 | windows-mcp.exe 路径 |
|
| 工具超时 |
一个关键实现细节
wincu 必须用 .generations/live/ 下的真实路径启动,不能用 profiles/web/node_modules 的软链接。
因为它的入口判断是:
import.meta.url === pathToFileURL(process.argv[1]).href软链接会让 import.meta.url 解析成真实路径,而 argv[1] 是链接路径,两者不等,
server 会静默退出(exit 0,无任何输出)。
本插件的 resolveWcuServer() 会自动优先选 .generations 路径。
测试
npm test # 全部 6 个套件单独跑:
node test/catalog-test.mjs # 目录一致性、去重、危险工具排除(43 断言)
node test/config-test.mjs # 配置校验与路径解析(21 断言)
node test/backend-patch-test.mjs # 后端补丁状态与行为(14 断言,无后端时跳过)
node test/aggregate-e2e.mjs # 工具面合并、双后端路由(13 断言)
node test/concurrency-test.mjs # 并发不串号(6 断言)
node test/electron-verify.mjs # DSH 真实 Electron 运行时(7 断言)
catalog-test、config-test、backend-patch-test不需要运行中的后端,任何环境都能跑 (CI 默认跑这三个)。其余三个需要本机已安装 wincu 与 windows-mcp。
诊断
遇到 wm 工具被拒(USER_CONTROL)时:
node scripts/diagnose-gate.mjs输出补丁状态、5 秒内的钩子触发统计、以及 MCP 层实测结果。 完整排查过程见 docs/diagnosis-user-control.md。
排错
工具没出现(mcp__desk__* 不存在)
看日志
%APPDATA%\dsh-desktop\logs\harness.log,搜[aggregate]正常情况下应有:
[aggregate] unified-desktop 0.1.0 ready (wcu=true wm=true guard=true) [wcu] windows-computer-use MCP server 0.5.0 ready [wm] Starting MCP server 'windows-mcp'如果
wcu=false:检查 wincu 是否安装。路径必须是profiles\.generations\live\dsh-computer-use-win+*\node_modules\dsh-computer-use-win\mcp\server.mjs如果
wm=false:uv tool install windows-mcp --python 3.14
loader 一直显示 still waiting for 1 plugin entries
这是正常的。MCP 初始化约需 30-40 秒(两个后端依次启动),loader 只是计时提示, 插件就绪后不再刷新该行。
工具重复出现(mcp__wincu__* 和 mcp__desk__* 都有)
说明独立的 wincu 没有被禁用。在 profile 的 cordis.patch.yml 加:
- id: mcp-dsh-computer-use-win
disabled: true调用返回 USER_CONTROL
windows-mcp 的桌面控制门。两种情况:
没打后端补丁 → 执行
node scripts/patch-backend.mjs后重启打了补丁但你正在操作 → 停下鼠标键盘约
idleThresholdSeconds秒再试
用 control_status 查看当前状态:state: "ready" 表示可操作,"user" 表示正在等你空闲。
如果一直卡在 user 且 wait_seconds 固定在某个值附近不动,说明有设备在高频上报
无位移的鼠标移动(常见于无线接收器)。补丁 2 已处理这种情况,确认它是否应用:
node scripts/patch-backend.mjs --checkDOM 模式读不到网页
read_webpage 的 use_dom=true 需要浏览器(Chrome/Edge/Firefox)有活动标签页,
且该页面已加载完成。
已知限制
不是沙箱。守卫是正则黑名单,挡得住直白危险命令,挡不住刻意构造的绕过。
wincu 升级可能破坏路径。
resolveWcuServer按目录名前缀匹配,升级后版本号变化会自动重新探测。两个后端独立启动。一个挂了另一个仍可用,但相应工具会缺失。
DOM 模式依赖浏览器。
read_webpage的use_dom需要 Chrome/Edge/Firefox 活动标签页。参数未做归一化。两个后端的参数名保持原样(如 wincu 用
elementId,wm 用loc/label), 模型需要按各工具自己的 schema 传参。归一化在Unreleased计划中。依赖本地后端补丁。windows-mcp 0.8.8 的桌面控制门在部分硬件上不可用, 本项目通过
scripts/patch-backend.mjs修复。已向上游报告 (CursorTouch/Windows-MCP#498); 若上游合并,可移除本地补丁。详见 docs/upstream-tracking.md。
设计取舍
为什么用「聚合」而不是「改源码合并」
两个后端分别是 Node(wincu)和 Python(windows-mcp)。真合并意味着用同一种语言重写另一方的核心能力:
把 wincu 的 OCR + UIA RuntimeId 机制移植到 Python —— 工作量大且易出错
把 windows-mcp 的 DOM 提取移植到 Node —— 需要重写 CDP/IAccessible2 逻辑
聚合层用 MCP 协议做边界,两个后端各自演进,互不干扰。代价是多一个进程,收益是
升级任一方都不需要改聚合层(除非工具名变了,那会在 buildToolList 里报 missing backend tool)。
为什么排除 PowerShell / Registry / FileSystem / Process
不是能力不够,而是重复且危险:
DSH 原生已有
pwsh、read/write/edit/glob/grep,且受 DSH 沙箱与审批管辖MCP server 是独立进程,DSH 的沙箱管不到它(
dsh-fs-sandbox的策略只作用于 DSH 自己的工具)保留它们等于开一条绕过沙箱的通道,收益为零
贡献
git clone <repo>
cd dsh-unified-desktop
npm test # 需要本机已装 wincu 与 windows-mcp添加新工具:
在
lib/catalog.mjs的CATALOG加条目(name/backend/target/description)跑
node test/catalog-test.mjs—— 它会校验命名规范、去重、能力覆盖跑
node test/aggregate-e2e.mjs—— 确认后端真的提供了该工具
修改守卫规则:编辑 lib/guard.mjs 的 PS_RULES / REG_DENY_PREFIX,然后跑 npm test。
License
MIT。聚合层原创;能力来自两个上游项目(均为 MIT)。
上游的版权声明见 THIRD-PARTY-NOTICES.md。
This server cannot be deployed
Maintenance
Related MCP Connectors
- ZionDeskOAuthapp.ziondesk
Connect ChatGPT, Claude, Cursor or VS Code to your Windows PC: files, terminal, browser, apps.
Connect AI assistants to your approved computer for files, commands, browser and desktop tasks.
Web scraping, browser automation, screenshots and AI data extraction for AI agents via MCP.
214 tools for AI agents over one MCP endpoint: image, video, audio, 3D, data, storage, mail, GPUs.
Related MCP Servers
- AlicenseNot gradedqualityBmaintenanceEnables comprehensive Windows desktop automation including screen capture, OCR text extraction, mouse/keyboard control, window management, process control, and clipboard operations through 25+ tools for AI agents.61 PyPI8MIT
- AlicenseNot gradedqualityBmaintenanceEnables agentic control of Windows via MCP tools for screenshots, mouse, keyboard, UI Automation, OCR, windows, and clipboard, while risky actions require real-human approval through a policy-gated dialog with audit logging.5MIT
- AlicenseNot gradedqualityCmaintenanceEnables MCP clients to observe and control the Windows desktop through the UI Automation accessibility tree — no vision model required — by exposing tools for reading windows and interactive elements, clicking, typing, scrolling, shortcuts, PowerShell, screenshots, virtual desktops, web scraping, file operations and persistent memory, including background-window control without stealing focus. An optional agent mode adds a single natural-language task tool that runs the full upstream agent loop when an LLM provider is configured.1MIT
- AlicenseNot gradedqualityBmaintenanceEnables agents to control Windows desktop applications through UI Automation and Win32, supporting window management, mouse/keyboard input, element inspection, screenshots, OCR, macro recording, and autonomous multi-app missions. It also provides an HTTP/stdio MCP interface, an operator UI, and optional telemetry and safety controls.MIT