DeepSeek Harness plugin

dsh-hermes-bridge

DSH ↔ WeChat bridge: inbound dispatch (WeChat → DSH agent, persistent per-cwd session pool) + outbound push (task progress → WeChat via hermes send, zero-LLM). 微信 ↔ DSH 双向桥:入站调度 + 出站推送,常驻会话复用。

Jump to install

Source facts

Repository
dsh-pulse/dsh-hermes-bridge
Latest update
Aug 21, 2026
Category
Remote & Mobile
GitHub stars
0
Format
plugin
Catalog evidence
Upstream dsh.bundle evidence
Evidence path
package.json#dsh.bundle
Checked against
0.1.0-rc.8
Upstream check date
2026-08-20

This evidence comes from the upstream catalog. This site has not installed, run, or security-reviewed the plugin.

Install

Start with a prompt that asks an agent to review the GitHub repository and source. Switch to the command if you want to install it yourself.

Copy this prompt into DSH, Codex, or another agent and ask it to review the GitHub repository and source first.

Do not install or run any commands yet. Read this plugin's GitHub repository, README, and relevant source code. Then answer the questions below clearly and directly so I can decide whether it fits my needs:

1. What is this plugin, and what problem does it solve?
2. Who is it for, and what are its typical use cases?
3. How is it used after installation? Include one minimal example.
4. What known limitations or privacy, security, compatibility, or maintenance risks does it have?
5. Give a clear recommendation: recommend, conditionally recommend, or do not recommend, with reasons.

Distinguish statements documented by the repository, inferences from source code, and unknowns. If evidence is insufficient, say so explicitly. Do not guess or simply repeat the README.

GitHub: https://github.com/dsh-pulse/dsh-hermes-bridge
Plugin: dsh-hermes-bridge
Author: dsh-pulse

Check the source files

Read the README and other files from this plugin directory before installing.

File explorer3 files
README.mdSource · read only

dsh-hermes-bridge

DSH ↔ WeChat bridge plugin: inbound dispatch (WeChat → DSH agent) + outbound push (DSH → WeChat), powered by the Hermes gateway as the WeChat transport. Zero-LLM outbound push via hermes send, and a persistent per-cwd session pool that reuses DSH agent sessions (15–20× cheaper than one-shot headless invocations).

> Scope: this plugin is a task-queue execution endpoint for DSH — it does not implement the WeChat protocol itself. The WeChat side (both the inbound trigger and the transport) comes from a self-deployed Hermes Agent gateway plus your own inbound script; without those, the WeChat half of the chain will not work.

微信 ↔ DSH 双向桥插件:入站调度(微信消息 → DSH agent 执行)+ 出站推送(任务进度/结果 → 微信)。出站走 hermes send 零 LLM 消耗;按工作目录复用常驻会话,比一次性 headless 调用省 15–20× token。

