云端 Hook 权限与失败处理
用 preToolUse 控制工具,区分崩溃、超时、HTTP 错误和输出处理。
This page has not been translated into English yet. The original Chinese version is shown below.
云端工具权限预先授予,没有人在每次调用时等待批准。需要阻止某类工具,应使用 preToolUse,不能依赖 CLI 的 permissionRequest 或交互提示。
权限输出
| 字段 | 作用 |
|---|---|
permissionDecision | allow、deny 或 ask;云端 ask 作为 deny |
permissionDecisionReason | 拒绝时必填,给代理说明原因 |
modifiedArgs | 替换工具参数的对象 |
比如一个校验脚本决定拒绝后,返回:
{
"permissionDecision": "deny",
"permissionDecisionReason": "The requested operation is outside this task's approved scope."
}多个 preToolUse Hook 按顺序执行,任一返回 deny 就阻止工具。输出 {} 或空内容则回到默认流程。
失败方式不是同一种结果
| 情况 | preToolUse 结果 |
|---|---|
| Command Hook 返回非零,包括 2,或崩溃 | 拒绝工具,即使 stdout 写了 allow |
| Command Hook 超时 | 回到默认权限流程,不因此拒绝 |
| HTTP Hook 网络错误、超时或非 2xx | 回到默认权限流程 |
| 成功并返回明确 deny | 拒绝工具 |
超时始终是 fail-open,并非“安全 Hook 越慢就越严格”。为强制校验选择方案时,应考虑超时或接收端不可达会怎样影响任务,而不是只验证正常拒绝路径。
默认 timeoutSec 为 30 秒;timeout 是秒单位别名,两者都存在时以 timeoutSec 为准。
其他输出
成功后的 postToolUse 可返回 modifiedResult 和 additionalContext。后者在多个 Hook 间用双换行合并,最多 10 KB;整体 Hook 响应还有 10 MiB 的单次上限,两者不能混淆。
userPromptSubmitted 的 modifiedPrompt 仅 SDK 编程 Hook 使用,command/HTTP 配置文件 Hook 不处理它。需要修改模型收到的转换后文本,应核对 userPromptTransformed 的 modifiedTransformedPrompt,它不负责阻止该轮执行。
HTTP Hook
HTTP 类型会把输入 JSON POST 到配置 URL。默认要求 HTTPS,preToolUse 更必须使用 HTTPS。allowedEnvVars 声明允许在请求头中展开的变量名,设置此字段时也要求 HTTPS。
云端目标需要满足网络访问规则。Hooks 参考把默认网络概括为只有 GitHub/Copilot 主机,但防火墙专门文档还明确默认启用常见依赖的推荐 allowlist;部署接收端前应以实际 Internet access 规则检查,不能把两种概括合成固定主机清单。
本地验证脚本
先用代表性 JSON 输入测试脚本,确认退出码、stdout 和 stderr。无效输出或调试文字混入决策输出可能使决策不生效;诊断信息应写到 stderr,并避免输出 token、凭据或完整敏感上下文。
云端教程要求单行 JSON,而参考针对 CLI 说明了 progress 行剥离与最终多行 JSON 解析。跨环境脚本优先输出一个完整、紧凑的决策 JSON,不依赖 CLI 时间线进度输出行为在云端一致。
脚本不运行时,检查默认分支中的 .github/hooks/*.json、version、可执行权限、shebang 和 cwd。教程存在 cwd: scripts 同时命令为 ./scripts/... 的示例;实际使用应按工作目录解析相对路径,避免重复目录。