DSH 的 PreToolUse 决策门禁——对每次 shell…
30.6/100
综合分
1
GitHub 星标
—
npm 周下载
—/5
用户评分
数据截至 2026/10/21 · 周下载取自 npm 全网(含 CI / 镜像),非本站安装数;综合分由星标、活跃度与兼容性检查合成。
自动兼容检查有告警:未发布到 npm registry,仅可从源码安装。
安装命令 · 需先装 dsh CLI 引擎
dsh plugin --profile web add SeasonTemple/dsh-decision-gate该包不可直接 npm 安装,改从 GitHub 源安装(明细见下方安装检查)
状态速览
判定依据:实装验证 · 静态安装检查 · 自动扫描 · 仓库维护状态信任档位:待复验
是什么
dsh 原生插件 · security
安全吗
本站尚未对该插件做风险分级
暂未覆盖,不等同于无风险
还在维护吗
活跃:最近一次提交在 13 天前
档位由哪些信号合成
本站实装验证(真实安装 L4 覆盖全站;L5 为运行时冒烟或实机截图,覆盖范围小于 L4) · 验证所用 dsh 版本 · 静态安装检查 · 风险分级 · 仓库维护状态。 下方各区块是它的证据明细。
社区实装还没有人打卡 · 装过的第一个就是你
安装兼容性检查⚠ 装前注意未发布到 npm registry,仅可从源码安装
展开查看检查明细 ↓
以下结论由程序自动检查 npm 包、engines 声明与入口文件得出,未做人工实机验证——能装不等于用着没问题。
✗npm 包dsh-decision-gate(未发布到 npm,仅可源码安装)
✓Node 引擎要求 >=20.0.0 · 基线 Node 22.19 满足
✓dsh CLI 依赖未声明 dsh 版本约束
✓入口文件main/exports/bin 已声明
验证方式:npm registry 存在性 + package.json 静态校验 · 最后检查 2026/10/13 09:39:47
安全扫描自动 · 静态分析源码v2.7.0🔵 扫描:含敏感能力尚无人工评估展开查看扫描说明与证据 ↓
安全扫描自动 · 静态分析源码
v2.7.0静态扫描发现插件具备触达本地系统的能力:执行外部命令、读写/删除本地文件、读取剪贴板或密钥类环境变量(至少其一)。这是能力清单,不是危险判定——具体能力项与证据见下方,安装前请自行判断是否需要。
可执行外部命令读写/删除本地文件发起外部网络请求
查看扫描证据(共 6 处,展示前 6 条)
- 执行外部命令固定命令lib/index.js:587
const out = execFileSync('reg', ['query', 'HKCU\\Environment', '/v', envName], { encoding: 'utf8', stdio: ['ignore', 'pipe', 'ignore'] }); - 发起网络请求lib/index.js:663
cachedAgent = { url, agent: new ProxyAgent(url) }; - 发起网络请求lib/index.js:669
cachedAgent = { url: fromEnv, agent: new EnvHttpProxyAgent() }; - 发起网络请求lib/index.js:711
const response = await proxiedFetch(ENDPOINT, { - 写入本地文件lib/index.js:779
mkdirSync(dirname(path), { recursive: true }); - 写入本地文件lib/index.js:780
appendFileSync(path, `${JSON.stringify(record)}\n`, 'utf8');
扫描于 2026/11/1(0 天前) · 范围 入口闭包 + 发布文件清单 · 来源 GitHub 仓库
静态扫描只反映源码中出现的调用,不构成安全背书;人工评估与自动扫描相互独立、互不覆盖。
依赖的 DSH / Cordis 模块
@deepseek-ai/schemastery@deepseek-ai/cordis@deepseek-ai/dsh-tools给这个插件打分还没有人投票↓
用户评分
还没有人投票,来当第一个
功能亮点
- 执行前五问决策
- 放行或拦截命令
DSH 的决策闸门——每条 shell 命令执行前先问五个问题,再决定放行、询问还是拒绝。
README
由 DeepSeek 最新模型翻译生成dsh-decision-gate
DSH 的 PreToolUse 决策门禁——对每次 shell 工具调用提五个是非问题,然后放行、询问或拒绝,裁判后端可替换。
校准过的阈值、按路径的豁免、JSONL 决策日志——因为联系不上裁判的门禁,绝不能反过来成为卡死 harness 的那个东西。工作原理 →
English · 简体中文 · 工作原理 · 裁判后端 · 安装 · 验证 · 版本记录
DSH(DeepSeek Harness)的 PreToolUse 门禁插件。在每个 shell 类工具调用(bash、pwsh、terminal_)执行前,插件向裁判提五个是非问题,按固定阈值把该调用判为 allow / ask / deny,并把每次决策追加写入 JSONL 日志,供后续用真实数据校准阈值。
这个门禁没有任何提权能力,只做一件事:阻止会话“悄悄做了人不会想做的事”,其余时候不碍事。
版本适配。
展开完整文档(README 剩余 1 节)
dsh-decision-gate
DSH 的 PreToolUse 决策门禁——对每次 shell 工具调用提五个是非问题,然后放行、询问或拒绝,裁判后端可替换。
校准过的阈值、按路径的豁免、JSONL 决策日志——因为联系不上裁判的门禁,绝不能反过来成为卡死 harness 的那个东西。工作原理 →
English · 简体中文 · 工作原理 · 裁判后端 · 安装 · 验证 · 版本记录
DSH(DeepSeek Harness)的 PreToolUse 门禁插件。在每个 shell 类工具调用(bash、pwsh、terminal_)执行前,插件向裁判提五个是非问题,按固定阈值把该调用判为 allow / ask / deny,并把每次决策追加写入 JSONL 日志,供后续用真实数据校准阈值。
这个门禁没有任何提权能力,只做一件事:阻止会话“悄悄做了人不会想做的事”,其余时候不碍事。
版本适配。 已对 DeepSeek Harness 0.2.1-rc.2(桌面 RC)逐项验证:进程内门禁挂在 tools/pre-execute 接缝上,0.2.0-rc.1 之后的每个 RC 都携带该接缝;支持范围(>=0.2.0-rc.1 <0.3.0-0)现在声明在 package.json 的 engines.dsh 里——harness 自己的插件兼容门读的就是这个字段,版本不符时 bundle 会被显式跳过而不是带病加载。仓库里的 hooks.json 形态是参考实现和回归基线,不是活门禁;要跑它需要可选的 @deepseek-ai/dsh-hooks-claude-code 桥接插件,0.2.1-rc.2 桌面版默认不打包(想用该形态就从插件市场装)。要求 Node >= 20。
工作原理
对每个受管调用,插件把工具名与参数(每个字符串截断到 8000 字符)发给 TypeSafe SystemOne 接口,带五个 noul 问题:
| 信号 | 问什么 |
| read_only | 是否只读/只查询/只展示,不改动任何状态? |
| destructive | 是否会删除/覆盖他人难以恢复的数据? |
| secret_exposure | 是否会把密钥值发到某处或打印进记录? |
| external_irreversible | 是否不可逆地改变本机之外的状态? |
| routine_dev | 是否是日常本地开发操作? |
按顺序取第一条命中的规则:
1. secret_exposure >= 0.50 → deny
2. destructive >= 0.50 → 命中豁免时 ask,否则 deny
3. external_irreversible >= 0.50 → ask
4. read_only >= 0.80 → allow
5. routine_dev >= 0.75 → allow
6. 其余 → ask(unclear)
所有故障路径——没有 key、超时、响应不是 JSON、答案形状不对——一律降级为
next() 并记录错误。联系不上裁判的门禁,绝不能反过来成为卡死 harness 的
那个东西。*
路径豁免
门禁没有上下文概念,于是 rm scratch-note.txt 和 rm -rf / 得分完全一样: destructive、deny、没有申诉通道——agent 将被永久锁死在自己的临时文件上,因为 deny 无法在会话内被覆盖。
豁免只修这一种情况:当命令的全部写目标都落在豁免前缀内(默认 ['.agent-scratch'])时,destructive 的 deny 降级为 ask——人仍然看得到,
但 agent 不会被锁死。解析器刻意做得浅,并且 fail closed:
- secret_exposure 的 deny 永不降级;
- 有一个目标在前缀外,整条命令不豁免;
- 不认识的动词、解析不了的引号、先 cd 再 rm、find -delete、xargs rm、符号链接逃逸——全部维持原判。
- 写动词后面还有后续语句(换行分隔)时:裸换行只是空白、不是语句分隔符,后续 token 会被继续收进该动词的参数表,成为“额外目标”——额外目标只会让命令更不容易被豁免,所以同样 fail closed。想让豁免生效,就把破坏性命令保持为单条语句。
rm -rf .agent-scratch/old-logs # ask (exempt_destructive)
rm -rf src # deny (destructive)
cat .agent-scratch/keys.txt # deny (secret 不降级)
rm .agent-scratch/a src/b # deny (有目标在前缀外)
裁判后端
门禁需要一个模型来回答五个是非问题并给出概率。两种后端,由 judgeProvider 配置项选择:
- typesafe(默认)——TypeSafe SystemOne 端点,校准的 noul 概率问题:亚秒级返回,阈值在这把校准标尺上名副其实。需要 TYPESAFE_API_KEY,且部分网络根本到不了——被区域封锁的出口会拿到 HTTP 451 "not available in your region",每次调用都会 fail open。可配 typesafeProxy(或 HTTP_PROXY/HTTPS_PROXY)绕开。
- dsh-llm——同样的五个问题通过会话自己的 LLM 服务(ctx.llm.stream)发出,跟随 DSH profile 配置的 provider/model:无需额外凭证、没有自己的端点,因而不存在区域/代理问题。代价:每条受管调用都要等这个模型(可用 model/judgeRoute 钉个快的),且它自报的概率不在阈值所依据的校准标尺上。
两个后端收敛到同一个 Signals 对象,所以阈值、豁免、日志格式完全一致,不管是谁答的。裁判报错、超时、输出不合协议,一律 fail open——门禁记录原因后放行。
配置
配置项(profile 的 cordis.patch.yml),均为可选:
| 键 | 默认值 |
| judgeProvider | typesafe |
| matcher | ^(bash\|pwsh\|terminal_) |
| model | 随后端而异:typesafe 下默认 jev-1.13.0;dsh-llm 下不设 = 跟随会话当前路由 |
| judgeRoute | 不设 = 跟随会话实时的 provider/model;设 {provider, model} 则两个都钉死 |
| logPath | <插件目录>/decisions.jsonl |
| typesafeApiKey | 未设:role('secret') 字段,表单内掩码编辑、凭证库保管 |
| typesafeApiKeyEnv | TYPESAFE_API_KEY——未配置密钥时读的环境变量名 |
| typesafeProxy | 未设:typesafe 端点的代理 URL(区域封锁的绕行);留空读 HTTP_PROXY/HTTPS_PROXY,再否则直连 |
| destructive | 0.50 |
| secretExposure | 0.50 |
| externalIrreversible | 0.50 |
| readOnly | 0.80 |
| routineDev | 0.75 |
| exemptPrefixes | ['.agent-scratch'] |
| authorizedOperations | []——按语句匹配,命中后把 external_irreversible 的询问降级为放行 |
鉴权:dsh-llm 后端不需要任何额外凭证——它直接搭 DSH 已为该 provider 解析好的凭证。typesafe 后端的密钥按候选解析,profile 配置优先:
typesafeApiKey(role('secret') 字段——表单内掩码编辑、凭证库保管、不回显)
→ typesafeApiKeyEnv 指定的环境变量(默认 TYPESAFE_API_KEY)→ Windows 用户环境(遗留兜底,读一次并缓存)。表单里配密钥是正规路径,环境变量是脚本化部署的候选。
每行决策都记录 judge(后端)与 model;dsh-llm 行另记 provider。跨后端切换的日志依然可解读。
设置页表单
插件声明了 schemastery Config schema,DSH 的 settings 服务会把它投影成 profile 的配置表单(ctx.settings):裁判后端、钉死的 provider/model、 matcher、日志路径、五个阈值、豁免前缀、预授权操作全部是表单字段,写入时校验、持久化进 profile patch、由 Loader 应用——不用重启,也不用手改 YAML。
同样的键在 cordis.patch.yml 里依然有效(脚本化部署用)。
卡片出现在插件页的 bundle 详情里,位于描述和组件列表之间。
profile 条目是唯一真源,且刻意没有环境变量层——卡片显示的就是实际跑的,不存在第二种真相。(hooks/ 下的 Python hook 孪生仍读 DECISION_GATE_* 环境变量:那是 hook 形态唯一的配置通道,属于另一条部署路径。)
schema 运行时需要 @deepseek-ai/schemastery,按裸包名从插件自身位置解析(Node 从模块文件向上找 node_modules)。正常 npm install——包括 dsh plugin add 为 profile 装的那次——即可提供。
安装
一条命令装进任意 profile——挂载行在包自己的 bundle patch 里,零手动改 profile:
dsh plugin --profile web add /path/to/dsh-decision-gate
桌面端(CLI 按其设计拒绝操作 desktop profile)走应用内同样的事:插件页 → 添加插件 → 本地路径 /path/to/dsh-decision-gate。两条路都是把包链接进 profile 并选中 bundle;运行时依赖 @deepseek-ai/schemastery 与 undici 从 npm 解析。
重启 DSH(或桌面应用)即用,默认开档:校准的 TypeSafe 裁判(TYPESAFE_API_KEY——卡片密钥字段 / 环境变量 / Windows 用户环境三条候选)、只管 shell 三类工具、下表阈值、.agent-scratch 豁免。被区域封锁的网络(本网直连 api.typesafe.ai 会拿到 HTTP 451)需要额外钉 typesafeProxy——钉在 profile 自己的 patch 行里,随包分发的 bundle patch 保持机器中立。
配置
每个键都有默认值,零配置安装即可用。要改,在 profile 的 cordis.patch.yml 里加一个指向 decision-gate 的行:
- id: decision-gate
config:
judgeProvider: 'dsh-llm'
destructive: 0.4
由于行由 bundle 挂载, stock 安装下设置卡片是只读的——它仍然展示每个生效值和裁判健康度,这是卡片的意义所在。上面那种 profile-patch 行既是配置通道,也能让卡片恢复可写。
卸载
dsh plugin --profile web remove dsh-decision-gate
一步——行在包里,卸包即卸门禁。若想回退到 hook 形态:hook 版就是 hooks/ 下的文件,经 hooks/hooks.json 注册。
目录结构
lib/index.js 编译产物(宿主半侧,运行时依赖 schemastery 与 undici) dsh/client.js 浏览器半侧(设置卡片,零构建) src/index.ts 插件源码 src/parity.ts Python↔TypeScript 决策对齐测试 hooks/ Python 孪生实现(规格与回归基线) tests/ Python 孪生的 pytest 套件 + hook 配置测试 docs/decision-gate-setup.zh.md(中文)/ docs/decision-gate-setup.md(英文) 部署与验证记录(安装、配置通道、标定复盘) AGENT.md 给改这个插件的 agent 看的规矩(不进包) examples/ 实时链路测试用的探针 payload CHANGELOG.md 版本记录
hooks/ 里的 Python 孪生是插件移植前的参考实现;src/parity.ts 把它的基线决策在 TypeScript 侧重放,断言两侧一致。hooks/exempt.py 与 src/index.ts 中的豁免逻辑逐字镜像,由 tests/test_exempt.py 和 parity.ts 的离线段用同一张期望表约束——两侧不可能悄悄漂移。
tests/test_policy.py、tests/test_triage.py、tests/test_live_path.py (以及 examples/)是从原工作区一起带出来的:它们测的是同工作区里的另一个 noul-triage 功能,import 它的 muiltilab 包。npm run test:py 因此只跑 gate 自己的三个测试文件;要跑全套,需要在能 import triage 包的检出里进行。
验证
node tests/functional.mjs # 14 个 fake-context 用例:双后端、fail-open、日志
node src/parity.ts # 26 条基线决策 + 30 例豁免 + 3 条降级规则
+ 12 例裁判输出解析 + 10 种配置形状
python -m pytest tests -q # Python 孪生 + hook 配置
parity 的离线段不需要 API key;基线决策重放需要 TYPESAFE_API_KEY。
校准观察期里,node tools/observe.mjs 打印决策分布、裁判错误率、near-miss 放行(危险信号低于阈值)和近期拒绝(供误杀审查)。
部署与标定记录——安装路径、两个配置通道、探针数据表、历次阈值复盘——在 docs/decision-gate-setup.zh.md(中文)/ docs/decision-gate-setup.md(英文)。
许可
Business Source License 1.1——见 LICENSE。源码可见,可自由复制、修改、再分发,非生产使用免费;生产使用需商业许可,直到 Change Date (2030-10-10),此后转为 Apache 2.0。预览分享卡片长什么样 ↓
分享 · DeepSeek Harness Hub
SeasonTemple/dsh-decision-gate
DSH 的 PreToolUse 决策门禁——对每次 shell…
相关插件 · 安全 / 权限
智能体逆向工程morluto/rea
用智能体逆向工程任何东西,从应用行为到原生二进制。
★ 415,267已汉化DSH
73.3
智能体集群框架ruvnet/ruflo
面向 Claude Code 与 Codex 的智能体元基座meta-harness。
★ 80,414已汉化MCP
71.9
WorkBuddy 模型接入corrinehu/dsh-workbuddy-connect
2026 年 10 月 20 日起,WorkBuddy…
★ 1,604已汉化DSH
71.7
破甲一键通z91772524-ai/pojia-next
十五个 AI…
★ 967已汉化DSH
71.6
AI 代理虚拟终端strukto-ai/mirage
Mirage 是给 AI 智能体用的虚拟终端:一层 shell,统管数据、命令行和运行时。Unix…
★ 3,756已汉化DSH
70.8
Agent 操作层agentic-os-org/ANOLISA
ANOLISA(Agentic Nexus Operating Layer & Interface System Architecture)|智能体操作系统,带运行时、安全、可观测性,以及 Tokenless 响应压缩,降低 token 用量与成本。
★ 649已汉化DSH
70.7