@zhengjunyao/dsh-updater

devtested: passnpmMIT

Track DeepSeek Harness's own releases and update in one click: reads the npm dist-tags and the GitHub changelog, shows every change between the running build and the target, grades the risk, then hands the install to a detached helper that backs the current install up with an atomic rename, runs npm

下载量 / Downloads
925
依赖体积 / node_modules
14.56 MB
测试时间 / Tested
2026-11-07
DSH 版本 / Version
0.2.2-rc.1

Install

dsh plugin --profile web add @zhengjunyao/dsh-updater

Sandbox test results

StageResult
1 install✓
2 list✓
3 mount✓
4 boot—

Four stages run in an isolated sandbox: install (network on) → list → mount → boot (last three with no network).

README

@zhengjunyao/dsh-updater

[English](README.md) | 中文

跟踪 DeepSeek Harness 自身的版本并一键更新:跟 npm dist-tags(latest / next / alpha)与

GitHub Release(tag dsh-v*,双语正文),在 Web GUI 里显示当前版本到目标版本之间每一个版本的更新点

和一份分级风险清单,然后把安装交给一个分离助手——用 mv 把当前安装瞬时移开做备份 →

npm install --prefix <当前安装前缀> → 校验落地版本 → 用完全相同的命令重启 →

启动失败自动回滚。

一句话定位

DSH 的更新频率高(0.1.x-rc.x 通道多),而 dsh 自身不带任何自更新机制。

  • npm i -g @deepseek-ai/dsh 之后还得自己重启一次,而且重启命令必须和当初启动时一模一样

(端口、profile、cwd、node 路径都可能被改过)。

  • 本机可能有多份 DSH 安装:process.argv[1] 反查出的运行安装、PATH 里最先命中的那份、

以及 npm config get prefix 指向的那份,三者完全可以是三个不同目录——一次天真的

npm i -g 会更新到最后那个,然后什么变化都不会发生。

  • npm 发布频繁但只有 GitHub Release 写变更说明,且 npm 上有的版本不一定有对应 release;

反过来,只在 GitHub 发布的版本根本装不上。

本插件把「看版本 → 读更新点 → 评风险 → 装 → 校验 → 重启 → 失败回滚」串成一条链,并让

正在运行的安装目录成为唯一的更新目标。

四个能力

1. 跟踪最新版本

  • 三个通道:npm dist-tag latest / next / alpha,由配置项 channel 决定跟随哪一个。
  • 后台定时检查:checkIntervalMinutes(默认 180 分钟,0 关闭)+ checkOnBoot(启动后 8 秒跑一次)。

后台检查的目的不是打扰,而是让缓存里的 registry / releases 快照保持温热,

打开面板或问 Agent 时不用等两次网络往返。

  • 缓存:cacheTtlMinutes(默认 30 分钟)内的结果直接复用,落地在 cache/registry.json

与 cache/releases.json;force 参数可绕过缓存。

  • 上游故障不致命:registry 或 GitHub 拉取失败时,沿用上一次成功的结果并在

upstream.warnings 里标注「可能是旧的」——「连不上 GitHub」不会被显示成「没有新版本」。

  • dist-tag 缺失或滞后时按通道阶梯回退:next / alpha 没打 tag 时,回退到

latest 之上最新的预发布版本,避免「明明有更新的预发布却报无更新」。

  • 面板同时显示 newerElsewhere:当前通道之外是否存在更新的版本。

2. 显示更新点

  • 版本之间的事实来自 npm(能不能装),变更说明来自 GitHub Release(改了什么)。
  • 更新点覆盖 (当前版本, 目标版本] 区间内每一个已发布版本,不只是一个 diff;

用户跑 latest 常常一次跨过好几个发布。

  • 每个版本按 GitHub Release 正文里的 <h3> / # 标题分组渲染条目;

正文是双语的(中文段 + --- + 英文段),解析优先取中文段,缺失时回退英文段。

  • 拿不到对应 release 的版本明确标出「没有找到该版本的发布说明」(notesMissing),

不假装没有变化。

  • 只在 GitHub 发布、npm 上不存在的版本会被排除出可选目标(installMissing)并说明原因。
  • GitHub 未认证限流是 60 次/小时;配置 githubToken 可提高上限,面板会显示剩余额度与重置时间。

3. 一键更新

入口是设置页「DSH 更新」卡片里的按钮或侧边栏入口,也可以由 dsh_update 工具触发。

真正的安装由分离助手 helper/update-helper.mjs 完成,因为一个进程无法安全替换自己正在运行的代码:

1. 宿主写 pending-spec.json,spawn 分离助手,回 202 之后才退出自己;

2. 助手等旧宿主释放端口(超时后 SIGKILL 旧进程兜底);

3. mv(rename)把当前安装原子移开做备份——不是复制三万个文件;同目录 rename 是瞬时且原子的,

因此回滚不依赖剩余空间;

4. npm install -g --prefix <当前安装前缀> --registry <registry> --no-audit --no-fund @deepseek-ai/dsh@<版本>

(--prefix 永远显式传入,不用 npm config get prefix);npm 输出实时流入日志;

5. 校验落地结果:读 package.json 版本必须等于目标版本、入口脚本 <root>/lib/bin.js 必须存在、

node_modules/@deepseek-ai 下必须有包(npm 退出码为 0 也可能留下半装目录);

6. 用完全相同的调用重启(process.execArgv + argv[1:] + 原 cwd + 原可执行文件),

所以 dsh web --port 3080、自定义 profile、自定义路径都原样保留;

7. 启动失败则把备份 rename 回原位并拉起旧版本;

