前言¶
在 DeepSeek Harness(DSH)裏讓智能體跑 Windows 側 PowerShell,常見有兩條路:走 bash 工具進 WSL,或走內置 pwsh 工具。前者會把命令包成 /bin/bash -c "...",外層雙引號往往在 PowerShell 看到腳本之前就把 $ 展開;後者能原樣傳遞 $ 和 here-string,但每次調用都是新進程,整條命令還要擠進 Windows 命令行,大約 32,700 字符就會觸發 spawn ENAMETOOLONG。若腳本很長、或希望變量、當前目錄、已加載模塊在多次工具調用之間保留,內置路徑都會顯得彆扭。
下面介紹社區插件 dsh-pwsh-plugin(維護者 citydirector):它在 Harness 裏註冊 pwsh_run,把腳本正文經 stdin 送進一個常駐的 PowerShell 7 進程;同一倉庫還提供 WSL 側的 llrun 墊片,在 Windows 上替換 bash 工具實現,爲 WSL 命令補上可 enforcement 的寫邊界。插件歸類爲客戶端,在 SkillHub 插件目錄 可查到條目;目錄站與 DeepSeek / 幻方無官方從屬關係,DSH 生態本身是「一切皆插件」的思路,裝什麼由你在 profile 裏選。
這是什麼¶
dsh-pwsh-plugin 是一個發佈在 npm 的 DSH bundle(當前 package 版本 0.2.17,MIT 許可證)。它做兩件事,且都與內置工具並存、不替換內置 pwsh:
pwsh_run:腳本以 base64 走 stdin 進入常駐 pwsh 7,路上不做轉義、不受 32K 命令行上限約束;冷啓動大約 400ms 只付一次。README 記載單次實測 91,741 字符仍可執行,完整數據見倉庫 FINDINGS.md。custom-bash(僅 Windows):bundle 通過cordis.patch.yml插入一行,指向包內wsl/custom-bash.mjs,圍欄使用隨包發佈的llrun二進制,無需手工拷貝到/usr/local/bin。說明見 docs/llrun.md。
運行環境要求:DSH 0.2.0-rc.2 或更新(文檔寫明在 0.2.0-rc.2 與 0.2.1-rc.3 上驗過),以及本機已安裝 PowerShell 7。package.json 中 engines.dsh 爲 >=0.2.0-rc.2 <0.3.0。
核心功能¶
pwsh_run 與內置工具的差別¶
| 層 | 行爲(據 README 歸納) |
|---|---|
bash 工具 |
命令包在 /bin/bash -c "..." 裏,$ 與 heredoc 易在外層被處理掉。 |
內置 pwsh |
轉義正確,但每 call 新進程,且受 Windows 命令行長度限制。 |
pwsh_run |
腳本正文 stdin 送入常駐會話,上述兩類問題在設計上被避開。 |
工具參數如下(名稱與含義以 README 爲準):
| 參數 | 必填 | 說明 |
|---|---|---|
script |
是 | PowerShell 腳本正文,原樣送達;不要轉義 $,不要包 pwsh -c,不要加外層引號。 |
workdir |
否 | 先 Set-Location;會話有狀態,後續調用繼承目錄。無效路徑則本次不執行腳本。 |
timeoutMs |
否 | 單次超時,默認 120000。 |
輸出規則:stdout 原樣返回;warning / verbose 帶前綴;異常帶 [script threw]。錯誤流排在 stdout 之後,stdout 與 stderr 的逐行時序不保留;需要順序時在腳本里自行 2>&1 或 *>&1。
可選配置項包括 pwshPath(默認 pwsh)、idleMs(默認 30 分鐘空閒回收)、maxSessions(默認 4)、maxOutputBytes(默認 8MB)、allowUnconfined(默認 false,沙箱策略缺席時拒絕啓動而非悄悄放開)。常駐進程在啓動時經 ctx.sandbox.confine 包進與內置 pwsh 等價的 workspace 邊界;read-only 模式不啓動 pwsh_run,文檔建議該模式下繼續用內置 pwsh。
bundle 會改 profile 什麼¶
安裝 bundle 後,cordis.patch.yml 會自動插入兩行,無需手改 profile:
id: pwsh-run— 工具本體。id: custom-bash— 僅 Windows 啓用(disabled: !!js process.platform !== 'win32')。
remove 會連同包一起撤掉這兩行。bundle 不會把 Linux 上的官方 tool-bash 關掉;官方行本身已在 Windows 上 disabled。
安裝與啓用¶
插件以 DSH bundle 形式安裝;下列命令與路徑均來自倉庫 README,<version> 須換成 npm 上已發佈的版本號(例如目錄頁或 Plugins 頁給出的最新版)。
側欄(桌面端)
Plugins → Add plugin → 填倉庫地址 https://github.com/citydirector/dsh-pwsh-plugin,再打開開關。
命令行(desktop profile)
desktop 是保留 profile,只能用桌面安裝自帶的 dsh.cmd 管理,並設置正確的 DSH_HOME(桌面 App 使用的數據根,默認思路是 ~/.dsh 下的 profile 樹):
$dsh = '<桌面端安裝目錄>\resources\runtime\cli\bin\dsh.cmd'
$env:DSH_HOME = '<DSH_HOME>'
& $dsh plugin --profile desktop add 'dsh-pwsh-plugin@<version>'
本地開發檢出可用 file: 規格(硬鏈接檢出,改代碼即時生效;registry 規格則是拷貝):
& $dsh plugin --profile desktop add 'file:<檢出目錄>'
也可直接 npm i dsh-pwsh-plugin,效果等價於讓 DSH 解析 registry 包名。README 還提到 github:citydirector/dsh-pwsh-plugin#<tag> 仍可用,但會繞開 pnpm 的 minimumReleaseAge 等供應鏈策略。
安裝後可用非保留 profile 執行 --dump-config,應能看到 # == dsh-pwsh-plugin 以及 - id: pwsh-run。若曾手寫 - id: pwsh-run 再裝 bundle,會出現重複註冊,啓動時報 tool "pwsh_run" is already registered;切換方式時須先刪手寫行再裝 bundle。
不裝成 npm 依賴時的手寫 patch(摘錄)
- insert:
- id: pwsh-run
name: '<路徑>/plugin/index.mjs'
config:
pwshPath: 'pwsh'
plugin/ 下 index.mjs、session.mjs、session-server.ps1 三文件須同目錄存放。
安裝前建議自行瀏覽 GitHub 源碼 與 LICENSE;插件與 DSH 同進程權限運行,沙箱與組合是否完整會影響 pwsh_run 能否啓動(例如缺少 ctx.sandboxPolicy 且未設 allowUnconfined: true 時會拒絕啓動)。
典型用法¶
啓用 pwsh_run 後,智能體每次調用只提交 script 字段裏的 PowerShell 文本,Harness 負責送進常駐會話。下面兩步體現文檔強調的有狀態會話(變量與 workdir 跨調用保留),可在 DSH 裏分兩次調用驗證。
第一次設置工作目錄並寫入變量:
Set-Location 'C:\your\workspace'
$global:buildTag = 'demo-1'
'ok'
第二次在同一 agent 工作區再調用,腳本不必重複 Set-Location,直接讀會話裏已有的值:
$global:buildTag
Get-Location
若單次腳本很長,按 README 的設計無需再爲命令行長度做分段拼接;仍須遵守 maxOutputBytes 與 timeoutMs,輸出截斷或超時會按文檔說明報錯或重建會話。
在 Windows 上啓用 bundle 後,bash 工具會走 custom-bash + llrun 路徑,寫邊界與 SSH agent socket 探測等行爲以 docs/llrun.md 爲準;驗收腳本爲倉庫內 wsl/acceptance.sh(須在未被 custom-bash 再包一層的 WSL 裏跑)。
適用場景與注意¶
更適合誰
- 經常在 DSH 裏跑較長 PowerShell 腳本、或依賴
$/ here-string 且不想和bash -c引號層搏鬥的 Windows 桌面用戶。 - 需要跨多次工具調用保留 pwsh 變量、
Set-Location、已Import-Module的模塊狀態的 agent 工作流。 - 在 Windows + WSL 組合下,希望
bash工具對工作區外寫入(如/mnt/c任意寫)有 landlock 等硬邊界時,可依賴 bundle 自帶的llrun路徑。
務必留意的邊界
read-only沙箱模式:用內置pwsh,不要用pwsh_run。- 升級插件版本會 dispose 常駐會話,僅存在於會話內的狀態會丟失;版本更新走 DSH Plugins 頁的
updateBundle/ 再次add 'dsh-pwsh-plugin@<version>',且 profile 裏須是 registry semver 規格才便於 DSH 比對版本。 workspace-write下捕獲子進程 stdio 的寫法可能失敗(README 故障表有node.exe/ 管道相關說明);需要輸出時改用文檔推薦的Start-Process重定向等模式。- npm 剛發佈後的 CDN 延遲、pnpm
minimumReleaseAge導致「更新裝到舊版」屬於供應鏈策略,不是權限錯誤。
更完整的運行時限制見 docs/runtime-notes.zh-CN.md。
結尾¶
dsh-pwsh-plugin 把「長腳本、少轉義、會話狀態」和「WSL bash 寫邊界」收進一個 MIT 的 DSH bundle:裝完 bundle 即可用 pwsh_run,Windows 上還可一併啓用 custom-bash。若要覈對元數據、版本與安裝入口,可看 SkillHub 目錄頁 與 GitHub 倉庫 中的 README.zh-CN.md。