dsh-remote-server: Mention servers with @ and execute SSH commands in a DeepSeek Harness session.

前言

让模型操作远程服务器,常见的做法有两条:在目标机上部署 agent,或者把 shell 权限整体交给智能体。前者多一个常驻进程要维护,后者意味着一条高危命令可能在无人确认的情况下跑在生产机上。

dsh-remote-server 给出另一种组合:不往服务器上安装任何东西,命令通过你现有的 ssh 客户端执行,但每条命令都要经过一道固定顺序的审批流水线——无法明确放行的一律落到人工,人工不可达则以拒绝收尾。

这是什么

dsh-remote-server 是 DeepSeek Harness(下称 DSH)的一款插件,作者是 MRZHUH,采用 MIT 许可,当前版本 0.1.1。DSH 的理念是「一切皆插件」,这款插件在会话中加入了 @ 提及能力:输入 @ 列出已注册的服务器,选定后引用随消息传递,模型在每条命令上都会显式写出目标服务器。

官方的一句话定位:在 DSH 会话中用 @ 提及服务器,通过 SSH 在其上执行命令,所有命令置于一个 fail closed 的两级审批门槛之后。

核心功能

不在服务器上装任何东西

这是插件的核心设计,值得单独一节:

  • 目标机上无 agent、无 daemon、无入站端口。插件驱动你自己的 ssh 客户端,现有 ~/.ssh/config 继续生效——跳板机、agent forwarding、known_hosts 都不用改。
  • 身份验证仅支持密钥。identityFile 只是交给 SSH 客户端打开的路径,插件从不读取、复制或存储密钥材料;password 字段会被拒绝而不是存储。
  • 运行 dsh 的机器上需要有 OpenSSH 客户端。如果缺少 ssh,插件会在加载时失败并给出对应平台的安装命令,而不是挂载成一个什么都跑不了的状态。

注册服务器

两条路径:

1、在 Settings -> Servers -> Add a server 中添加;
2、或写入 remote-servers 设置命名空间(YAML)。

remote-servers:
  servers:
    - alias: web-01
      host: 10.0.0.11
      user: ops
      tags: [prod, web]
      description: edge tier - start here
    - alias: db-01
      host: db-01.internal.example
      port: 2222
      identityFile: ~/.ssh/id_ed25519_db

alias 是你在 @ 之后输入的名字,不能包含空白字符;配置项包括 aliashostusertagsdescription,以及可选的 portidentityFile

也可以直接导入现有配置:导入功能读取 ~/.ssh/config(或你指定的路径),列出主机供你选择注册;重新扫描时会提示哪些主机已经注册过,而不是列出一排禁用的重复项。

如果服务器拒绝了你的密钥,服务器页面会给出一条填好你的用户名、主机和端口的 ssh-copy-id 命令。

两个工具与服务器信息页

插件向模型暴露两个工具:

工具 作用
remote_exec 在单个已注册服务器上运行一条命令,返回 stdout、stderr 和退出码
remote_server_info 读取已采集的服务器信息,或重新探测机器

每个服务器有一页信息:可达性、你写的描述,以及主机自身的数据——hostname、OS、CPU、memory、disk、uptime,全部在单次 SSH 往返中采集。没有检查过的服务器会如实显示未检查,而不是给出占位数字。页面标题同时显示已安装的插件包版本。

审批流水线

每条命令都要经过一个固定顺序的流水线,顺序本身就是设计的一部分:

  1. 未注册别名:直接拒绝,不发起连接。
  2. Full access:harness 的 danger-full-accessnever 权限组合下,已注册服务器的命令不再二次提示。
  3. 高危规则集:确定性匹配命中即强制人工决策,模型分类器不能推翻。
  4. alwaysAsk:设置后,从这里往后的所有命令都交给人工。
  5. 只读 allowlist:命中已配置前缀的普通调用立即执行。
  6. 模型分类器:对剩下的命令回答 auto 或 human。
  7. 人工审批:通过 harness 审批通道询问。

九类高危类别强制人工决策:递归删除、磁盘与文件系统写入、关机重启、服务停止与重启、用户与权限变更、包安装与卸载、写入系统路径、提权、读取凭据或密钥路径。

fail closed 的含义是:任何无法给出明确放行的命令都落到人工;分类器超时、报错或回答含糊都不算通过——拒绝分支是代码里的默认路径,而不是错误处理分支。

开启模型自动审批

