DSH Desktop 上手指南:安装、数据目录、MCP 配置与使用技巧
DSH Desktop 是把 DeepSeek Harness 打包成「下载即用」的本地桌面应用:装完就有图形界面、终端、文件浏览和插件体系,不用自己从命令行拼环境。本文整理它的官方入口、安装方式、数据与配置目录,以及实际使用中总结的一批技巧和避坑点。
说明:DSH Desktop 是独立的社区桌面封装项目,与 DeepSeek 官方没有隶属关系;DeepSeek Harness 及其依赖遵循各自上游的许可与商标政策。
一、相关地址
| 用途 | 地址 |
|---|---|
| DSH Desktop 源码仓库 | github.com/dataelement/dsh-desktop |
| GitHub 下载(Releases) | github.com/dataelement/dsh-desktop/releases |
| 官网下载 | www.dshdesktop.com/zh/#download |
| DeepSeek Harness 上游项目 | github.com/deepseek-ai/deepseek-harness |
| Preset 广场(工作配方) | dshdesktop.com/preset/ |
二、下载与安装
最省事的方式是走官网下载页,它会按当前系统推荐对应安装包:
| 平台 | 安装包 | 直接下载 |
|---|---|---|
| Windows x64 | Setup(.exe) | dsh-desktop-windows-x64-setup.exe |
| macOS(Apple 芯片) | DMG | dsh-desktop-mac-arm64.dmg |
| macOS(Intel) | DMG | dsh-desktop-mac-x64.dmg |
如果官网打不开或者想固定版本,就去 GitHub 的 Releases 页面挑对应版本下载。安装过程是常规的下一步式安装,装完直接启动就能用。
三、数据目录:所有配置都在 .dsh 里
这是最值得先记住的一件事:DSH 的全部数据、配置、会话和日志都在用户主目录下的 .dsh 目录,不散落在别处。
C:\Users\<用户名>\.dsh\其中 <用户名> 是本机登录用户名。需要注意:在 Windows 的 8.3 短名形式下,同一个目录也可能显示成下面这样,两者是同一个位置:
C:\Users\Admini~1\.dsh\目录内主要包含:
| 目录 / 文件 | 作用 |
|---|---|
profiles\desktop\ | 桌面 profile 的配置目录:解析后的完整配置 cordis.yml、用户补丁层 cordis.patch.yml、已安装插件 |
profiles\desktop\node_modules\ | 插件包本体,第三方插件装在这里 |
profiles\desktop\.plugin-manager\logs\ | 插件安装过程的 pnpm 日志,装插件失败时看这里 |
profiles\desktop\.dsh-market\ | 插件市场的状态与操作日志(log.ndjson) |
sessions\ | 会话记录,按 JSONL 存储 |
storages\ | 结构化存储(JSON 后端),保存设置类数据 |
logs\desktop-next.log | 桌面端日志,排障第一入口 |
recovery\ | 启动异常时的恢复数据 |
electron-user-data\ | Electron 层数据(缓存、窗口状态等) |
.credentials.yaml | 账号凭据,注意保密 |
desktop-preferences.json | 桌面端偏好设置 |
因为所有东西都集中在这一个目录,备份和迁移就是把整个 .dsh 目录拷走(迁移到新机器时注意凭据文件别随手丢到公共位置)。
四、MCP Server 配置文件
给 DSH 挂 MCP Server,改的是这个文件:
C:\Users\<用户名>\.dsh\profiles\desktop\cordis.patch.yml同目录下的 cordis.yml 是各层合成后的完整配置,属于生成物,直接改容易被覆盖;cordis.patch.yml 才是用户补丁层,它在所有 bundle 层之后生效,所以配置项都写在这里。
结构与官方 MCP 客户端插件一致,用 insert 往配置里追加一行,每台服务器一条记录。transport 支持 stdio(本地进程)和 streamable-http(远端服务):
# 用户补丁层:在 bundle 层之后生效
- insert:
# 本地启动的 MCP Server
- id: mcp-mysql
name: '@deepseek-ai/dsh-mcp-client'
config:
serverName: mysql
transport: stdio
command: npx
args:
- -y
- '@some-org/mysql-mcp-server'
env:
MYSQL_URL: 'mysql://user:pass@127.0.0.1:3306/db'
# 远端已有的 Streamable HTTP MCP Server
- id: mcp-blog
name: '@deepseek-ai/dsh-mcp-client'
config:
serverName: blog
transport: streamable-http
url: https://blog.example.com/mcp
headers:
Authorization: 'Bearer <你的访问令牌>'几个关键点:
- 工具命名固定为
mcp__<serverName>__<工具名>。例如serverName: blog加一个create_post工具,模型看到的就是mcp__blog__create_post。名称只由这两段决定,重启和重载后保持不变,所以会话历史和权限规则不会失效。 serverName在同一 profile 内必须唯一,两行用同名会在加载时报明确错误。字符范围是[A-Za-z0-9_-],长度 1 到 32。- 改完即生效,通常不用重启。补丁层会被重新加载,新增的 MCP Server 会连接并注册工具;连接失败时 DSH 仍能正常启动,只是该服务器的工具不出现,并在日志里记录一条错误。
- 常用可选字段:
toolCallTimeoutMs(单次调用超时,默认 60000)、cwd(stdio 的工作目录)、reconnect.maxAttempts(重连次数,默认 10)。
五、使用技巧
1. 权限模式:先按需放开,别一直全开
DSH 内置三档权限预设,配置在 cordis.patch.yml 的 permission 项里:
| 预设 | 文件系统 | 审批 | 适用场景 |
|---|---|---|---|
read-only | 只读 | 每次都问 | 只想让模型读代码、给方案 |
workspace-write | 限工作区可写 | 每次都问 | 日常改代码,推荐默认 |
danger-full-access | 不限制 | 不询问 | 需要装依赖、跑全量脚本时临时用 |
改默认档位只改一行:
- id: permission
name: '@deepseek-ai/dsh-permission-presets'
config:
defaultPreset: workspace-write注意 danger-full-access 同时会把审批策略设成 never,也就是不再向你确认任何操作,建议只在可信任务里临时切。
2. 用 Agent Preset 切换工具集
DSH 自带几套 Agent 预设,决定这个会话暴露哪些工具:standard(通用编码,默认)、ptc(把工具当 SDK 用代码调用,适合批量操作)、minimal(极简,只有一个持久终端)、cordis(带配置自省工具,适合改 DSH 自身配置)。
会话里按需切换比堆一屏用不上的工具更省 token。官网的 Preset 广场上还有社区分享的「工作配方」可以直接参考。
3. 模型与默认模型分开配
可用模型列表在 llm-deepseek 里定义,默认用哪个在 agent-default-model 里指定,两者都写在补丁层:
- id: agent-default-model
name: '@deepseek-ai/dsh-agent-default-model'
config:
provider: deepseek-official
model: deepseek-v4-pro
reasoningEffort: highreasoningEffort 直接换推理强度:复杂任务调高,日常问答调低更省。
4. 出问题先看日志,不要先猜
| 现象 | 先看哪里 |
|---|---|
| 启动异常、MCP 连不上、代理异常 | ~\.dsh\logs\desktop-next.log |
| 插件装不上 / 装完没生效 | ~\.dsh\profiles\desktop\.plugin-manager\logs\<操作ID>\pnpm.log |
| 插件市场下载失败 | ~\.dsh\profiles\desktop\.dsh-market\log.ndjson |
顺手一个技巧:日志里会打印本次 GUI 的实际地址,形如 dsh web: http://127.0.0.1:65006/?token=****。端口是随机的,找不到页面时从这里取。
5. 代理:它读的是系统代理
DSH Desktop 启动时会探测系统代理,日志里能看到一行结论,例如 outbound proxy = http://127.0.0.1:7890/ (source: system, ...),或者 outbound proxy = none。如果插件市场或 MCP Server 拉不动,先确认这行的结论对不对,再去查代理本身。
6. 第三方插件的坑:一个坏 schema 能拖垮整个会话
这是实际踩到过的例子:装了某个第三方 MCP 客户端插件后,每一轮请求都报同一个错——
Invalid schema for function 'mcp_tool_search':
schema must be a JSON Schema of 'type: "object"', got 'type: null'.原因是该插件给自己新增的搜索工具写参数 schema 时,用的是沙箱 DSL 的「属性映射」写法({ query: {...} }),但注册到宿主侧的工具接口要求的是完整 JSON Schema({ type: 'object', properties: {...} })。缺了根节点的 type,序列化出去就变成 type: null,官方接口直接拒收,于是整轮对话全挂,不是这个工具本身调用失败,而是每次请求都失败。
经验总结:
- 如果突然出现「每一轮都报同一个 schema 错误」,优先怀疑最近装的插件,而不是网络或账号。
- 处理顺序:禁用最近装的插件 → 看
desktop-next.log里插件相关告警 → 确认后再决定修补还是弃用。 - 手动修补
node_modules里的插件源码能救急,但插件升级会覆盖,要么给上游提 issue,要么在升级后重新打补丁。
7. 环境变量:会话内能拿到这些信息
DSH 会把当前环境注入到子进程,脚本里可以直接读:
| 变量 | 含义 |
|---|---|
DSH_HOME | 数据根目录(即 .dsh) |
DSH_PROFILE | 当前 profile 名,桌面端是 desktop |
DSH_PROFILE_DIR | 当前 profile 的完整路径 |
DSH_SESSION_ID | 当前会话 ID |
DSH_WEB_URL | 本次 GUI 的访问地址 |
写脚本时用 DSH_HOME 拼路径,比硬编码用户名可靠得多。
8. 会话是可检索的文件
会话以 JSONL 存在 sessions\ 下,一行一个事件。这意味着历史对话可以直接被脚本处理:模糊查找某次任务的结论、统计 token 消耗、把某段历史喂给别的工具,都不需要再手工复制粘贴。
9. 迁移机器时的最小清单
- 拷走整个
.dsh目录(配置、插件、会话、凭据一起过去)。 - 确认新机器上插件能重新安装:部分插件是 GitHub 直装,需要能访问对应源。
- 检查
cordis.patch.yml里的绝对路径(例如外部程序的安装路径、令牌),换了机器或用户名后要跟着改。
六、小结
DSH Desktop 的形态很清晰:上游是 DeepSeek Harness 这套「一切皆插件」的内核,桌面版负责把它变成开箱可用的应用;所有状态都收敛在 C:\Users\<用户名>\.dsh\ 一个目录里,配置改 profiles\desktop\cordis.patch.yml,MCP Server 用 insert 追加一行即可生效。
上手阶段建议按这个顺序走:先确认数据目录和日志位置,再把权限档位收到 workspace-write,然后按需接 MCP Server;遇到「每轮都报同一个错」这种诡异现象,直接去看日志里最近生效的插件。
评论区