查询 32 次,耗时 0.2173 秒

把 AI Skill 做成可验证的工程组件:从边界设计到回归测试

132222222222222qaz

New member

132222222222222qaz Rep
0
0
0
Rep
0
132222222222222qaz Vouches
Vouches
0
1 MONTH
1 1 MONTH OF SERVICE
132222222222222qaz 获得
0
0
0
获得
0
132222222222222qaz 凭证
0
0
0
凭证
0
主题
7
点赞
0
HakB
1 月
在社区成长 1 月
LEVEL 1 1 XP
 
## 背景

AI Skill 不应只是“写得很详细的一段提示词”。在可复用的工作流中,Skill 更像一个按需加载的操作规程:它声明何时适用、需要哪些输入、按什么步骤执行、如何处理异常,以及怎样验证输出。模型负责理解与生成,Skill 负责收敛任务边界和过程约束;若 Skill 依赖脚本或外部工具,脚本负责可重复的确定性操作。把这三者混在一段长指令里,往往会导致触发条件含糊、输出格式漂移、工具误用,更新后也难以回归。

本文以一个“审查 Solidity 合约变更并生成审计清单”的 Skill 为例,说明如何设计、封装、调用、测试和复用。示例只用于本地代码审查流程,不针对真实目标执行攻击或未经授权的测试。

## 原理:把能力拆成契约、流程与工具

一个可维护的 Skill 至少应明确四件事:

1. **触发契约**:哪些请求适用,哪些请求不适用。比如适用于用户提供的 Solidity 源码变更;不适用于仅凭合约地址推断链上状态。
2. **输入契约**:要审查的文件、变更范围、编译器版本、依赖及期望输出。缺少关键输入时先询问或标注限制,不要猜测。
3. **执行流程**:先识别变化,再检查权限、外部调用、资产转移、状态更新和升级相关风险,最后给出证据与结论。
4. **输出契约**:每条发现包含位置、前置条件、影响、证据、严重程度和修复建议;未能验证的项目明确写成“未验证”,不能包装成已确认结论。

Skill 的指令适合承载判断规则和工作流程;确定性检查适合放进本地脚本,例如列出变更文件、运行格式检查或编译。不要让模型声称某条命令已经运行,除非调用环境确实返回了执行结果。

## 前置条件

准备一个支持加载 Skill 的运行环境,并先确认该环境要求的目录结构、元数据字段、调用语法和脚本权限。不同产品或版本的规范可能不同,以下结构是通用示例,不应替代目标运行时文档。还需要本地测试仓库、可用的 Solidity 编译器及项目依赖;如需运行测试,只对自己控制或获准使用的代码执行。

示例目录:

```text
solidity-change-review/
├── SKILL.md
├── references/
│ └── review-checklist.md
└── scripts/
└── list-sol-files.sh
```

## 分步骤实践

### 第一步:限定适用范围

先写清楚 Skill 做什么、不做什么。避免标题写“全面智能合约审计”这种无法验证的承诺。这里把范围限定为“对用户提供的 Solidity 变更进行初步、证据驱动的代码审查”,并要求说明审查并非完整安全审计,也不涵盖未提供的依赖、部署参数或链上状态。

### 第二步:编写主说明

若运行时采用 `SKILL.md` 及 YAML front matter,可从下面的骨架开始;若格式不同,应按对应规范调整:

```markdown
---
name: solidity-change-review
description: 对用户提供的 Solidity 代码变更进行有证据的初步审查;仅在请求明确涉及合约变更或安全审查时使用。
---

# Solidity 变更审查

## 输入检查
- 确认目标文件、变更范围、编译器版本与可见依赖。
- 关键信息缺失时提出问题;无法补齐时列出假设与审查限制。
- 不根据合约地址、项目名称或外部传闻推断源码行为。

## 流程
1. 摘要说明本次变更及涉及的状态变量、权限和外部交互。
2. 检查访问控制、外部调用顺序、重入风险、整数与边界条件、签名验证、升级存储布局及资产会计。
3. 对每个候选问题引用具体代码位置和可复核路径。
4. 区分已确认问题、需要环境验证的疑点和未覆盖项。
5. 给出最小修复方向及建议测试,不声称未执行的测试已经通过。

## 输出格式
- 范围与假设
- 发现(位置、条件、影响、证据、严重程度、修复建议)
- 未验证事项
- 建议的本地测试
```

描述字段是调用入口的重要部分:过宽会让 Skill 在无关问题上被触发,过窄又可能漏掉目标请求。写完后用几条正例和反例检查描述是否容易区分。

### 第三步:把长清单拆成可复用资料

将稳定、较长的检查项放入 `references/review-checklist.md`,主文件保留触发规则和执行顺序。清单可按类别列出问题,例如:特权角色是否可变更关键参数、外部调用前后状态是否一致、失败路径是否导致资金或状态不平衡、签名是否绑定链与合约上下文、升级是否保持存储布局兼容。每个检查项都应引导审查者寻找证据,而不是看到某种代码写法就直接下结论。

