多平台 IM 网关:飞书(Lark)WebSocket 长连接(无需公网)、企业微信 AES 加密回调、Telegram 长轮询;每会话独立 agent、白名单访问、Web GUI 可视化设置卡片。
安装
# npm 包(预构建)
dsh plugin --profile web add dsh-im-hub
# GitHub 源码(首次需按提示配置 allowBuilds 构建授权后重试)
dsh plugin --profile web add github:ThreeBody6666/dsh-im-hub
装任何插件都等于在你的机器上跑第三方代码,权限和你本人一样大——能读你的文件、用你的凭据、访问网络,工具审批管不到它。GitHub 来源的插件还会在安装时执行构建脚本。请只安装可信来源,并尽量锁定 commit(github:owner/repo#sha)。
README
dsh-im-hub
DeepSeek Harness (dsh) 的多平台 IM 网关插件:把 dsh 智能体接入 飞书(Lark)、企业微信(WeCom) 和 Telegram,让你在平时用的聊天软件里直接和智能体对话。
每个会话一个智能体、多轮上下文、白名单访问控制、空闲自动回收。默认无需公网地址(飞书长连接 / Telegram 长轮询;企业微信走 HTTP 回调)。
特性
- 飞书 / Lark — 官方 WebSocket 长连接(
/callback/ws/endpoint+ protobuf 帧、客户端主动 ping 保活、3 秒事件应答、message_id 幂等去重),或 webhook 模式。默认模式不需要公网地址;国际版 Lark 通过adapters.lark配置(open.larksuite.com)。 - 企业微信 — 应用消息回调,完整实现
WXBizMsgCrypt(AES-256-CBC 解密 + SHA1 验签),并通过消息 API 主动回复。 - Telegram — Bot API 长轮询(
getUpdates),超长消息自动按 4096 字符分片。 - Mock 适配器 — 无需任何真实平台凭据,通过 stdin + 本地 HTTP 端点即可测试。
- 每个聊天一个 agent 会话:保留上下文、同一聊天串行处理(不交错)、空闲超时后自动释放。
- 所有适配器强制白名单(
allowedUserIds);留空 = 允许所有人(生产环境请务必配置)。 - 聊天内命令:
/help、/reset、/status、/model。
安装
# 从 npm 安装(推荐):
dsh plugin --profile im add dsh-im-hub
# 从本地源码安装(开发调试):
dsh plugin --profile im add link:D:/projects/dsh-im-hub
这会创建一个 headless profile im,bundle 为 @deepseek-ai/dsh-base + dsh-im-hub。启动:
dsh --profile im
配置
方式 A — Web GUI 可视化设置卡片(v0.2.0+)
当插件运行在 Web GUI(dsh web profile)中时,设置页会出现可视化配置卡片,位置:设置 → 插件 → 可配置插件 → IM 网关(dsh-im-hub)。卡片直接编辑同一份配置,保存即热生效(无需改 cordis.patch.yml、无需重启)。凭据字段仅存服务端,界面上显示"已配置 / 未设置"徽标,不可回显。
可视化填写指引
每个控件都说明用途,每个空输入框都提供可照填的示例。凭据仍为只写字段:下面的截图仅展示占位示例,不包含真实 Token 或 Secret。
Telegram:Bot Token 与访问白名单

飞书:App ID、App Secret 与 Open ID 白名单

企业微信:企业 ID、应用凭据与回调 Token

方式 B — YAML(cordis.patch.yml)
插件行默认禁用。在 profile 自己的 cordis.patch.yml($DSH_HOME/profiles/im/cordis.patch.yml)中启用:
- id: dsh-im-hub
disabled: false
config:
adapters:
telegram:
enabled: true
token: '123456:ABC-DEF...'
allowedUserIds: [123456789] # Telegram 数字用户 id;留空 = 所有人
完整配置项:
| 键 | 默认值 | 说明 |
|---|---|---|
adapters.telegram.enabled |
false |
启用 Telegram Bot API 适配器(长轮询)。 |
adapters.telegram.token |
'' |
来自 @BotFather 的 Bot token。 |
adapters.telegram.allowedUserIds |
[] |
允许对话的数字用户 id。 |
adapters.telegram.timeoutSeconds |
50 |
getUpdates 长轮询超时。 |
adapters.telegram.pollIntervalMs |
500 |
轮询超时/出错后的间隔。 |
adapters.feishu.enabled |
false |
启用飞书适配器。 |
adapters.feishu.appId / appSecret |
'' |
飞书自定义应用凭据。 |
adapters.feishu.mode |
'websocket' |
websocket(官方长连接,无需公网)或 webhook。 |
adapters.feishu.webhookPath |
'/feishu' |
webhook 模式的 HTTP 路径。 |
adapters.feishu.verificationToken |
'' |
webhook 事件校验 token。 |
adapters.feishu.allowedUserIds |
[] |
允许对话的 open_id。 |
adapters.lark.enabled |
false |
启用 Lark 国际版适配器(与飞书同一开放平台,open.larksuite.com)。 |
adapters.lark.appId / appSecret |
'' |
Lark 自定义应用凭据。 |
adapters.lark.mode |
'websocket' |
websocket(官方长连接,无需公网)或 webhook。 |
adapters.lark.webhookPath |
'/lark' |
webhook 模式的 HTTP 路径。 |
adapters.lark.verificationToken |
'' |
webhook 事件校验 token。 |
adapters.lark.allowedUserIds |
[] |
允许对话的 open_id。 |
adapters.wecom.enabled |
false |
启用企业微信应用消息回调适配器。 |
adapters.wecom.corpId / corpSecret / agentId |
'' |
企业微信应用凭据。 |
adapters.wecom.token / encodingAesKey |
'' |
后台「接收消息」配置的 Token / EncodingAESKey。 |
adapters.wecom.path |
'/wecom' |
HTTP 回调路径。 |
adapters.wecom.allowedUserIds |
[] |
允许对话的用户 id。 |
adapters.mock.enabled |
false |
仅测试用适配器(stdin + 本地 HTTP)。 |
adapters.mock.port |
0 |
mock 端点固定端口(0 = 随机)。 |
agent.cwd |
'' |
agent 会话工作目录(默认 dsh 进程 cwd)。 |
agent.provider / agent.model |
'' |
覆盖模型选择;留空 = 部署默认。 |
agent.maxMessageLength |
4000 |
单条外发消息最大字符数(超出自动拆分)。 |
agent.idleTimeoutMs |
1800000 |
聊天空闲多久后释放 agent(0 = 永不)。 |
agent.instructionPrefix |
'' |
附加到每条用户消息前的前缀。 |
http.host / http.port |
0.0.0.0 / 8080 |
webhook 模式 HTTP 服务绑定地址(飞书 webhook / 企微回调)。 |
飞书 / Lark 前置条件
- 在飞书开放平台(国际版用 Lark Open Platform)创建企业自建应用,订阅
im.message.receive_v1事件,并开通消息权限(im:message:send_as_bot、im:message:p2p_msg、im:message:group_msg/group_at_msg)。 - 长连接模式仅企业自建应用可用;在开发者后台事件订阅里选择「使用长连接接收事件」,或配置 webhook 请求地址。
企业微信前置条件
- 在企业微信管理后台创建应用,配置「接收消息服务器」:URL 填
https://你的公网地址/wecom,随机 Token 和 43 位 EncodingAESKey 填入配置。 - 企业微信没有长连接模式,回调服务器需要公网 HTTPS 地址(或隧道)。
聊天命令
| 命令 | 作用 |
|---|---|
/help |
显示命令帮助。 |
/reset |
清空当前聊天的对话上下文(重建 agent)。 |
/status |
显示活跃会话 / 智能体 / 适配器。 |
/model |
显示当前模型选择。 |
工作原理
IM 平台 ──(适配器)──► Bridge ──► ctx.agents.create({ sessionId })
▲ │ │
└──── 回复文本 ◄───────────┴── session/event 监听 ◄── agent 回合
- 每个
platform:chatId对应一个 agent 会话(参照@deepseek-ai/dsh-headless,但按聊天常驻)。 - 入站 IM 消息以
source.kind = 'plugin'/form = 'relay'注入会话(社区惯例);出站文本通过session/event(assistant/message,按回合聚合后按maxMessageLength分片)读回。 - 同一聊天的回合通过 busy-promise 链串行,消息排队避免交错。
- 空闲 agent 在
agent.idleTimeoutMs后被释放,下一条消息到来时重建。
安全说明
- 务必配置白名单。 每个启用适配器的
allowedUserIds都要设置;留空意味着任何人都能驱动你的智能体——而它可以执行主机上的工具。 - IM 消息以插件来源的用户消息注入会话,不绕过部署自身的审批/护栏策略,请视同普通用户输入对待。
- 平台密钥(
token、appSecret、encodingAesKey)存放在 profile 的cordis.patch.yml中,请保持该文件私密。
开发
node --test test/ # 单元测试(protobuf 帧编解码)
dsh plugin --profile im add link:D:/projects/dsh-im-hub # 从源码安装
dsh --profile im --patch test/disable-skin.overlay.yml # 带 mock 适配器启动
# 发送消息:curl -X POST http://127.0.0.1:9099/mock -H 'content-type: application/json' -d '{"text":"hi","chatId":"test"}'
提示:如果 dsh-skin 管理器(
$DSH_HOME/cordis.patch.yml)插入的 UI 皮肤行在你的 headless profile 中无法解析,请用--patchoverlay 禁用它(参考test/disable-skin.overlay.yml)——home 层优先于 profile 层,overlay 才是可靠的禁用位置。
License
MIT
链接
同类插件
omdsh-dev/dsh-notification★ 42
回合完成桌面通知,按结果分控 + 关键词过滤。
omdsh-dev/dsh-open-in-vscode★ 40
从 Web GUI 一键在 VS Code 中打开工作区目录。
whyihaveyou/dsh-suite#plugin-notify★ 19
回合完成、错误或待审批时推送 IM webhook(飞书/企微/钉钉/Slack/Discord/自定义)与本地通知。
bill9109/dsh-web-ui-notify★ 12
桌面通知提醒。
bobleer/dsh-acp-for-bitfun★ 9
BitFun 与 DSH 的 ACP 交互对接。
openma-ai/deepseek-harness-acp★ 7
ACP profile 插件与独立 stdio server,可从 Zed 等 ACP 客户端使用完整 DSH agent,并共享 DSH 凭据与会话。