用 dsh-stream-rules 按需給 Agent 注入引導規則

前言

給編碼 Agent 加約束,最常見的做法是把規則寫進系統提示:不要直接 pip install、訪問 GitHub API 請用 gh、讀 PDF 走指定 skill。規則一多,每一步都要帶着這些文字進上下文,真正觸發的場景卻很少。上下文被佔着,模型還不一定記得住。

DeepSeek Harness(dsh)的核心理念是「一切皆插件」:模型、工具、會話、UI 都可以用插件增刪替換。社區裏因此出現了不少按這個思路做的擴展。dsh-stream-rules 做的事情比較窄:平時不往系統提示裏塞規則,只在工具調用匹配到模式時,才注入一條 steering 引導。需要時給提醒,平時不佔上下文。

需要先說明:本文寫的是社區插件。DeepSeek Harness 本身由 DeepSeek 開源,插件目錄站點 deepseek-harness-plugin.com 是獨立的社區索引,與 DeepSeek / 幻方沒有官方從屬關係,也不是官方應用商店。安裝前應自己看源碼和許可證。

這是什麼

dsh-stream-rules 是一款 DeepSeek Harness 的「工具與能力」插件,由 jiesou 維護,倉庫在 jiesou/dsh-stream-rules,許可證爲 MIT。npm 包名是 @jiesou/dsh-stream-rules。截至 2026-08-18,GitHub 與目錄頁均顯示 4 個 star;倉庫 package.json 與 npm 上的版本均爲 0.1.7

作者把它定位爲 jiesou/opencode-stream-rules 到 DSH 的移植。README 裏寫思路類似 oh-my-pi 的 Time-traveling stream rules:規則平時休眠,匹配後再注入,避免每輪都付上下文稅。實現上兩者並不相同。oh-my-pi 會在流式輸出中途打斷並重試;dsh-stream-rules 掛在 DSH 的 tools/pre-execute 上,匹配對象是「工具名 + 序列化後的參數」,代碼集中在單個 src/index.ts(約 60 行),沒有改 Harness 核心,也沒有 monkey-patch。

裝上之後默認不會生效。你需要自己寫規則文件,插件纔會在匹配時注入引導。

工作原理

插件監聽 tools/pre-execute。這是 DSH 文檔裏的允許 / 拒絕 / 詢問瀑布流:工具真正執行前,插件可以放行、拒絕,或往後續步驟排隊一段模型可見的上下文。官方說明裏,agent.inject() 追加的是下一次模型請求能看到的上下文,它不是喚醒空閒 Agent 的接口。

一次工具調用進來後,插件大致按下面的順序處理。

  1. 把工具名和參數展平成一段字符串,對規則列表做 match。命中的是第一條返回 true 的規則。
  2. agentId + 規則下標 做去重。同一條規則在每個會話、每個 agent 上最多觸發一次,和上游實現裏的 notified 去重一致。
  3. 若規則帶 reject: true,第一次命中時返回 { kind: 'deny', reason: prompt },這次工具調用被拒絕;同一條規則再次命中則放行。
  4. 若未設置 reject,則通過 agent.inject() 注入一條 SYSTEM NOTICE: … 引導,然後 next() 放行當前這次調用。引導進入下一次 pre-step 的模型可見上下文。

這兩條路徑要分開看。README 把整體效果概括成「注入引導後 agent 從同一位置重試」,更貼近 reject: true 的行爲:第一次攔住,模型看到拒絕原因後再試。默認路徑不會攔住當前這次調用,只是把提示排進後續上下文。如果目標是「第一次就不準執行」,需要顯式寫 reject: true

匹配用的是普通函數,不是正則引擎。match 的入參是扁平化後的字符串,裏面同時包含工具名和參數裏的文本,因此示例裏用 v.includes('pip') && v.includes('install') 這種寫法就能工作。

安裝與啓用

社區目錄頁給出的安裝命令如下,在 DeepSeek Harness 終端裏運行即可:

dsh plugin add github:jiesou/dsh-stream-rules

如需可復現安裝,目錄頁建議固定 commit 哈希:

dsh plugin add github:jiesou/dsh-stream-rules#<commit>

倉庫 README 還提供了指定 profile 的寫法,並推薦從 npm 安裝預構建產物:

dsh plugin --profile <name> add @jiesou/dsh-stream-rules

從 GitHub 安裝時:

dsh plugin --profile <name> add github:jiesou/dsh-stream-rules

也可以在 profile 的 cordis.patch.yml 里加一行:

- id: stream-rules
  name: '@jiesou/dsh-stream-rules'

