前言¶
DeepSeek Harness(DSH)的會話是「一次一步」推進的:某個工具調用在前臺跑多久,整輪對話就停多久。Agent 執行 bash({ command: "sleep 60" }) 會把會話凍住一分鐘;長時間 wait_agent 同理。DSH 對超時較慢的「工作型」命令有 promote 到後臺作業的兜底,但先要耗完 timeout,而純等待並不是工作。
在工作區裏寫 AGENTS.md 或給每個 preset 複製規則,新工作區容易漏配。維護者 JJJACKsong 的 sleep-not-permitted 是 profile 級 DSH 插件(npm 包名 dsh-plugin-sleep-not-permitted,當前目錄頁標註 v0.4.0),裝一次後對所有工作區、會話與子代理生效,用系統提示預防 + 工具守衛拒絕,把等待改寫成後臺作業或結束本輪等待完成通知。
這是什麼¶
sleep-not-permitted 是 DeepSeek Harness 的 Cordis 宿主插件:禁止 Agent 在前臺「乾等」。當模型嘗試 sleep、wait、tail -f、watch、無 -c 的 ping、無限循環等命令,或調用超過預算的阻塞等待工具(wait_agent、job_output 且 wait: true)時,調用會被同步拒絕;拒絕原因裏寫明應使用 run_in_background: true,或結束本輪由作業完成通知喚醒。
守衛不會偷偷改寫工具參數——DSH 在分發前會記錄並展示參數,插件只能拒絕、不能僞裝成另一次調用。
- 維護者:JJJACKsong
- 分類:工作流(SkillHub 目錄)
- 倉庫:https://github.com/JJJACKsong/sleep-not-permitted
- 許可證:MIT(見倉庫
LICENSE)
核心功能¶
下面按 README 已說明的行爲歸納,不做超出文檔的擴展。
預防與 enforcement¶
- 事前預防:在系統提示中緊貼「後臺作業」段落寫入同一條規則(
announceInPrompt: true時),引導模型優先選後臺形態。 - 事後門禁:若仍以前臺形式調用,通過
ctx.tools.guard()同步拒絕,錯誤信息中包含可照抄的重試方式。
會被攔截的內容¶
等待型 shell 命令(默認作用於 bash、pwsh、terminal_send):sleep、wait、tail -f / -F、watch、無 -c 的 ping、yes、while true 類無限循環,以及 docker logs -f、journalctl -f、kubectl logs -f 等跟隨日誌。引號內的字面量不算命中(例如 echo "sleep 30" 放行)。
阻塞等待工具:wait_agent,以及 job_output 在 wait: true 且請求等待超過 maxBlockingWaitMs(默認 30000 毫秒)時。設爲 0 可進入嚴格模式:任意前臺等待一律拒絕。
輪詢:在 pollWindowMs(默認 120000)內同一檢查命令出現超過 pollRepeatThreshold(默認 3)次時拒絕,避免用「睡一下再 check」代替正式等待。
交互式 / 需人工確認的命令(interactiveGuard: true 時):如不帶 -n 的 sudo、不帶 BatchMode 的 ssh、vim / less / top、docker run -it、npm login 等。這類命令在後臺也會被拒——後臺作業無 stdin,會靜默掛住。
已帶 run_in_background: true 的調用放行(後臺作業內的 sleep 允許)。普通命令、ask_user_question、不帶 wait 的 job_output 等不受影響。
外部等待的正確寫法¶
若等待對象沒有本地 DSH job 句柄(遠端主機、外部服務),應把「等待本身」包進後臺作業,例如:
ssh host 'until [ -f done ]; do sleep 5; done'
並對該 bash 調用設置 run_in_background: true,然後結束本輪;作業完成後由通知喚醒,再用 job_output 讀結果。完成通知只表示作業結束,不代表成功,需根據 completed / failed / killed 與 exit code 再決策。
安裝與啓用¶
插件以標準 DSH bundle 形式掛載(dsh.bundle.patch → cordis.patch.yml)。SkillHub 目錄頁的說明是:請安裝 DSH 插件 JJJACKsong/sleep-not-permitted(可在 DSH 內讓插件管理器讀取該標識完成安裝)。
README 給出的 web profile 預構建包安裝示例(無需本地構建)如下;路徑中的版本與 release 文件名以文檔原文爲準:
dsh plugin --profile web add https://github.com/JJJACKsong/sleep-not-permitted/releases/download/v0.1.0/dsh-plugin-sleep-not-permitted-0.1.0.tgz
若已有插件目錄的絕對路徑,也可:
dsh plugin --profile web add /path/to/sleep-not-permitted
Electron desktop profile 需用會話內 plugin_manager 的 install_bundle,target 傳目錄絕對路徑(詳見 README「安裝 / 卸載」)。
卸載 web profile:
dsh plugin --profile web remove dsh-plugin-sleep-not-permitted
臨時關閉而不卸載:將配置中 enabled 設爲 false,或在插件管理頁關閉 sleep-not-permitted 條目。
注意:插件隨當前 DSH 進程權限運行,安裝前請自行審閱倉庫源碼與 MIT 許可證;社區目錄 SkillHub 爲獨立站點,與 DeepSeek / 幻方無官方從屬關係。
配置要點¶
在 profile 的 cordis.patch.yml 中按 id 覆蓋,或編輯插件包內 cordis.patch.yml。節選常用字段:
- id: sleep-not-permitted
name: 'dsh-plugin-sleep-not-permitted'
config:
enabled: true
maxBlockingWaitMs: 30000 # 0 = 拒絕一切前臺等待
antiPolling: true
pollRepeatThreshold: 3
pollWindowMs: 120000
interactiveGuard: true
announceInPrompt: true
language: auto # auto | both | zh | en
disabledRules: []
extraRules: []
未知規則 id、空 tools、非法正則等會在掛載期直接報錯,不會出現「已安裝但未生效」的靜默狀態。peer 依賴 @deepseek-ai/cordis ^4.0.2 與 @deepseek-ai/dsh-tools;README 寫明在 DSH 0.1.5-rc.2 與 0.2.1-rc.3 上驗證。
典型驗證步驟¶
README 建議用下列方式確認守衛已生效:
- 前臺
sleep 5→ 應立即被拒,模型看到Error: …及重試說明。 wait_agent(timeout_ms: 300000)→ 超過默認 30 秒預算,應立即被拒。- 對
sleep 5使用run_in_background: true→ 應立刻得到 jobId,結束後收到完成通知。 announceInPrompt: true時,系統提示中應出現對應規則段。
倉庫內測試命令:
node --test test/detect.test.mjs test/plugin.test.mjs
適用場景與邊界¶
適合:長期跑 DSH Agent、依賴後臺作業與完成通知的工作流;希望統一禁止前臺 sleep / 輪詢 / 長阻塞 wait,避免會話被無意凍住。
邊界(README 已知說明):
- 不猜測「可能很慢」的工作命令(如
npm install),仍走 DSH 原有 timeout 與 promote。 bash script.sh內部 sleep 無法靜態檢測,只能靠工具 timeout。- 後臺作業自身無超時;長任務應自行套
timeout、寫 deadline 或結束標記,避免永不通知。 - 中途需要人工決策的任務應先
ask_user_question或走審批,再用非交互參數啓動,而不是丟進無 stdin 的後臺。
結尾¶
sleep-not-permitted 把「禁止前臺等待」從散落的工作區文檔收攏到 profile 級插件:提示詞引導 + guard 拒絕,並明確要求後臺作業或結束本輪。若你在 DSH 裏常被 sleep 或長 wait_agent 拖住會話,可以按上文方式安裝並做一次前臺 / 後臺對比驗證。
- SkillHub 目錄:https://www.skillhub.cn/plugins/JJJACKsong/sleep-not-permitted
- GitHub:https://github.com/JJJACKsong/sleep-not-permitted