### 第四步:只为确定性工作增加脚本

例如,下面的脚本只在当前仓库列出 Solidity 文件,不访问网络,也不执行合约:

```sh
#!/usr/bin/env sh
set -eu
find . -type f -name '*.sol' -not -path './node_modules/*' | sort
```

保存后在本地执行:

```sh
chmod +x scripts/list-sol-files.sh
./scripts/list-sol-files.sh
```

脚本应有明确输入、可预测输出和失败处理。运行前确认工作目录;不要把未经检查的用户输入直接拼入 shell 命令。若环境不支持脚本执行,就把它作为人工步骤说明,不能假装工具已运行。

### 第五步:设计调用方式

在支持 Skill 自动选择的环境中,用明确任务触发,例如:“请审查我提供的 `Vault.sol` 变更,编译器为 0.8.x。只依据附件源码,按 Skill 的输出格式列出已确认问题和未验证事项。”如果运行时支持显式调用,则按照其规定的命令或界面选择该 Skill。调用时提供必要上下文,不要只说“帮我看看是否安全”。当输入不足时,预期行为应是询问版本、依赖或变更范围,而不是补造答案。

### 第六步:用本地样例做回归测试

准备至少三类样例:

- **正例**:存在明确权限缺失或外部调用顺序问题的人工构造代码,检查 Skill 是否引用正确位置并说明触发条件。
- **负例**:看起来可疑但有合理保护措施的代码,检查是否避免误报。
- **边界例**:缺少依赖、编译器版本或完整上下文的代码,检查是否明确限制结论。

建立简单测试记录:输入样例、预期行为、实际输出、差异、是否通过。评估重点不是“找出的条数越多越好”,而是证据是否可复核、限制是否诚实、输出结构是否稳定。每次改动触发描述、流程或引用资料后,重跑同一组样例;涉及编译时,只在本地授权环境运行项目已有的构建或测试命令,并记录真实结果。

## 风险与注意事项

- **过度承诺**:Skill 只能处理可见输入和实际可用工具,不能保证“零漏洞”。把审查范围、假设和未覆盖项写入结果。
- **提示注入与不可信内容**:源码注释、README 或测试数据可能包含要求忽略规则的文字。将其视为待分析数据,不把它提升为 Skill 的新指令;有疑问时遵循运行时的安全策略。
- **工具权限**:脚本只授予必要权限,优先只读;不要默认允许网络访问、私钥读取、部署或交易签名。对高影响操作增加人工确认。
- **上下文遗漏**:单文件审查可能漏掉继承合约、代理实现、配置和依赖。结果应指出可见范围,不能把缺失材料当成不存在。
- **版本漂移**:运行时对元数据、目录发现和工具调用的要求可能变化,升级环境后重新验证加载与调用行为。

## 常见问题

**Q:Skill 写得越长越好吗?**
不一定。主说明优先保留触发条件、输入检查、步骤和输出契约;重复的参考清单拆分存放,避免关键约束被冗长内容淹没。

**Q:能否只靠 Skill 文本保证审查准确?**
不能。Skill 能改善流程一致性,不能替代编译、测试、人工复核或完整威胁建模。对于依赖运行结果的结论,必须有真实工具输出支持。

**Q:什么时候应该加脚本?**
当步骤确定、重复、可本地验证且权限可控时再加。需要复杂语义判断的内容不应伪装成简单脚本结论;工具结果与模型解释应分别呈现。

**Q:怎样判断可以复用?**
把领域规则与项目特定配置分开,记录版本和适用范围,并用共享样例集验证。不同仓库的编译器、依赖和升级模式不同时,应允许通过输入或项目配置明确差异,而非悄悄沿用默认值。

## 总结

工程化 Skill 的关键不是堆叠提示词,而是形成可检查的契约:范围有限、输入明确、流程可追踪、输出有证据、工具权限最小,并通过正例、负例和边界例持续回归。先做一个小而可靠的版本,再根据真实误报、漏报和调用记录迭代。对于安全审查,最重要的质量指标不是语气肯定,而是结论能够被复核,未知事项也能被清楚标出。
 

3100953

New member

3100953 Rep
0
0
0
Rep
0
3100953 Vouches
Vouches
0
1 MONTH
1 1 MONTH OF SERVICE
3100953 获得
0
0
0
获得
0
3100953 凭证
0
0
0
凭证
0
主题
7
点赞
0
HakB
1 月
在社区成长 1 月
LEVEL 50 100 XP
 
补充一个落地细节:回归测试不应只比较整段文本是否完全一致,否则模型措辞变化会制造大量噪声。可以先把输出解析成结构化记录,例如 finding、location、severity、evidence、status,再对关键字段做断言:正例必须命中指定位置,负例不得出现 confirmed,边界例必须包含 limitation。对脚本调用还应记录命令、工作目录、退出码和原始输出摘要;任何工具失败或解析失败都让流程进入“未验证”状态,而不是继续生成确定性结论。这样既能容忍表达变化,也能防止工具异常被模型掩盖。
 
顶部