當前倉庫裏已經包含 lib/ 編譯結果,package.jsonmain 指向 lib/index.js。README 寫 GitHub 安裝會跑 prepare 做構建,但寫作時看到的 package.json 並未聲明 prepare 腳本;若選擇 GitHub 安裝,以當時倉庫裏的構建產物和 DSH 對 git 依賴 prepare 的提示爲準。官方文檔也說明:從 git 安裝等於執行第三方代碼,pnpm 高版本可能要求你顯式允許構建腳本。只安裝你審查過的來源,並儘量釘死 commit。

插件以當前 dsh 進程的權限運行,安裝時可能執行代碼。安裝前請檢查源代碼倉庫和 MIT 許可證。

編寫規則

安裝只是把插件掛進 profile。規則要自己寫。倉庫 rules/ 目錄裏目前只有 rules.js.example,以 _ 開頭的文件會被跳過。

先找到插件目錄。$DSH_HOME 默認是 ~/.dsh

$DSH_HOME/profiles/<name>/node_modules/@jiesou/dsh-stream-rules

然後把示例改名爲本地規則文件:

mv rules/rules.js.example rules/rules.local.js

rules/*.local.js 已被倉庫 .gitignore 忽略,適合放本機規則。直接改 node_modules 裏的文件,升級插件時容易被覆蓋。更穩妥的做法是把規則放到自己的目錄,再用 config.rules 指過去:

- id: stream-rules
  name: '@jiesou/dsh-stream-rules'
  config:
    rules: /path/to/your/rules

示例規則來自倉庫 README,可以直接作爲起點:

// rules/rules.local.js
export default [
  {
    match: (v) =>
      v.includes('pip') &&
      v.includes('install') &&
      !v.includes('uv pip') &&
      !v.includes('uvx'),
    reject: true,
    prompt: 'Use `uvx` or `uv venv` + `uv pip` instead of `pip install` directly',
  },
  {
    match: (v) => v.includes('curl') && v.includes('api.github.com'),
    prompt: 'Prefer using `gh` cli over `curl https://api.github.com/...`. gh offers more requests limits.',
  },
  {
    match: (v) => v.includes('pdf'),
    prompt: 'Use the `markitdown` skill to read PDF files.',
  },
  // add your rules here
]

字段含義如下。

  • match:必填。(v: string) => boolean。每次工具調用都會被扁平化成字符串再匹配。
  • prompt:必填。注入給模型的引導文本;reject: true 時同時作爲拒絕原因。
  • reject:可選。爲 true 時,第一次命中拒絕該次工具調用,之後同一條規則再命中會放行。

第一條示例把裸 pip install 攔住,提示改用 uvx / uv pip,但又排除了已經走 uv 的調用。reject: true 只攔第一次,後續重試會放行,README 給的理由是:引導邊界,但不要把模型鎖死,例如環境已經在容器裏時,仍允許它完成安裝。第二條、第三條只有 prompt,匹配後注入引導,不拒絕當前這次調用。

規則文件可以是 .js.ts,默認導出一個數組。加載失敗時插件會在控制檯打出 [dsh-stream-rules] failed to load …,不會把整個工具調用打掉。

適用場景與注意事項

適合已經在用 DeepSeek Harness、希望用少量本地規則約束工具習慣的人。例如統一包管理器、引導用 gh 而不是手寫 curl、提醒走某個 skill 讀 PDF。它不是權限系統,也不是沙箱:reject: true 只對「該 agent 上這條規則的第一次命中」生效,之後會放行;默認路徑甚至不會攔住當前這次調用。需要硬攔截的策略,應使用 DSH 自己的 tools/pre-execute 權限門、ctx.tools.guard() 或沙箱插件,而不是隻靠這個輕量引導。

匹配是子串函數,不是結構化 schema 校驗。工具名和參數被拼成一段文本,規則寫得太寬容易誤傷,寫得太窄又可能漏掉。每條規則每個 agent 只觸發一次,同一會話裏模型若換一種寫法再次違規,這條規則不會再響。

實現上它依賴 @deepseek-ai/cordis@deepseek-ai/dsh-llm@deepseek-ai/schemastery 等 peer 依賴,並聲明需要 toolsagents 兩個服務。DeepSeek Harness 仍在 developer preview,擴展點若有不兼容變更,社區插件也可能要跟着改。以當時安裝的 dsh 版本和插件源碼爲準。

再次強調:插件以當前 dsh 進程權限運行。安裝社區插件等於在本機執行第三方代碼,請先看倉庫、許可證和 cordis.patch.yml,需要可復現環境時固定 commit。

小結

dsh-stream-rules 把「行爲邊界」從系統提示裏拿出來,改成工具調用上的按需注入。規則自己寫,匹配才說話,不匹配就不佔上下文。實現小,擴展點也是 DSH 文檔裏已有的 tools/pre-executeagent.inject()

目錄頁:https://deepseek-harness-plugin.com/zh-CN/plugins/dsh-stream-rules/

GitHub:https://github.com/jiesou/dsh-stream-rules

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

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

小夜