前言¶
把長任務交給 DeepSeek Harness(DSH)跑的時候,最難判斷的往往不是「慢」,而是「還在不在動」。一次編譯可能要十分鐘,一次長文本生成也可能一直沒有新的界面反饋;與此同時,LLM 請求掛起、工具調用空等、循環空轉,看起來同樣像卡住。如果看門狗只按牆鍾時間殺任務,長操作會被誤傷;如果完全不管,會話又會在真靜默裏耗下去。
dsh-stall-guard 要解決的就是這件事:跟蹤每個會話的最後活動時間和在飛操作,只有「運行中、沒有任何事件、也沒有任何在飛調用」才判定爲真卡死,然後用「排查 → 修復 → 換方向」的階梯消息把 Agent 推回去。倉庫 README 把這一點寫得很死:全程不終止任何任務。
本文按插件目錄頁、GitHub 倉庫 README、package.json 和 lib/index.js 交叉覈對後整理:它是什麼、怎麼判定卡住、如何安裝配置,以及查看狀態時該看哪些文件。
這是什麼¶
dsh-stall-guard 是一款面向 DeepSeek Harness 的任務看門狗插件,由 GitHub 用戶 akira399 維護,倉庫地址是 akira399/dsh-stall-guard。社區目錄把它歸在「會話與消息」分類,許可證爲 MIT,主要語言是 JavaScript。寫作時(2026-08-18)GitHub 顯示 3 顆星,package.json 版本爲 1.3.0,要求 Node.js >=20,零 npm 依賴。
它解決的不是「給 Agent 加一個停止按鈕」,而是這三類現場:
- 會話顯示 running,但長時間既沒有 turn/step/tool/LLM 事件,也沒有在飛操作
- 長構建、長生成這類「看起來很久、其實還在幹活」的任務,不能被當成卡死
- 真靜默發生後,需要可復現的引導,而不是直接掐掉當前任務
DeepSeek Harness 官方倉庫的定位是「一切皆插件」:模型、工具、會話、循環等能力都由插件組合。dsh-stall-guard 走的是社區插件這條路,收錄在獨立站點 DeepSeek Harness 插件庫;該目錄與 DeepSeek / 幻方沒有官方從屬關係,安裝前應把它當成第三方源碼來審查。
需要提前說清一處文案差異:目錄頁的一句話簡介仍寫「只在真正靜默時輕推或終止」。對照倉庫 README、package.json 描述和 1.3.0 源碼,當前實現沒有 terminate 選項,也不會發出終止指令;狀態字段裏雖然還留着 terminated,註釋寫明只是兼容保留、不會再被置位。下文以倉庫一手資料爲準。
核心功能¶
監控 → 判斷 → 繼續 / 修復 / 換方向¶
插件掛上 agent/status 和 session/event,爲每個會話維護「最後活動時間」和「在飛操作計數」。週期掃描的間隔由 checkIntervalMs 控制(默認 5 秒)。判定邏輯可以壓成一張表:
| 任務情況 | 判定 | 行爲 |
|---|---|---|
| 持續有事件(步驟 / 工具 / LLM 流在動) | 推進中 | 不干預;任何活動都會把階梯重置回第 1 級 |
| 單個長操作在飛(如 10 分鐘構建、長文本生成) | 推進中(busy > 0) |
不引導;超過 busyTimeoutMs 只記一條 LONG_RUNNING |
無事件 + 無在飛,靜默超過 stallThresholdMs |
真卡死 | 階梯式引導:診斷 → 修復 → 換方向循環 |
默認真靜默閾值是 120000 ms(2 分鐘)。在飛觀察窗口默認 600000 ms(10 分鐘);把 busyTimeoutMs 設爲 0 可以關掉 LONG_RUNNING 記錄,但不會因此開始引導——有操作在飛時,源碼直接 return。
三級階梯,只注入消息¶
policy 默認是 auto。真靜默確認後,插件通過會話的合法通道注入一條 user/message,按冷卻間隔(默認 30 秒)升級:
- 第 1 級 DIAGNOSED(排查):請 Agent 說明自己在等什麼、是否有操作失敗或掛起。
- 第 2 級 FIXING(修復):請它針對卡點重試、完成掛起調用或修好出錯步驟,然後繼續。
- 第 3 級及以後 REDIRECTING(換方向):請它放棄當前方法、改用替代方案,並保留已完成成果。第 3 級之後按同一冷卻間隔循環,沒有終止檔。
默認文案寫在 lib/index.js 裏,每條都會再附一行看門狗自己的診斷,格式類似:
[看門狗診斷] 最後活動:tool/call;位置:第 2 輪第 5 步;已靜默 125000ms。
如果只想記日誌、不向 Agent 說話,把 policy 改成 report 即可。
在飛豁免與運行狀態¶
「有操作在飛 = 推進中」靠事件對來計數:
tool/call、tool/code-dispatch、tool-workflow/run-start、request/header:busy + 1tool/result、tool-workflow/run-end、assistant/message:busy - 1(不會減到 0 以下)step/end、turn/end:把busy清零,避免計數漂移
運行中狀態由 turn/start / turn/end 驅動,同時也監聽 agent/status。README 特別寫了:即使錯過 agent/status,turn 一打開就會開始監視。覆蓋的無進展場景包括 LLM 調用掛起、工具調用掛起、循環空轉。
還有一條設計邊界必須知道:如果 Agent 卡在一個永不返回的 await 上,注入的消息會排隊到該步驟結束後才被處理。插件此時不會殺任務,只會按冷卻繼續下一級引導。
事件落盤和狀態接口¶
每次檢測或引導都會追加到 $DSH_HOME/stall-guard/events.jsonl(未設置 DSH_HOME 時等價於 ~/.dsh/stall-guard/events.jsonl)。事件類型只有:
STALL:真靜默檢測(默認每 60 秒最多記一次,避免刷屏)LONG_RUNNING:在飛過久,僅記錄DIAGNOSED/FIXING/REDIRECTING:階梯注入是否成功
README 強調:永遠沒有終止類事件。若本機開了 Web UI,還可以查即時狀態:
GET http://127.0.0.1:3080/api/dsh-stall-guard/status
返回當前配置、各會話的 ladderStage、以及最近 50 條事件。GUI 通知在 README 裏被標成後續增強,當前版本沒有這一項。
安裝與啓用¶
目錄頁給出的安裝命令如下,在 DeepSeek Harness 終端裏運行即可:
dsh plugin add github:akira399/dsh-stall-guard
如需可復現安裝,按目錄頁說明固定 commit。寫作時 main 分支最新提交是 db5b2147ccd60c0a0f9305f12402fb84491e919d(對應 1.3.0):
dsh plugin add github:akira399/dsh-stall-guard#db5b2147ccd60c0a0f9305f12402fb84491e919d
倉庫 README 另給了一條帶 profile 的寫法,適合用 npx 拉 CLI、並明確裝進 web profile 的場景:
npx -p @deepseek-ai/dsh dsh plugin --profile web add github:akira399/dsh-stall-guard
安裝後需要重啓 DSH。cordis.patch.yml 會把插件插入當前 profile 的組合配置,默認啓用(opt-out)。修改 settings.yaml 裏 stall-guard 段之後熱生效,不必再重啓。
目錄頁的安全提示同樣適用:插件以當前 dsh 進程的權限運行,安裝時可能執行代碼。安裝前請檢查源代碼倉庫和許可證。
典型用法¶
1. 使用默認閾值,只在真靜默時引導¶
裝好並重啓後,默認配置已經是「開着、2 分鐘真靜默、auto 階梯」。適合大多數「偶爾會掛、但不希望長任務被碰」的編碼 Agent。你不需要先寫配置;只要會話處於 running,插件就會從 turn 打開開始監視。
2. 把靜默閾值改短,並確認是 auto 策略¶
如果本地任務通常幾分鐘內就會有工具回包,可以把閾值改到 60 秒,掃描間隔改到 3 秒。倉庫 README 給的示例是:
stall-guard:
stallThresholdMs: 60000
checkIntervalMs: 3000
policy: auto
保存後配置熱生效。想先觀察、不注入消息時,把 policy 改成 report。
3. 看日誌,確認引導而不是誤殺¶
真靜默發生後,打開事件文件,確認出現的是 STALL 和階梯事件,而不是對長操作動手:
tail -n 20 ~/.dsh/stall-guard/events.jsonl
同時請求狀態接口,覈對 busy、idleMs 和 ladderStage:
curl -s http://127.0.0.1:3080/api/dsh-stall-guard/status
如果某次構建已經跑了很久,但 busy > 0,狀態裏不應出現階梯升級,日誌裏最多隻有 LONG_RUNNING。這就是 README 說的:「任務執行時間長」不等於「卡住」。
4. 自定義三級文案(可選)¶
diagnoseMessage、fixMessage、redirectMessage 都可以改。留空或不寫時,源碼會回退到內置中文默認句。每條仍會自動拼接 [看門狗診斷] 那一行,自定義文案不用自己拼現場信息。
倉庫提供了自檢命令,覆蓋語法、默認配置、在飛豁免、階梯循環不終止、活動重置階梯、STALL 節流和狀態路由等:
pnpm verify
適用場景與注意事項¶
適合:
- 經常把編譯、測試、長生成交給 DSH,又擔心會話在無事件時悄悄停住
- 需要一份可審計的卡頓記錄(JSONL + 狀態接口),而不是隻看聊天窗口
- 希望干預手段僅限於「給 Agent 再寫一句話」,不要由插件結束任務
需要注意:
- 插件以當前 dsh 進程權限運行,安裝時可能執行代碼。使用前閱讀 akira399/dsh-stall-guard 源碼和 MIT 許可證;生產環境建議固定 commit。
- 它不是硬中止。卡在永不返回的 await 時,消息會排隊;此時仍要靠宿主界面的停止能力或人工介入。
- 在飛計數依賴特定事件類型。若某個工具或工作流不走 README 列出的那幾對事件,
busy可能不準,表現爲該豁免或不該豁免。 - Web 狀態路由依賴
webServer服務;沒有 Web UI 時,仍可看events.jsonl和插件日誌。 - 社區目錄不是官方應用商店。DSH 仍處於開發者預覽,核心 API 會繼續變,插件行爲以當時安裝的 commit 爲準。
結尾¶
dsh-stall-guard 把「慢」和「死」拆開:有事件或有在飛操作就當作推進中;只有真靜默才按排查、修復、換方向循環輕推,並且把每次判定寫進日誌。對長時間跑任務、又不想被看門狗誤殺的 DSH 用戶,這是一套邊界寫得很清楚的社區方案。
目錄頁:https://deepseek-harness-plugin.com/zh-CN/plugins/dsh-stall-guard/
GitHub:https://github.com/akira399/dsh-stall-guard