让模型直接读写并操作任意 Windows 桌面应用
30.8/100
综合分
1
GitHub 星标
—
npm 周下载
—/5
用户评分
数据截至 2026/10/27 · 周下载取自 npm 全网(含 CI / 镜像),非本站安装数;综合分由星标、活跃度与兼容性检查合成。
安装命令 · 需先装 dsh CLI 引擎
dsh plugin --profile web add 111xjyuan/dsh-desktop-sidecar该包不可直接 npm 安装,改从 GitHub 源安装(明细见下方安装检查)
状态速览
判定依据:实装验证 · 静态安装检查 · 自动扫描 · 仓库维护状态信任档位:已验证
是什么
dsh 原生插件 · ui
安全吗
本站尚未对该插件做风险分级
暂未覆盖,不等同于无风险
还在维护吗
活跃:最近一次提交在 8 天前
档位由哪些信号合成
本站实装验证(真实安装 L4 覆盖全站;L5 为运行时冒烟或实机截图,覆盖范围小于 L4) · 验证所用 dsh 版本 · 静态安装检查 · 风险分级 · 仓库维护状态。 下方各区块是它的证据明细。
社区实装还没有人打卡 · 装过的第一个就是你
安全扫描自动 · 静态分析源码v2.7.0🔵 扫描:含敏感能力尚无人工评估展开查看扫描说明与证据 ↓
安全扫描自动 · 静态分析源码
v2.7.0静态扫描发现插件具备触达本地系统的能力:执行外部命令、读写/删除本地文件、读取剪贴板或密钥类环境变量(至少其一)。这是能力清单,不是危险判定——具体能力项与证据见下方,安装前请自行判断是否需要。
可执行外部命令读写/删除本地文件发起外部网络请求
查看扫描证据(共 51 处,展示前 51 条)
- 执行外部命令来自配置/变量lib/index.js:35
const c = spawnProcess(cmd, argv, opts); - 写入本地文件lib/index.js:48
mkdirSync(SHOT_DIR, { recursive: true }); - 读取本地文件lib/index.js:50
for (const f of readdirSync(SHOT_DIR)) { - 读取本地文件lib/index.js:52
try { if (now - statSync(p).mtimeMs > 3600_000) unlinkSync(p); } catch {} - 删除本地文件lib/index.js:52
try { if (now - statSync(p).mtimeMs > 3600_000) unlinkSync(p); } catch {} - 写入本地文件lib/index.js:292
mkdirSync(dir, { recursive: true }); - 写入本地文件lib/index.js:479
mkdirSync(dirname(file), { recursive: true }); - 写入本地文件lib/index.js:480
writeFileSync(file, png); - 读取本地文件lib/index.js:1032
if (looksPath && !existsSync(bare)) { - 执行外部命令固定命令lib/index.js:1038
const found = String(execSync('where.exe ' + bare, { timeout: 2500, windowsHide: true, stdio: ['ignore', 'pipe', 'ignore'] }) || '').split(String.from - 读取本地文件lib/ocr.mjs:16
for (const c of PS_CANDIDATES) { if (c && existsSync(c)) { PS = c; return PS; } } - 执行外部命令固定命令lib/ocr.mjs:17
const probe = spawnSync('where', ['powershell.exe'], { encoding: 'utf8' }); - 读取本地文件lib/ocr.mjs:39
const img = decodePng(readFileSync(path)); - 写入本地文件lib/ocr.mjs:45
writeFileSync(src, encodePng(up.width, up.height, up.rgb)); - 删除本地文件递归lib/ocr.mjs:55
try { rmSync(dir, { recursive: true, force: true }); } catch {} - 执行外部命令来自配置/变量lib/ocr.mjs:61
const r = spawnSync(resolvePs(), ['-NoProfile', '-NonInteractive', '-ExecutionPolicy', 'Bypass', '-File', OCR_PS1, '-Path', path, '-Language', languag - 写入本地文件lib/ocr.mjs:103
writeFileSync(f, png); - 删除本地文件递归lib/ocr.mjs:106
try { rmSync(dir, { recursive: true, force: true }); } catch {} - 读取本地文件lib/ocr.mjs:117
for (const name of readdirSync(tmpdir())) { - 读取本地文件lib/ocr.mjs:121
const st = statSync(p); - 删除本地文件递归lib/ocr.mjs:124
rmSync(p, { recursive: true, force: true }); - 执行外部命令来自配置/变量lib/uia.mjs:11
const r = spawnSync(PS, ['-NoProfile', '-NonInteractive', '-ExecutionPolicy', 'Bypass', '-File', UIA_PS1, ...args], { - 执行外部命令固定命令lib/ps.mjs:17
const probe = spawnSync('where', ['powershell.exe'], { encoding: 'utf8', windowsHide: true, timeout: 5000 }); - 读取本地文件lib/ps.mjs:24
if (c === 'powershell.exe' || existsSync(c)) { cached = c; return c; } - 执行外部命令来自配置/变量lib/ps.mjs:34
const r = spawnSync(powershellPath(), ['-NoProfile', '-NonInteractive', '-Command', - 发起网络请求lib/web.mjs:53
const res = await fetch('http://127.0.0.1:' + port + '/json/version', { signal: AbortSignal.timeout(1200) }); - 读取本地文件lib/web.mjs:65
const rec = JSON.parse(readFileSync(PROFILE_STATE, 'utf8')); - 写入本地文件lib/web.mjs:74
mkdirSync(PROFILE_ROOT, { recursive: true }); - 写入本地文件lib/web.mjs:75
writeFileSync(PROFILE_STATE, JSON.stringify(rec, null, 2)); - 读取本地文件lib/web.mjs:91
if (override && existsSync(override)) return override; - 读取本地文件lib/web.mjs:92
const found = CANDIDATES.find((p) => existsSync(p)); - 发起网络请求lib/web.mjs:236
const res = await fetch('http://127.0.0.1:' + port + '/json/list', { signal: AbortSignal.timeout(1500) }); - 写入本地文件lib/web.mjs:279
mkdirSync(PROFILE_ROOT, { recursive: true }); - 执行外部命令来自配置/变量lib/web.mjs:297
this.child = spawn(bin, argv, { stdio: 'ignore', windowsHide: !this.headed }); - 发起网络请求lib/web.mjs:317
const res = await fetch('http://127.0.0.1:' + port + '/json/version', { signal: AbortSignal.timeout(1500) }); - 发起网络请求lib/web.mjs:328
const res = await fetch('http://127.0.0.1:' + port + '/json/new?' + encodeURIComponent(url), { method: 'PUT' }); - 发起网络请求lib/web.mjs:659
const v = await fetch('http://127.0.0.1:' + this.port + '/json/version', { signal: AbortSignal.timeout(1200) }); - 删除本地文件递归lib/web.mjs:681
try { await rm(this.profileDir, { recursive: true, force: true }); break; } catch { await sleep(200 * (i + 1)); } - 删除本地文件lib/web.mjs:688
if (child) { try { rmSync(PROFILE_STATE, { force: true }); } catch {} } - 删除本地文件递归lib/web.mjs:698
try { await rm(PROFILE_ROOT, { recursive: true, force: true }); break; } catch { await sleep(250 * (i + 1)); } - 删除本地文件递归lib/web.mjs:726
if (liveProfile) { try { rmSync(liveProfile, { recursive: true, force: true }); } catch {} } - 写入本地文件lib/actions-log.mjs:12
try { mkdirSync(DIR, { recursive: true }); } catch {} - 写入本地文件lib/actions-log.mjs:26
appendFileSync(FILE, line + '\n', 'utf8'); - 读取本地文件lib/actions-log.mjs:28
const raw = readFileSync(FILE, 'utf8'); - 写入本地文件lib/actions-log.mjs:31
writeFileSync(FILE, lines.slice(-MAX_LINES).join('\n') + '\n', 'utf8'); - 读取本地文件lib/actions-log.mjs:42
if (!existsSync(FILE)) return { file: FILE, total: 0, entries: [] }; - 读取本地文件lib/actions-log.mjs:44
try { raw = readFileSync(FILE, 'utf8'); } catch { return { file: FILE, total: 0, entries: [] }; } - 读取本地文件lib/actions-log.mjs:55
if (!existsSync(FILE)) return { cleared: true, file: FILE, total: 0 }; - 读取本地文件lib/actions-log.mjs:58
try { total = readFileSync(FILE, 'utf8').split('\n').filter(Boolean).length; } catch {} - 写入本地文件lib/actions-log.mjs:59
try { renameSync(FILE, FILE + '.1'); } catch {} - 写入本地文件lib/actions-log.mjs:60
writeFileSync(FILE, '', 'utf8');
扫描于 2026/11/2(1 天前) · 范围 入口闭包 + 发布文件清单 · 来源 GitHub 仓库
静态扫描只反映源码中出现的调用,不构成安全背书;人工评估与自动扫描相互独立、互不覆盖。
依赖的 DSH / Cordis 模块
@deepseek-ai/dsh-tools给这个插件打分还没有人投票↓
用户评分
还没有人投票,来当第一个
DeepSeek Harness 原生 Windows 桌面控制:UIA 控件树、离线 OCR、可验证点击、Unicode 输入。零外部运行时。
README
由 DeepSeek 最新模型翻译生成dsh-desktop-sidecar
给 DeepSeek Harness 装上「手」:原生 Windows 桌面控制。不依赖 Python、不下载驱动、不弹窗口、不走 MCP。
在任意 Windows 10/11 应用里看屏幕、读文字、点按钮、打字、按快捷键——包括微信、Office、浏览器、网课播放器这些没有自动化接口的软件。
和同类方案的区别
| | 本项目 | MCP + UIA 方案(如 dsh-computer-use-win) | CUA/视觉方案 |
| 安装 | npm 一个包 | 需另装 MCP 客户端 + 桥 | 需下载 ~60MB 驱动二进制 |
| 运行时 | 零外部依赖(koffi 直调 Win32) | Python/PowerShell 子进程 | 独立驱动进程 |
| 读界面 | UIA 控件树 或 离线 OCR | 只有 UIA | 只有截图(靠视觉模型) |
| 微信/Electron/Qt | ✅ OCR 兜底可用 | ❌ UIA 树为空 | ✅ 但 token 贵 |
| 点击校验 | ✅ 点完自动比对像素 | ❌ | ❌ |
| 环境自检 | desktop_doctor 四项体检 | ❌ | ❌ |
一句话:有 UIA 用 UIA(精确、后台、省 token),没有就自动降级到 OCR + 坐标点击——不用你判断。
展开完整文档(README 剩余 1 节)
dsh-desktop-sidecar
给 DeepSeek Harness 装上「手」:原生 Windows 桌面控制。不依赖 Python、不下载驱动、不弹窗口、不走 MCP。
在任意 Windows 10/11 应用里看屏幕、读文字、点按钮、打字、按快捷键——包括微信、Office、浏览器、网课播放器这些没有自动化接口的软件。
和同类方案的区别
| | 本项目 | MCP + UIA 方案(如 dsh-computer-use-win) | CUA/视觉方案 |
| 安装 | npm 一个包 | 需另装 MCP 客户端 + 桥 | 需下载 ~60MB 驱动二进制 |
| 运行时 | 零外部依赖(koffi 直调 Win32) | Python/PowerShell 子进程 | 独立驱动进程 |
| 读界面 | UIA 控件树 或 离线 OCR | 只有 UIA | 只有截图(靠视觉模型) |
| 微信/Electron/Qt | ✅ OCR 兜底可用 | ❌ UIA 树为空 | ✅ 但 token 贵 |
| 点击校验 | ✅ 点完自动比对像素 | ❌ | ❌ |
| 环境自检 | desktop_doctor 四项体检 | ❌ | ❌ |
一句话:有 UIA 用 UIA(精确、后台、省 token),没有就自动降级到 OCR + 坐标点击——不用你判断。
不需要视觉模型也能用。 截图会作为图片返回给支持看图的模型,但每一条能力都有纯文本路径(UIA 控件树 / 离线 OCR / 坐标),所以文本模型照样能跑完整流程——这是本项目和「截图转视觉模型」类方案的根本区别。
desktop_windows → 现在有哪些窗口 desktop_tree → 这个窗口有哪些控件(UIA,带编号索引,可直接点) desktop_invoke → 直接触发控件(不移动鼠标、不需要窗口在前台) desktop_read → 窗口里写了什么(离线 OCR,带坐标) desktop_capture → 截图:直接作为图片返回,带坐标尺 + 缩放契约,画面没变就不重复发 desktop_click → 点控件编号(带身份校验)/ 点文字 / 点坐标(点后像素校验) desktop_sequence → 批量:一次调用跑多步(dryRun / stopOnError / Esc 中止) desktop_type → 输入中文(剪贴板 + 真 Ctrl+V,稳) desktop_key → 按键 / 组合键 desktop_course → 网课自动播放(帧差判播放 + 自动下一节) desktop_doctor → 环境自检(平台 / DPI / 多屏 / OCR / 前台锁 / 输入控件)
0.5.0 更新(对标 dsh-pilot 后补齐)
- DPI 感知:启动即声明 per-monitor v2,并在 desktop_doctor 里体检——125%/150% 缩放下坐标不再偏。
- 截图直接给模型看:desktop_capture 现在返回 image block(不再让你多调一次读图),图上叠了坐标尺(顶部 x、左侧 y,单位是客户区像素)。
- 帧去重:同一窗口画面没变时返回 unchanged:true 且不重复附图,省 token。
- 批量:desktop_sequence 一次调用跑多步,支持 dryRun、stopOnError、步骤上限 24,按住 Esc 可随时中止。
- UIA 索引点击 + 身份校验:desktop_tree 返回编号,desktop_click{control:N, expect:{role,name}} 会重读控件树核对身份,控件挪位就拒点而不是点错。
- 控件过滤:meaningfulOnly(默认开)把装饰性容器滤掉并给出 controlTotal / filteredOut,几百个元素降到几十个;有名字的 Pane 放行(原生对话框)。
3 分钟上手
1. 安装,任选一种:
A. npm(已发布,推荐) plugin_manager install_bundle dsh-desktop-sidecar
B. 插件市场:搜 desktop-sidecar
C. 本地源码(开发用) plugin_manager install_bundle file:<本目录绝对路径>
2. 先自检,有异常会直接给修复建议:
调用 desktop_doctor
期望 ok: true,四项:platform / ocr / foreground / editable-child。
3. 让它干一件事,例如:
打开记事本,写一句“你好,世界”
模型会依次走 desktop_windows → desktop_type → desktop_read 验证。
两条路线(很重要)
| 应用类型 | 识别方式 | 说明 |
| 记事本、Office、资源管理器、设置、WinUI 应用 | UIA 控件树 | desktop_tree 拿到按钮/菜单的名字与 Invoke 能力,desktop_invoke 直接触发——不移动鼠标、不需要前台,最稳也最省 token |
| 微信、VS Code、Discord、Electron/Qt 自绘界面 | OCR + 坐标点击 | 这些应用不实现 UIA,desktop_tree 会返回空并自动附一段 OCR 摘要;用 desktop_read 找字、desktop_click 的 text 参数按字点击 |
经验法则:能用 desktop_invoke 就别用 desktop_click;能按文字点就别按坐标点。
常见问题
OCR 返回 0 行?
系统缺「中文(简体)」OCR 语言包。设置 → 时间和语言 → 语言 → 添加中文(简体) → 可选功能勾选「光学字符识别」。desktop_doctor 会直接指出这条。
点了没反应? 看返回里的 changed 和 hint。changed:false 且 inClient:true 多半是点在了纯文本区(光标移动也算成功);按钮/菜单请改 desktop_invoke 或 desktop_key。
截图拍到了别的窗口? 工具会先把目标窗口抬到最上层再截;仍不对就先把它切前台(desktop_invoke + focus,或手动点一下)。
中文变成乱码? desktop_type 走剪贴板 + 真 Ctrl+V,正常不会乱;目标应用禁用粘贴时,改用 desktop_key 逐键发送。
管理员窗口点不动? Windows UIPI 限制:非提权进程不能向提权窗口发送输入。用管理员身份启动 DSH。
权限与安全
- 一切操作都在你本机的桌面会话内,只能做你自己能做的操作。
- 不上传屏幕内容或文字;OCR 用 Windows 本地引擎,完全离线。
- 截图临时文件在 %TEMP%\dsh-sidecar,超过 1 小时自动清理。
- 前台锁、UIPI、锁屏/安全桌面这类系统限制不会被绕过——这是设计选择,不是缺陷。
平台
Windows 10 1809+ / Windows 11,x64 与 arm64。
macOS / Linux 未实现(需要完全不同的辅助功能 API,暂不在计划内)。
开发
开发期把它同步进 DSH profile 的 node_modules,避免每次重装 powershell -NoProfile -File scripts/sync.ps1
改完 lib/ 后在 DSH 插件面板「禁用 → 启用」即可热重载,无需重启。
依赖:koffi(原生 FFI);peer @deepseek-ai/dsh-tools >= 0.1.5-rc.1。
许可
MIT预览分享卡片长什么样 ↓
分享 · DeepSeek Harness Hub
111xjyuan/dsh-desktop-sidecar
让模型直接读写并操作任意 Windows 桌面应用
相关插件 · UI / 主题
破甲增强版JeffKeeping/dsh-purge-plus
dsh-purge 的非官方分支fork:适配 DeepSeek Harness 0.2.1-rc.2、破甲内核…
★ 387已汉化DeepSeek 客户端
71.9
无代码业务系统平台nocobase/nocobase
NocoBase 是什么
★ 24,804已汉化DSH
71.8
1Panel 服务器面板1Panel-dev/1Panel
全球 250 万+ 自托管用户共同喜爱。
★ 37,344已汉化DSH
71.5
终端编码代理esengine/DeepSeek-Reasonix
· 指南 · ACP · 扩展开发 · 规格 · 官方网站 · Discord · QQ
★ 36,045已汉化DSH
71.2
工作状态行动态ccch1mneyyy/working-activity
作者:chimney@ccch1mneyyy。社区项目,非 DeepSeek 官方项目。
★ 664已汉化DSH
71.2
多模型配置管家farion1231/cc-switch
跨平台桌面一体化助手,支持 Claude Code、Codex、OpenCode、DeepSeek Harness 等工具,唯一官网 ccswitch.io
★ 151,202已汉化DSH
71.1
这是你的仓库?认领条目