8. 期间恢复控制台始终可用(默认 http://127.0.0.1:3098,被占用时依次试 +1…+9)。

4. 更新风险提示

版本号本身不足以回答「该不该按这个按钮」。风险引擎把目标版本、本机安装拓扑、

已装插件契约与本次操作的可行性汇总成一份有序清单,分三级:

  • high:不要盲目执行,默认拦截一键更新直到显式确认;
  • warn:先读一遍;
  • info:背景信息。

检查项(每一条都来自代码,不是猜测):

风险项 · 检查内容 · 级别

prerelease · 目标版本带预发布标识(rc / alpha / beta)。跟随 latest 通道却拿到预发布时升为 high · warn / high

breaking · 扫描更新点文本里的破坏性措辞(BREAKING、不兼容、破坏性、重大变更、不再支持、已移除、移除了、废弃、已弃用、必须升级、需要手动、要迁移、升级指南、deprecat、backwards-incompatib 等) · high(命中时);否则一条 info 说明「未发现」

migration · 更新点里提到迁移 / 改名(migrat、迁移、改为、改名、重命名、rename) · warn

version-jump / version-gap · 跨版本幅度:跨 ≥2 个次版本或跨主版本记 warn(跨 ≥4 个次版本或跨主版本时);小跨度只记 info · warn / info

notes-missing · 区间内有版本在 npm 上存在却没有对应 GitHub release,变化内容未知 · warn

not-on-npm · 区间内有版本只在 GitHub 发布、npm 上没有,无法安装,已从可选目标排除 · info

install-unknown · 反查 process.argv[1] 得不到安装根,更新不知道要替换哪个目录 · high

multi-install · 本机存在多份 DSH 安装:说明本次只更新正在运行的那一份,并列出其它份;若 PATH 首选与运行中的不是同一个目录,明确指出「更新完重启后手动敲 dsh 可能又跑回旧的那一份」 · high

path-mismatch · 只有一份安装,但 PATH 首选仍与运行中的不一致 · warn

prefix-drift · npm config get prefix 与运行安装的前缀不一致(直接 npm i -g 会装到前者) · info

preflight:* · 预检结果逐条并入清单(见下) · 按检查项

plugin-incompatible · 已装插件在各自 package.json 的 dsh.engines.dsh 里声明的范围是否覆盖目标版本;不覆盖时提示「bundle 加载失败会让插件树整体起不来」 · high(有插件不兼容时);否则一条 info 汇总(含未声明范围的插件数)

backup · 更新前是否备份;关闭备份时明确写出「npm 会留下半装目录且无法自动恢复」 · info / warn

session-interrupt · 更新必然中断当前会话,并说明自动回滚是否开启 · info

预检项(preflight,全部来自 src/installs.ts,无论通过与否都会逐条返回):

预检项 · 通过条件 · 不通过时级别

target · 从 npm registry 解析到了目标版本号 · high

install-root · 从 process.argv[1] 反查到了 @deepseek-ai/dsh 包根 · high

install-writable · 当前用户对安装根(及其前缀)有写权限,不需要 sudo · high

install-complete · 安装根下 node_modules/@deepseek-ai 有包(否则疑似损坏,更新会顺带修复,但回滚点也是这个损坏状态) · warn

npm · PATH 里能找到 npm · high

prefix · 能从安装目录推导出 npm 前缀(<prefix>/lib/node_modules 布局) · warn

node · Node 主版本 ≥ 20(@deepseek-ai/dsh 自己不声明 engines,npm 不会替你拦低版本 Node,所以这里自设下限);解析不出主版本号时跳过 · high

tarball · 目标版本的 dist.tarball HEAD 返回成功(镜像/网络异常只记 warn,明确 404 才 high) · warn / high

disk · 剩余空间 ≥ 2 GB(一份新安装 + 一份等大的旧安装备份 + npm 的下载副本);读不到空间时跳过 · high

分级与拦截:

  • level 是所有风险项里最严重的一级;score 是 0–100 的加权分(high 45 分 / warn 12 分 / info 2 分,上限 100),供面板画表盘。
  • vetted 为 false 表示清单里仍有 high 项——「还没被审过」。
  • confirmOn 决定一键更新的拦截门槛:high(默认)只拦 high;warn 连 warn 也拦;

never 完全关闭拦截(仍然显示清单)。

  • 被拦时:HTTP 返回 428(面板)或工具返回 requiresRiskConfirmation: true(Agent),

并附上最严重的前几项原因;确认后带 confirmRisk: true 重试。

  • 检查在点击更新的那一刻重新跑一遍:用户确认过的那份报告,必须是即将执行的那次操作对应的报告。

安装

# 从 GitHub(仓库带 dsh-plugin topic)
dsh plugin --profile web add github:zhengjy01/dsh-updater

# 本地开发:link / file 两种写法
dsh plugin --profile web add link:/path/to/dsh-updater
dsh plugin --profile web add file:/path/to/dsh-updater

# 发布到 npm 之后
dsh plugin --profile web add @zhengjunyao/dsh-updater

装完需要重启一次 dsh web 才会加载宿主侧代码。

界面位置

  • 设置页「DSH 更新」卡片(settings.section,id updater,order 339):当前版本与运行安装目录、

本机安装份数、各通道目标版本、更新点、风险清单、一键更新按钮、更新历史、上次失败报告、插件设置。

  • 侧边栏入口:由 entry 控制——sidebar(默认,内联在侧边栏)/ ball(固定在角落的球)/

both(两者都有)/ off(不挂载入口)。

  • 更新期间显示全屏遮罩(showOverlay,默认开),新宿主应答

…(truncated)

Rendered from the README published on npm. Formatted only, not edited.

Versions

Published on npm::2,最后更新 2026-09-29

Links

GitHub · Homepage · npm

Same category