🎁 福利专区全网大模型免费应用 + 新用户福利 + 注册活动入口,低成本玩转 AI

桌面图形外壳 R2h1/deepseek-harness-app

DeepSeek Harness
R2h174 天前有提交已提供中文文档扫描:含敏感能力

双击启动自动拉起引擎,在原生窗口打开完整 GUI

28.2/100
综合分
2
GitHub 星标
—
npm 周下载
—/5
用户评分

数据截至 2026/9/16 · 周下载取自 npm 全网(含 CI / 镜像),非本站安装数;综合分由星标、活跃度与兼容性检查合成。

安装命令 · 需先装 dsh CLI 引擎
dsh plugin --profile web add R2h1/deepseek-harness-app
该包不可直接 npm 安装,改从 GitHub 源安装(明细见下方安装检查)

状态速览

判定依据:实装验证 · 静态安装检查 · 自动扫描 · 仓库维护状态
信任档位:已验证
是什么[目录]—
dsh 原生插件 · ui
暂无时间戳·判据 →
装得上吗[实装验证]✓
本站已真实安装成功
非静态推断
L4 · 真实安装等级说明 →
数据截至 2026/09/26·判据 →
安全吗[自动扫描]—
本站尚未对该插件做风险分级
暂未覆盖,不等同于无风险
数据截至 2026/11/05·判据 →
还在维护吗[仓库]—
更新放缓:最近一次提交在 74 天前
暂无时间戳·判据 →
图例:✓ 通过! 需注意— 未判定 / 无数据· 「未判定」= 本站尚无数据,不代表插件有问题
档位由哪些信号合成

本站实装验证(真实安装 L4 覆盖全站;L5 为运行时冒烟或实机截图,覆盖范围小于 L4) · 验证所用 dsh 版本 · 静态安装检查 · 风险分级 · 仓库维护状态。 下方各区块是它的证据明细。

验证判据与等级说明 →

可信度证据

安全扫描自动 · 静态分析源码
v2.7.0
🔵 扫描:含敏感能力尚无人工评估
展开查看扫描说明与证据 ↓

静态扫描发现插件具备触达本地系统的能力:执行外部命令、读写/删除本地文件、读取剪贴板或密钥类环境变量(至少其一)。这是能力清单,不是危险判定——具体能力项与证据见下方,安装前请自行判断是否需要。