> ⚠️ Read this first — environment assumptions. This plugin was developed against one specific environment (see [Environment assumptions](#environment-assumptions)). DSH and Hermes deployments vary wildly between users; this plugin cannot work out-of-the-box everywhere. Please review the assumptions and adapt the configuration to your setup before expecting it to run. > > ⚠️ 先读环境假设。 本插件基于特定开发环境编写(见「环境假设」章节)。DSH 与 Hermes 的部署方式千奇百怪,本插件无法开箱即用于所有环境,请先核对假设并适配你的配置。

Why

The one-way manual chain "WeChat → Hermes skill → dsh --profile headless" works but burns tokens on cold starts, loses session context between messages, and cannot notify you when a long task finishes. This plugin productizes the chain as a first-class DSH plugin:

  • Session reuse — agents stay alive per working directory (ctx.agents.create/resume + followup), so follow-up messages continue the same conversation.
  • Automatic pushback — every task reports 接单 → 开跑 → 完成/失败 to WeChat with structured changes / verification / leftovers.
  • Zero-LLM outbound — notifications go through hermes send (iLink REST), no model call, no gateway dependency for bot-token platforms.
  • Web UI visible — tasks are registered via ctx.jobs (falls back gracefully when the job controller is absent).

How it works

WeChat ──▶ Hermes gateway ──▶ dsh-run.sh (bridge-first) ──▶ POST 127.0.0.1:8643/v1/tasks
                                                              │
                                                              ▼
                                              persistent session pool (per cwd)
                                                              │
                                          DSH agent (full toolset, followup + whenIdle)
                                                              │
WeChat ◀── hermes send ──◀── structured result pushback ──◀──┘

Inbound: Hermes (or any HTTP client) POSTs a task to the plugin's loopback endpoint. The plugin dispatches to the per-cwd resident agent session and pushes progress back via hermes send. If the bridge is down, the shell script falls back to one-shot dsh --profile headless.

Environment assumptions

Developed and verified on one specific machine (see the deployment notes in DEVELOPMENT.md). Your environment will differ; check each item:

AssumptionValue used hereWhat to adapt on your side
DSH version0.1.0-rc.7 (Node ≥ 22)ctx.agents / ctx.agentPresets / session APIs are rc-stage snapshots — a DSH upgrade may break them. Pin the rc range you run, or adjust code.
DSH profileweb profile (persistent host; dsh web keeps the plugin resident)A headless-only deployment must host the plugin some other way (its HTTP loopback must stay alive).
DSH model configprovider: tokenrhythm / model: deepseek-v4-flash-0731 (from your ~/.dsh/settings.yaml agent-default-model)Point provider/model at your default model. {{model}} is resolved from agentOptions.model — if the persona template says {{model}} has no value, you are missing model.
Hermes installvenv at ~/.hermes/hermes-agent/venv/bin/hermes, gateway service hermes-gateway.service (user systemd)hermesBin config must point at your hermes CLI; the gateway service name/port may differ.
WeChat channeliLink personal-bot channel (ilinkai.weixin.qq.com) reached by HermesYour channel may be Telegram/Discord/Slack/etc. The outbound path only needs hermes send --to <platform>:<target> — switch pushTarget accordingly. The inbound trigger (Hermes skill / hook) is channel-specific.
hermes send targetsverified with hermes send --listRun hermes send --list yourself; chat IDs are environment-specific.
HTTP loopback127.0.0.1:8643Change port if it collides; the host is hardcoded to loopback (security).
Session persistence~/.dsh/sessions (per-user)If your DSH_HOME differs, session resume paths change accordingly.

Known limits (not bugs):

  • WeChat rate limit: the iLink channel throttles sendmessage (ret=-2 → 30s cooldown, handled by Hermes). Bursts of pushes can be dropped/serialized. Keep push volume low (the plugin pushes once per task state, which is fine).
  • No auth layer on the host: dsh web has no authentication by design. Run it loopback-only; do not expose it.
  • rc-stage API drift: any DSH upgrade needs a regression pass (see DEVELOPMENT.md for what to re-verify).

Install

From npm (published as @dsh-pulse/dsh-hermes-bridge):

dsh plugin --profile web add @dsh-pulse/dsh-hermes-bridge

Or from GitHub:

git clone https://github.com/dsh-pulse/dsh-hermes-bridge.git
cd dsh-hermes-bridge && npm install   # installs peer deps if missing

# register in your web profile patch
cat >> ~/.dsh/profiles/web/cordis.patch.yml <<'EOF'
- insert:
    - id: hermes-bridge
      name: 'file:/absolute/path/to/dsh-hermes-bridge/lib/index.js'
      config:
        port: 8643
        authToken: '${env.DSH_BRIDGE_TOKEN}'   # REQUIRED — plugin refuses to start without it
        pushTarget: 'weixin:<chat_id>'          # REQUIRED
        hermesBin: '/path/to/hermes'            # optional, default 'hermes'
        workspaceRoots: ['/path/to/workspace']  # optional cwd whitelist
EOF

Requires @deepseek-ai/cordis (peer dependency) — ships inside DSH. The plugin is designed for the web profile (persistent host); do not install into headless.

Configuration (Config schema)

keytypedefaultdescription
portnumber8643loopback listen port (host is hardcoded 127.0.0.1)
authTokenstringrequired; Bearer token checked on every request (constant-time compare)
pushTargetstringrequired; e.g. weixin:<chat_id> — resolved by hermes send
hermesBinstringhermespath to the hermes CLI
retriesnumber1outbound push retries
maxTextLennumber1500push text truncation
presetstringstandardagent preset mounted in session setup
provider / modelstringdsh defaultsagent model (align with your agent-default-model)
workspaceRootsstring[][]cwd whitelist (realpath prefix check; empty = unrestricted)
maxAgentsnumber3resident session cap (LRU eviction)
maxQueuenumber8task queue cap (429 when full)
taskTtlMsnumber86400000finished task retention (24h)

API (all endpoints require Authorization: Bearer <token>)

EndpointDescription
POST /v1/tasksInbound task {task, context?, cwd?, sessionId?, title?}202 {taskId}
GET /v1/tasks/:idTask status + structured result (changes/verification/leftovers)
POST /v1/tasks/:id/cancelCancel (queued → failed immediately; running → intent flagged)
POST /v1/notifyPure push {text} (no agent involved)
GET /v1/healthLiveness

Pushback messages (one per state, no spam):

📥 已接单 br-xxxxxxxx
🔧 开跑 br-xxxxxxxx
✅ br-xxxxxxxx(6m12s)
改动:…
验证:…
遗留:…

Security

  • Loopback only: server.listen(port, '127.0.0.1') — the host is hardcoded, exposing it requires source changes.
  • Auth required: authToken is mandatory; the plugin refuses to activate without it. Token lives in your profile patch (600 perms) or env, never in code.
  • cwd whitelist: when workspaceRoots is set, paths outside it are rejected (403) both at ingress and inside executeTask.
  • Zero shell: all child processes use spawn(args[]) — task text never passes through a shell.
  • Redaction: outbound push strips sk-/sk_tr_/ghp_ token patterns and credentials paths before sending.

> ⚠️ This plugin executes arbitrary DSH agent work with full tool access. Only feed it trusted instructions (keep the WeChat-side discipline in your Hermes skill layer), and never expose the HTTP port beyond loopback.

Troubleshooting

SymptomCause / fix
prompt variable "{{model}}" has no valueagentOptions.model missing — set model (align with your agent-default-model).
Task reports done but result is emptyCheck the session log for turn/end with reason.kind == "error" — the plugin now flags those as failed; verify model/provider.
hermes send fails Could not resolve targetRun hermes send --list, put the exact target in pushTarget.
EADDRINUSE on the portAnother instance holds it — change port, or restart the host once after code edits (ESM module cache).
WeChat pushes missing/serializediLink rate limit (ret=-2, 30s cooldown) — keep push volume low.
Hermes still runs headless instead of bridgeThe plugin is invoked via dsh-run.sh which internally tries the bridge first (then falls back). If your skill calls something else, point it at dsh-run.sh. See DEVELOPMENT.md §Troubleshooting-Hermes.

Development

See DEVELOPMENT.md (EN) / DEVELOPMENT.zh-CN.md (中文) — architecture decisions, the problems we hit and how they were solved, test strategy, and what to re-verify after a DSH upgrade.

License

MIT