@eduwork/dsh-remote-access
v0.1.2
Published
End-to-end encrypted remote access to a DSH host through a self-hosted relay
Maintainers
Readme
远程访问
@eduwork/dsh-remote-access 让你在手机或其他电脑的浏览器里使用另一台电脑上的 DeepSeek Harness(DSH):查看和新建会话、继续或取消任务、审批、回答提问、查看和下载结果。连接经自托管的中继服务器转发,端到端加密,中继看不到内容。每台设备都要在电脑上核对配对码、确认后才能连接,也可以随时移除。
包里有两部分:
- DSH 插件:运行在被访问的电脑上,在设置页开关远程访问、添加和移除设备,并让 DSH 的界面适合手机屏幕。
- 中继服务:部署在有公网地址的服务器上,转发密文,并提供手机上打开的网页。
使用
部署中继
需要 Node.js 24.22.1 或更新版本,以及为中继域名提供 HTTPS 并转发 WebSocket 的反向代理。
RELAY_URL=https://remote.example.edu/ RELAY_ACCESS_KEYS=替换成随机Key \
npx --yes --package=@eduwork/[email protected] eduwork-remote-relayRELAY_URL 是用户访问中继的公开地址;RELAY_ACCESS_KEYS 是发给电脑主人的接入密钥,多个用逗号分隔。中继默认监听 127.0.0.1:8787,可用 HOST、PORT 修改;<RELAY_URL>healthz 返回 ok,可用于监控。
完整的 中继部署指南 包含 Key 生成、Windows PowerShell 命令、HTTPS/Nginx、路径前缀、systemd 常驻运行、机构登录和 iframe 集成,以及启动后的验证与排错步骤。
中继也可以部署在同域的单独路径,例如 RELAY_URL=https://example.edu/eduwork-remote/。反向代理须保留此前缀,电脑上填写同一个完整地址。同域路径不隔离浏览器权限,部署者须确认站点与被配对电脑处于可接受的共同信任范围(见安全);作用于整个站点的 Service Worker 还须放过这段路径。
学校或企业也可以让成员凭自己的登录使用中继,不必逐个发接入密钥:RELAY_OIDC_ISSUER 填机构 OpenID Connect 登录的 issuer(例如 https://sso.example.edu),RELAY_OIDC_CLIENT_IDS 填桌面应用在该登录中的 client ID,多个用逗号分隔。电脑以登录得到的 ID Token 注册,中继用 issuer 公布的公钥验证,只记录用户标识,不记录 Token。Token 到期前电脑会自动换新的;到期仍未换新时,中继断开这台电脑现有的远程连接。机构登录失效、需要重新登录时,电脑停止连接中继,设置页提示重新登录。两种方式可以同时启用。
中继限制每个账号最多同时注册 5 台电脑,每台电脑每分钟最多接受 60 个设备连接,同一地址一分钟内注册被拒 10 次后要等待。中继在反向代理后面时,用 RELAY_CLIENT_IP_HEADER 指定代理传递客户端地址的请求头(例如 x-real-ip),否则所有用户共用代理的地址。
中继的网页默认不允许被其他页面嵌入。机构网站需要用 iframe 嵌入它时,用 RELAY_FRAME_ANCESTORS 列出允许嵌入的页面来源,多个用空格分隔:与中继同源的页面写 self,其他页面写它的来源,例如 https://portal.example.edu。命令行和 env 文件都会去掉引号,所以 self 与 'self' 等效;写多个来源时整个值加双引号,例如 RELAY_FRAME_ANCESTORS="self https://portal.example.edu"。iframe 不要加 sandbox 属性,中继网页需要运行脚本、注册 Service Worker 和下载文件。嵌入的页面应与中继属于同一站点(主域名相同,例如 portal.example.edu 与 remote.example.edu):跨站嵌入时,Safari 等 WebKit 浏览器无法在其中加载电脑的界面。
在电脑上开启
在 DSH 中安装插件后重启:
dsh plugin --profile web add @eduwork/dsh-remote-access打开“设置 → 远程访问”,填写中继服务器和接入密钥,勾选“允许远程访问”。显示“已连接”后即可添加设备。远程访问默认关闭。“测试连接”分别说明中继能否访问、身份能否通过,未开启时也可以测试;连接失败时可点“重试”。
机构的发行版可以预置自己的中继和登录(插件设置 organization: { relay, oidcProfileId },oidcProfileId 是 dsh-oidc 中的机构配置)。这时设置页默认使用机构账号:显示登录状态,未登录时可直接登录,登录后勾选“允许远程访问”即可,退出登录后远程访问随之停止。中继由发行版决定,设置页不显示也不能修改。用户也可以改选“使用自己的中继服务器”,填写中继和接入密钥。
机构登录模式还要求宿主安装提供 identityToken(profileID) 接口的 @eduwork/[email protected] 或后续兼容版本;旧版 0.3.0 不包含该接口。使用接入密钥的独立部署不依赖 OIDC 插件。
添加和移除设备
- 在电脑上点“添加设备”,出现二维码和链接。链接 10 分钟内有效,只能用一次。
- 在手机上扫码或打开链接,填写设备名称,点“开始配对”。
- 确认手机和电脑上显示的 6 位配对码一致后,在电脑上点“允许”。
之后在这台设备上打开中继地址就会连接到电脑;断线后自动重连。iPhone 和 iPad 上请先把页面添加到主屏幕,从主屏幕打开后再粘贴配对链接:只在 Safari 里配对的设备,7 天不用会丢失配对。
在电脑的“已配对设备”里点“移除”,该设备立即断开,之后不能再连接。
远程设备能做什么
可以选择已有工作区,查看或新建会话,继续和取消任务,审批或回答提问,查看和下载结果;宿主已安装相应插件时,还可以使用 Studio 成果和日历。
手机上看到的就是 DSH 自己的界面,只按窄屏做了调整:会话列表(工作区目录、搜索、新会话等)从左上角打开并铺满屏幕,选中会话或面板后自动收起;设置同样铺满屏幕,各分区排成一行标签,在远程设备上只能查看;对话中的耗时、重试、审批和提问与电脑上一致。
远端不能直接调用打开本机窗口、程序或发出通知的接口,不能注册或删除工作区、修改设置、管理账号、插件、凭据、技能、记忆或远程访问本身,也不能直接使用终端与代码执行接口。通过 Agent 发起的任务仍可能执行命令,沿用该会话的权限与审批规则;禁止直接调用终端接口不等于禁止 Agent 使用工具。完整清单见 src/gate/gate.ts,未列出的接口一律拒绝。
安全
- 电脑和设备之间端到端加密,中继只转发密文。配对链接固定了电脑的公钥,中继无法冒充电脑。
- 设备密钥由浏览器生成且不可导出,电脑只保存设备公钥。每次连接都要用设备密钥签名。
- 接入密钥和机构登录只决定谁能使用这台中继,不能用来连接别人的电脑。接入密钥保存在 DSH 的凭据里(
EDUWORK_REMOTE_ACCESS_KEY),不写进插件设置;机构登录的 ID Token 只发给发行版预置的中继,设置页不能更改这个地址。 - 手机上打开的网页由中继提供,部署中继的人可以修改它。请只使用你信任的中继。
- 手机上显示的 DSH 界面由所连的电脑提供,与中继网页同源。浏览器按来源(协议、主机、端口)而非路径隔离数据,因此一台电脑提供的界面能使用此浏览器与其他电脑的配对去连接它们。请只与自己的电脑配对。
- 同理,中继与其他网站同源时,那些网站的脚本能使用这里的配对连接电脑;任何一台被配对的电脑提供的界面,也能以用户的身份访问那些网站及脚本可访问的浏览器数据。独立域名能缩小信任范围;若选择同域路径集成,需要接受这项共同信任边界,路径前缀和普通 iframe 均不提供隔离。
- 允许其他页面嵌入中继的网页后,那些页面能把它显示在自己的页面里并加以遮挡,诱导用户点击(例如批准命令)。只允许你信任的页面嵌入。
协议细节见协议文档。
贡献来源
本插件由 @JunieXD 在 #192 中实现,承接了 @Paraso42 在 #180 中的远程访问原型贡献:DSH 宿主接入点梳理、接口白名单与拒绝原因、设备信任与撤销模型,以及断线重连、避免重复执行和跨网络部署的验收场景。@Paraso42 是远程访问功能的合作贡献者;当前协议与实现以 #192 为准。
开发
在本包目录运行:
npm ci
npm run check
node scripts/check-web.tscheck-web.ts 在 Chromium 和 WebKit 中走完配对、加载、请求、断线重连和移除设备,需要本机已安装 Playwright 的浏览器,不在 CI 中运行。