可执行外部命令读写/删除本地文件发起外部网络请求
查看扫描证据(共 59 处,展示前 56 条)
  • 读取本地文件
    src/bun/backend.ts:51
    return existsSync(join(dir, BUNDLED_BACKEND_ENTRY)) ? dir : null;
  • 读取本地文件
    src/bun/backend.ts:62
    return existsSync(candidate) ? candidate : null;
  • 读取本地文件
    src/bun/backend.ts:73
    const raw = readFileSync(join(dir, "VERSION"), "utf8").trim();
  • 读取本地文件
    src/bun/backend.ts:87
    return existsSync(join(dir, "apps/cli/src/bin.ts"));
  • 读取本地文件
    src/bun/backend.ts:91
    return existsSync(join(dir, BUNDLED_BACKEND_ENTRY));
  • 读取本地文件
    src/bun/index.ts:56
    const raw = readFileSync(resolve(process.cwd(), "../Resources/version.json"), "utf8");
  • 读取本地文件
    src/bun/index.ts:203
    if (existsSync(candidate)) return candidate;
  • 读取本地文件
    src/bun/index.ts:217
    if (existsSync(candidate)) return candidate;
  • 读取本地文件
    src/bun/index.ts:230
    if (existsSync(candidate)) return candidate;
  • 写入本地文件
    src/bun/logger.ts:31
    mkdirSync(dir, { recursive: true });
  • 写入本地文件
    src/bun/logger.ts:47
    appendFileSync(logPath(), line + "\n");
  • 读取本地文件
    src/bun/mobile-access.ts:114
    if (existsSync(candidate)) return candidate;
  • 发起网络请求
    src/bun/mobile-access.ts:138
    upstreamRes = await fetch(`http://${upstream}${url.pathname}${url.search}`, init);
  • 发起网络请求
    src/bun/mobile-access.ts:227
    fetch(req, srv) {
  • 发起网络请求
    src/bun/mobile-access.ts:314
    fetch(req) {
  • 读取本地文件
    src/bun/mobile-access.ts:327
    return new Response(readFileSync(lib), {
  • 读取本地文件
    src/bun/mobile-access.ts:519
    const raw = readFileSync(this.tunnelAutoPath, "utf8");
  • 写入本地文件
    src/bun/mobile-access.ts:535
    mkdirSync(this.tunnelCacheDir, { recursive: true });
  • 写入本地文件
    src/bun/mobile-access.ts:536
    writeFileSync(this.tunnelAutoPath, JSON.stringify({ at: Date.now() }), "utf8");
  • 删除本地文件
    src/bun/mobile-access.ts:538
    rmSync(this.tunnelAutoPath, { force: true });
  • 读取本地文件
    src/bun/single-instance.ts:72
    if (existsSync(lock)) {
  • 读取本地文件
    src/bun/single-instance.ts:73
    const pid = Number(readFileSync(lock, "utf8").trim());
  • 删除本地文件
    src/bun/single-instance.ts:77
    rmSync(lock, { force: true });
  • 写入本地文件
    src/bun/single-instance.ts:79
    writeFileSync(lock, String(process.pid));
  • 删除本地文件
    src/bun/single-instance.ts:82
    rmSync(lock, { force: true });
  • 写入本地文件
    src/bun/tunnel.ts:63
    const out = createWriteStream(dest, { flags });
  • 写入本地文件
    src/bun/tunnel.ts:74
    const out = createWriteStream(dest);
  • 读取本地文件
    src/bun/tunnel.ts:78
    const rs = createReadStream(part);
  • 发起网络请求
    src/bun/tunnel.ts:95
    const head = await fetch(url, { method: "HEAD", signal }).catch(() => null);
  • 发起网络请求
    src/bun/tunnel.ts:102
    const res = await fetch(url, { signal });
  • 发起网络请求
    src/bun/tunnel.ts:119
    const res = await fetch(url, {
  • 删除本地文件
    src/bun/tunnel.ts:129
    await Promise.all(parts.map((p) => rm(p.file, { force: true }).catch(() => {})));
  • 读取本地文件
    src/bun/tunnel.ts:137
    if ((await stat(direct)).isFile()) return direct;
  • 读取本地文件
    src/bun/tunnel.ts:142
    const versions = await readdir(join(extractDir, "cloudflared"));
  • 读取本地文件
    src/bun/tunnel.ts:146
    if ((await stat(bin)).isFile()) return bin;
  • 读取本地文件
    src/bun/tunnel.ts:174
    const st = await stat(tmpFile);
  • 删除本地文件
    src/bun/tunnel.ts:180
    await rm(tmpFile, { force: true }).catch(() => {});
  • 写入本地文件
    src/bun/tunnel.ts:195
    await rename(tmpFile, finalBin).catch(async () => {
  • 写入本地文件
    src/bun/tunnel.ts:196
    await copyFile(tmpFile, finalBin).catch(() => {});
  • 写入本地文件
    src/bun/tunnel.ts:200
    await mkdir(extractDir, { recursive: true });
  • 执行外部命令固定命令
    src/bun/tunnel.ts:203
    const child = spawn("tar", ["-xzf", tmpFile, "-C", extractDir], { stdio: "ignore" });
  • 写入本地文件
    src/bun/tunnel.ts:209
    await rename(found, finalBin).catch(async () => {
  • 删除本地文件递归
    src/bun/tunnel.ts:214
    await rm(extractDir, { recursive: true, force: true }).catch(() => {});
  • 删除本地文件
    src/bun/tunnel.ts:217
    await rm(tmpFile, { force: true }).catch(() => {});
  • 执行外部命令来自配置/变量
    src/bun/tunnel.ts:223
    execSync(process.platform === "win32" ? "where cloudflared" : "command -v cloudflared", {
  • 读取本地文件
    src/bun/tunnel.ts:247
    await access(bin);
  • 执行外部命令来自配置/变量
    src/bun/tunnel.ts:282
    const child = spawn(
  • 读取本地文件
    src/bun/updater.ts:47
    if (existsSync(candidate)) return candidate;
  • 发起网络请求
    src/bun/updater.ts:55
    const res = await fetch(REGISTRY_URL, {
  • 写入本地文件
    src/bun/updater.ts:117
    mkdirSync(dir, { recursive: true });
  • 写入本地文件
    src/bun/updater.ts:118
    writeFileSync(
  • 写入本地文件
    src/bun/updater.ts:131
    writeFileSync(join(dir, "pnpm-workspace.yaml"), BACKEND_WORKSPACE_YAML);
  • 读取本地文件
    src/bun/updater.ts:163
    if (existsSync(join(dir, "node_modules")) && existsSync(trimScript)) {
  • 读取本地文件
    src/bun/updater.ts:177
    if (!existsSync(manifestPath)) {
  • 读取本地文件
    src/bun/updater.ts:181
    const installed = (JSON.parse(readFileSync(manifestPath, "utf8")) as { version?: unknown }).version;
  • 写入本地文件
    src/bun/updater.ts:186
    writeFileSync(join(dir, "VERSION"), installed + "\n");
扫描于 2026/11/5(0 天前) · 范围 全包扫描 · 来源 GitHub 仓库

静态扫描只反映源码中出现的调用,不构成安全背书;人工评估与自动扫描相互独立、互不覆盖。

社区实装还没有人打卡 · 装过的第一个就是你
给这个插件打分还没有人投票↓
用户评分
还没有人投票,来当第一个

功能亮点

  • 双击启动拉起引擎
  • 原生窗口打开GUI
  • 内置自动更新引擎

DeepSeek Harness 桌面端 —— 自包含的 ElectroBun 外壳,内置可自动更新的 dsh 引擎,附带 Windows 图形化安装程序

README

由 DeepSeek 最新模型翻译生成
DSH Desktop DeepSeek Harness 桌面端 —— 基于 ElectroBun 的原生桌面壳。 双击即可使用,不用再开终端跑 dsh web:应用自动在后台启动 DeepSeek Harness 引擎、等端口就绪后在原生窗口里打开完整 GUI,退出时干净地停掉引擎。 本应用只是引擎的外壳,与 deepseek-harness 仓库完全解耦:*引擎来自 npm 上最新的 @deepseek-ai/dsh,仍跑在 Node 上。 功能特性 - 开箱即用:双击启动,自动在后台拉起引擎并打开 GUI,无需手动开终端。 - 自动跟进最新引擎:每次启动检查 npm 上的最新 @deepseek-ai/dsh,发现新版本就自动下载安装到用户数据目录(内置 pnpm + Node),下次启动直接用最新版——不需要重新打包;离线时优雅回退到应用内置的离线引擎。 - 自包含后端:pnpm backend:provision 把一份 @deepseek-ai/dsh 和 Node 运行时打进应用作为离线兜底,新机器无网络也能用。 - 动态端口:以 dsh web --port 0 启动(OS 分配端口),从输出行解析真实地址——不会再撞上固定 3080 端口(比如另一个正在运行的 Harness)。
展开完整文档(README 剩余 1 节)
DSH Desktop

DeepSeek Harness 桌面端 —— 基于 ElectroBun 的原生桌面壳。

双击即可使用,不用再开终端跑 dsh web:应用自动在后台启动 DeepSeek Harness 引擎、等端口就绪后在原生窗口里打开完整 GUI,退出时干净地停掉引擎。

本应用只是引擎的外壳,与 deepseek-harness 仓库完全解耦:*引擎来自 npm 上最新的 @deepseek-ai/dsh,仍跑在 Node 上。

功能特性

- 开箱即用:双击启动,自动在后台拉起引擎并打开 GUI,无需手动开终端。
- 自动跟进最新引擎:每次启动检查 npm 上的最新 @deepseek-ai/dsh,发现新版本就自动下载安装到用户数据目录(内置 pnpm + Node),下次启动直接用最新版——不需要重新打包;离线时优雅回退到应用内置的离线引擎。
- 自包含后端:pnpm backend:provision 把一份 @deepseek-ai/dsh 和 Node 运行时打进应用作为离线兜底,新机器无网络也能用。
- 动态端口:以 dsh web --port 0 启动(OS 分配端口),从输出行解析真实地址——不会再撞上固定 3080 端口(比如另一个正在运行的 Harness)。
- 品牌化启动页:窗口先显示加载页(含更新进度),引擎就绪后自动切换到真实 GUI。
- 系统托盘:打开窗口 / 在浏览器中打开 / 重新启动引擎 / 检查并更新引擎 / 退出;关闭窗口后应用驻留托盘,引擎继续运行。
- 单实例:Windows 用命名互斥量(进程退出自动释放),其余平台用 PID 锁文件。
- 干净退出:退出时用 taskkill /T 终止引擎进程树。

安装使用(用户)

下载安装

从 Releases 下载:

| 包 | 说明 |
| deepseek-harness-app-installer.exe | 推荐:图形化安装向导(简体中文 UI)。默认装到 %LOCALAPPDATA%\Programs\DeepSeek Harness,创建桌面/开始菜单快捷方式,注册卸载项 |
| DeepSeek Harness-Setup.exe | 单文件自解压包(无向导) |
| .zip | 原始分发包(需解压) |

首次启动

- 首次启动会自动检查并从 npm 安装最新引擎(在线约 200MB 下载;离线直接用内置引擎)。
- 需要 Windows 10/11(系统自带 WebView2 运行时;很老的系统可能缺,需装 WebView2)。

配置 API Key

- 在应用界面按引导配置(设置 → 模型/提供商),或设置环境变量 DEEPSEEK_API_KEY。
- 程序完全自包含,不需要装 Node / npm / pnpm。

日常使用

- 系统托盘:打开窗口 / 在浏览器中打开 / 重新启动引擎 / 检查并更新引擎 / 退出;关闭窗口后应用驻留托盘,引擎继续运行。
- 引擎自动跟进:每次启动检查 npm 最新版并自动安装到用户数据目录,无需手动重打包。
- 卸载:设置 → 应用 → DeepSeek Harness → 卸载(或运行安装目录下的 Uninstall.exe)。

数据与会话

- 你的对话数据存在磁盘上:~/.dsh/sessions/(按项目分目录)。
- 托盘里的任何操作(打开窗口 / 打开浏览器 / 重新启动引擎 / 检查更新)都不会删除会话;重启或更新后,会话会自动从磁盘重新加载。
- ⚠️ 唯一注意:正在生成中的回复,如果此时重启或更新引擎,这条回复会被中断(未生成完的部分会丢失,之前已完成的都在)。
- 卸载程序不会删除 ~/.dsh——你的会话和配置都会保留;如需彻底清除请手动删除该目录。
- 想备份/迁移:直接整体拷贝 ~/.dsh 即可。

注意点(常见问题)

- 安全软件误报:装有联想杀毒(Lenovo/Huorong)、阿里(AlibabaProtect)等安全软件的机器上,曾出现安装后文件被自动清理的情况——安装脚本已改用英文 section 名规避。若你的文件仍被清理,请把安装包/安装目录加入白名单。
- 引擎只跟随 latest:只自动安装 npm latest 标签的版本;预发布(next,例如 rc.8)不会自动安装,等转正后下次启动自动跟进。
- SmartScreen 提示:安装包未签名,首次运行需点“更多信息 → 仍要运行”。
- 首次启动较慢:需要在线下载最新引擎(约 200MB,视网络而定)。

已知限制

- 关闭主窗口后应用驻留托盘;如系统托盘创建失败,关闭窗口会直接退出。
- macOS 用 WKWebView(Safari 内核),尚未在此环境验证 dsh 前端行为。
- 应用外壳自身更新(ElectroBun Updater / bsdiff 增量)尚未接入——引擎版本已自动跟进。

开发(开发者)

环境需求

- Bun(构建/开发工具链)
- Windows 10/11(Edge WebView2 运行时,系统已预装);macOS/Linux 架构兼容但未验证
- 使用模型需要 DEEPSEEK_API_KEY(沿用你的 ~/.dsh 与 .env)

快速开始

bun install
bun start # 运行已构建的应用(或 bun dev:构建并运行)
bun run dev:watch # 改动自动重建

开发态默认从相邻的 ../deepseek-harness 源码 checkout 启动后端(等价于
node --import tsx/esm apps/cli/src/bin.ts web --port 0),方便迭代。

架构

DSH Desktop (ElectroBun)
├─ 主进程 (Bun): src/bun/index.ts │ ├─ 单实例检查 │ ├─ 解析后端来源(内置 → 本地源码 → npx 兜底) │ ├─ spawn dsh web --port 0(stdout 解析 URL 行) │ ├─ 加载页窗口 → 就绪后 loadURL(真实 GUI) │ └─ 托盘 / 关闭到托盘 / 退出时 kill 进程树 └─ 后端(未改动): @deepseek-ai/dsh web,跑在 Node + 自带原生插件上

配置(环境变量)

| 变量 | 默认 | 说明 |
| DSH_DESKTOP_BACKEND_DIR | 内置 resources/backend | 显式指定后端目录 |
| DSH_DESKTOP_NODE | 内置 resources/node,否则 PATH | 显式指定 Node 可执行文件 |
| DSH_DESKTOP_DEV_BACKEND | ../deepseek-harness | 开发用的源码 checkout 路径 |
| DSH_DESKTOP_USER_DATA | %LOCALAPPDATA%\dsh-desktop 等 | 日志与单实例锁目录 |

内置后端(离线兜底)

pnpm backend:provision # 安装 npm 最新 @deepseek-ai/dsh 到 resources/backend,并拷贝 Node 运行时 + pnpm
pnpm backend:pin 0.1.0-rc.6 # 固定一个具体版本
pnpm backend:check # 对比内置版本与 npm 最新版(有新版本时退出码 2)
pnpm gen:icons # 重新生成托盘/应用图标

resources/backend/VERSION 记录内置版本。日常使用不需要手动重打包:应用启动时会自动检查
npm 上的最新版并安装到 %LOCALAPPDATA%\dsh-desktop\backend;重新执行 backend:provision
只是为了刷新这份离线兜底(比如给离线机器分发时)。

打包

pnpm build:stable # 产出 artifacts/ 下的构建产物 + Setup.zip
pnpm build:installer # 产出图形化 NSIS 安装程序:artifacts/DeepSeek Harness-Installer.exe
pnpm build:portable # 产出单文件自解压包:artifacts/DeepSeek Harness-Setup.exe

build:installer 需要 NSIS(makensis;可用 DSHP_NSIS_MAKENSIS 指定路径,或加入 PATH)。macOS 构建必须在 macOS 上进行(ElectroBun 面向当前机器系统构建)。

发布(打 tag + release + 传安装包)

pnpm publish:release # tag v + release + 上传安装包
pnpm publish:release -- --version 0.1.1 # 指定版本
pnpm publish:release -- --update # 更新已有 release 的标题/描述
pnpm publish:release -- --draft # 先建草稿,网页手动发布
pnpm publish:release -- --notes NOTES.md # 自定义 release 描述(markdown)
pnpm publish:release -- --dry-run # 只打印计划,不改任何东西

- 自动解析 git remote origin 得到仓库,从 Git 凭据管理器取 token(或 GH_TOKEN)。
- 描述默认是中英双语模板(中文在前、英文在后);所有文本以 UTF-8 直接走 REST API,不经过 shell,不会再出现中文变 ? 的问题。
- 上传文件名固定为 deepseek-harness-app-installer.exe(同名旧资产会被覆盖)。
- 完整说明:node scripts/publish-release.mjs --help。
预览分享卡片长什么样 ↓R2h1/deepseek-harness-app
分享 · DeepSeek Harness Hub
R2h1/deepseek-harness-app

双击启动自动拉起引擎,在原生窗口打开完整 GUI

这个插件是你维护的吗?
作者本人可认领并核对本条目;认领通过后,详情页会显示「作者已认领」标记。
认领条目 →
回到顶部