自动审批默认关闭,直到你在配置里指名模型——插件无法预知你的部署组合了哪个 provider。在 profile 的 cordis.patch.yml 中:

- id: remote-server
  config:
    classifier:
      provider: deepseek
      model: deepseek-chat

providermodel 要么都设、要么都不设,只设其一会在加载时失败。这一步不涉及 API key:插件通过 ctx.llm 调用,凭据由 harness 解析,插件本身接触不到密钥。

安装与启用

从 npm 安装:

dsh plugin --profile web add dsh-remote-server

然后照常启动 dsh web(等同于 dsh --profile web)。--profile 指定装入哪个组合:profile 是 $DSH_HOME/profiles/ 下的一套可启动插件集合,可以让日常环境和干净环境并存,web 是 quickstart 默认启动的那套。发布的 tarball 已构建,无需手动编辑或额外许可。

如果 PATH 上没有 dsh 命令,可以用 npx 运行,或全局安装:

npx @deepseek-ai/dsh web
# 或
npm install -g @deepseek-ai/dsh

注意保留完整的包名作用域:裸写 npx dsh 会拉到一个无关的包,报 could not determine executable to run

从源码安装:

dsh plugin --profile web add github:MRZHUH/dsh-remote-server

git 安装拉取的是源码而非构建产物,pnpm 需要运行这个包的 prepare 脚本来编译。首次 add 会失败,并打印需要加入 pnpm-workspace.yaml 的配置键(以 pnpm 实际输出为准,旧版 pnpm 中这个键叫 allowBuilds):

onlyBuiltDependencies:
  - dsh-remote-server

允许这一条意味着允许该包在安装时于你的机器上执行代码,建议同时用 github:MRZHUH/dsh-remote-server#<sha> 固定 commit,避免后续 push 静默改变所运行的内容。从 npm 安装不需要这个许可,因为发布的 tarball 已经构建好。

安装过程中出现的 missing peer 警告(@deepseek-ai/dsh-*@deepseek-ai/cordisreact)属预期行为:这些 peer 由 dsh 安装自身在运行时提供,不在 profile 的 node_modules 里,插件可以正常工作。

卸载只需一条命令,已注册的服务器会保留:

dsh plugin --profile web remove dsh-remote-server

配置项

已核实的两个配置项:connectTimeoutMs 默认 10000,约束建立连接的过程;execTimeoutMs 默认 120000。README 的配置表在此之后被截断,其余配置项以仓库原文为准。

典型用法

装好插件、注册一台服务器之后,流程是这样的:

1、会话中输入 @,从列表中选定服务器;
2、用自然语言说出需求,引用随消息传递,模型在每条命令上显式写出目标服务器;
3、只读的命令立即执行;任何改变状态的命令都会停下来先问你。

若希望分类器自动放行一部分命令,再按上文在 cordis.patch.yml 中配置 providermodel 即可,不配置则保持全部人工确认的默认行为。

适用场景与注意

适合的场景:

  • 已有一套 SSH 体系和 ~/.ssh/config,想让模型代跑远程命令、又不想在目标机上引入 agent 的开发者与运维;
  • 需要「读类命令立即执行、改状态命令必须经人确认」这一默认策略的环境。

几点注意:

1、插件以当前 dsh 进程的权限运行,安装前应检查源码与许可证(本项目为 MIT)。从源码安装尤其要清楚:允许 prepare 脚本等于允许该包在安装时执行代码,建议固定 commit。
2、运行 dsh 的机器上需要有 OpenSSH 客户端,缺失时插件会在加载时直接失败。
3、发布流程上,GitHub Release 标签匹配 v<package.json version> 时触发 .github/workflows/publish.yml,通过 npm trusted publishing 以 provenance 发布,不使用 NPM_TOKEN secret。

结尾

dsh-remote-server 的价值在于把「让模型碰服务器」的默认路径从执行改成了拒绝:不装 agent、不存密钥,读类命令走 allowlist 立即执行,九类高危强制人工,分类器拿不准就交给人。如果你的工作流里模型和 SSH 已经密不可分,可以按上面的步骤试一遍。

  • 目录页:https://www.skillhub.cn/plugins/MRZHUH/dsh-remote-server
  • GitHub:https://github.com/MRZHUH/dsh-remote-server

注:skillhub.cn 为独立的社区插件目录,与 DeepSeek / 幻方无官方从属关系。

羽毛球分组比赛记分
小程序二维码

欢迎使用《羽毛球分组比赛记分》微信小程序

Xiaoye