技能使用指南

testing(软件测试技能)Skill 是什么?怎么安装和使用它?

testing(软件测试技能)Skill 教你按项目规范写测试:.sqltest 为首选、TCL 测试如何迁移、Rust 集成测试与 Fuzz 各自适用场景,还给出 make test、cargo test、test-runner 等真实运行命令与日志排查方法。一文看懂四层测试体系分工,让每次改代码都有测试兜底,点开了解安装与使用步骤。

软件测试技能Skilltesting
8 个章节 约 15 分钟阅读 AI 智能生成

软件测试技能Skill:让每一次改代码都有测试兜底

  • 四层测试体系一次讲清:.sqltest(新测试首选)、TCL .test(遗留兼容)、Rust 集成测试、Fuzz 测试,各自该放哪个目录、什么时候用,技能里都有明确对应表。
  • 一套用例多后端跑:.sqltest 格式让同一批测试用例可以在 CLI、Rust 绑定等多个后端上运行,避免为每个入口重复写测试。
  • 迁移有工具兜底:内置 convert 命令,可以把正在淘汰的 TCL .test 批量转换成 .sqltest,转换不全的地方会给出警告,提示你手工补齐。
  • 命令全部现成:make test、make -C testing/runner run-cli、cargo run -p test-runner -- run <目录>、cargo test 等运行方式一应俱全,不用自己摸索。
  • 工程纪律写进技能:每个功能变更必须配一个测试、测试必须先失败后通过、优先使用内存库、不要发明新测试格式——这些规则被固化在技能里,AI 生成测试时会主动遵守。

一、该技能叫什么?如何一键安装 AI 技能提升开发效率?

技能中文名:软件测试技能Skill 技能英文名:testing 技能ID:13734

这个技能解决的问题非常具体:在一个以 SQL 引擎为核心、同时提供 CLI 与 Rust 绑定的代码库里,"测试该写在哪儿、用哪种格式写、怎么跑起来、老测试怎么迁移"这四件事经常靠口口相传。新人接手时容易把新测试写进正在淘汰的 TCL 目录,或者自己发明一套测试写法,导致回归测试形同虚设。testing 技能把这些约定沉淀成一份可被 AI 直接调用的测试指南,让 AI 编码助手在帮你写代码的同时,顺手按项目规范补上对应的测试。

一键安装的思路与步骤:

  1. 确认前提:你的开发环境需要支持"AI 技能(Skill)"机制,即能够把外部技能挂载到 AI 编码助手中使用;同时准备好本地项目工作区,因为该技能中的路径约定(如 testing/runner/tests/、tests/integration/)是相对项目根目录的。
  2. 找到技能入口:在技能市场、技能目录或助手的技能管理面板中,按技能ID 13734 或英文名 testing 检索安装,具体入口与安装命令以官方说明为准。
  3. 启用技能:安装完成后在会话中启用该技能,确保助手在涉及测试编写、测试运行的问题时会加载这份指南。
  4. 验证是否生效:直接向助手提一个典型问题,例如"给 SELECT 1 + 1 写一个 .sqltest 测试",如果它输出的是包含 @database :default:、test 名称 { ... }、expect { ... } 结构的文件,并提示放到 testing/runner/tests/ 下,说明技能已正常加载。若输出的是通用 pytest / JUnit 写法,则说明技能未生效,需要重新检查挂载状态。

需要强调的是,技能本身不改变你的构建系统,它提供的是"测试该怎么写、怎么跑"的规范知识与命令索引,真正的执行仍由你本地的 make 与 cargo 完成。


二、该技能的主要功能和特点

  • 测试类型决策表:用一张表回答"这种场景该写哪种测试"。SQL 兼容性优先 .sqltest(位于 testing/runner/tests/);遗留 SQL 兼容用 TCL .test(正在逐步淘汰);回归测试与复杂场景用 Rust 集成测试(tests/integration/);复杂功能与边缘情况发现用 Fuzz(tests/fuzz/)。
  • 多后端复用同一批用例:.sqltest 格式的设计目标就是让相同的测试用例在多个后端(CLI、Rust 绑定等)上运行,一份用例覆盖多个入口,这是它相比传统单框架测试最明显的差异点。
  • 内置迁移路径:提供 convert 命令把 TCL 测试转成 .sqltest,例如 cargo run -- convert <TCL_test_path> -o <out_dir>。转换不保证 100% 准确,遇到警告时需要手工展开 foreach 循环等结构。
  • 完整的运行命令清单:涵盖整体套件(make test)、单个 TCL 测试(make test-single TEST=select.test)、SQL 测试运行器(make -C testing/runner run-cli 或 cargo run -p test-runner -- run <测试文件或目录>)、Rust 全工作区测试(cargo test)。
  • 测试数据库约定:明确 testing/system/testing.db 中已有 users 和 products 两张表,详细架构指向 docs/testing.md,避免每次重新造数据。
  • 带条件的日志调试:RUST_LOG=none,turso_core=trace make test 可以把详细日志输出到 testing/system/test.log,同时提醒"非常详细",防止误开导致日志刷屏。
  • 把工程纪律写进约束:每个功能更改都需要一个测试;测试必须在"没有改动时失败、有改动时通过";优先内存库 :memory:(sqltest)或 {:memory:}(TCL);不要发明新的测试格式,遵循现有模式;尽可能先写测试。

和普通"测试教程"相比,它强在绑定具体项目结构与真实命令,而不是泛泛讲单元测试理念。


三、如何使用该技能?

第 1 步:判断该写哪种测试。 先问自己:这次改动是 SQL 行为兼容性问题,还是 Rust 层的逻辑/回归问题?是前者写 .sqltest(新测试的首选),是后者写 Rust 集成测试;只有在维护历史用例时才碰 TCL。

第 2 步:编写 .sqltest 测试。 在 testing/runner/tests/ 下新建 *.sqltest 文件,按现有模式写:

@database :default:

test 示例加法 {
    SELECT 1 + 1;
}
expect {
    2
}

test 示例多行 {
    SELECT id, name FROM users WHERE id < 3;
}
expect {
    1|alice
    2|bob
}

要点:多行结果用 | 分隔列,一行一条记录;数据库优先用默认库或内存库;不要顺手改动 SQL 语句本身。

第 3 步:运行验证。 用 make -C testing/runner run-cli 或 cargo run -p test-runner -- run <测试文件或目录> 跑单个用例,确认输出符合预期。同时反向验证一次——在没有应用代码改动时,这个测试应当失败;应用改动后才通过,否则说明测试没有真正覆盖到改动点。

第 4 步:迁移遗留 TCL 测试(如需要)。 先执行 cargo run -- convert <TCL_test_path> -o <out_dir> 生成 .sqltest 初稿,再执行 make -C testing/runner run-rust 验证能否通过。若转换过程有警告,手工补齐缺失部分(例如把 foreach 循环展开)。特别注意:TCL 测试使用硬编码数据库,而 .sqltest 使用不同种子生成的数据库,所以通常需要调整预期结果去匹配新库的输出,而不是修改 SQL 语句。

第 5 步:需要时写 Rust 集成测试。 在 tests/integration/test_foo.rs 中按现有写法组织:

#[test]
fn test_something() {
    let conn = Connection::open_in_memory().unwrap();
    // ...
}

第 6 步:排查失败原因。 开启详细日志:RUST_LOG=none,turso_core=trace make test,到 testing/system/test.log 查看执行轨迹。注意日志量极大,定位完问题后应及时关掉。

第 7 步:回归确认。 提交前跑一遍 make test 与 cargo test,保证 SQL 兼容性与 Rust 层双向通过。


四、同类型竞品对比分析

方案名称 定位 核心功能 安装/使用门槛 适用场景 优势与不足
testing 技能(本技能) 面向 SQL 引擎项目的测试规范助手 四类测试分工、.sqltest / TCL / Rust / Fuzz 写法、convert 迁移、运行与日志命令 低:挂载技能即可,无需额外依赖;需熟悉项目目录约定 数据库内核开发、SQL 兼容性回归、CLI 与 Rust 绑定多后端验证 优势:与项目结构强绑定,规则明确、命令现成;不足:只服务特定项目,不具备通用语言生态覆盖
通用测试框架(如 pytest) 通用编程语言的测试框架 断言、夹具、参数化、插件生态 中:需要自行安装依赖、搭建目录与配置 业务后端、脚本、数据处理的单元与集成测试 优势:生态成熟、上手资料多;不足:不解决 SQL 兼容性对比与多后端复用问题
语言原生测试(如 cargo test 单用) Rust 工作区内置测试 单元测试、集成测试、文档测试 低:随工具链自带 Rust 逻辑层回归 优势:零配置、速度快;不足:难以表达"同一条 SQL 在不同后端结果一致"这类兼容性断言
Fuzz 测试工具 面向边缘情况的自动化探索 随机输入生成、崩溃发现、覆盖率引导 较高:需要搭建语料与运行环境 复杂功能、解析器、边界条件发现 优势:能发现人工想不到的输入组合;不足:不产出可读的确定性用例,不能替代回归测试

可以这样理解四者的关系:testing 技能负责"告诉你在什么位置写什么测试",cargo test 是执行 Rust 侧的引擎,.sqltest 运行器负责 SQL 兼容性,Fuzz 负责发现新问题——四者是互补而非替代。


五、该技能的典型应用场景与实际体验情况

场景一:数据库内核开发者修改 SQL 执行逻辑。 角色:引擎开发者。痛点:改完执行器不敢提交,不确定是否破坏兼容性。使用方式:让 AI 按 .sqltest 格式补一条针对该 SQL 行为的用例,放进 testing/runner/tests/,跑 make -C testing/runner run-cli 验证。实际体验:格式固定、学习成本极低,一条用例十几行就能锁定行为;需要注意的是预期结果必须与种子数据库实际输出一致,否则第一次跑就会红。

场景二:把堆积的 TCL 测试迁移到新格式。 角色:负责测试基建的工程师。痛点:TCL 测试正在逐步淘汰,但人工改写上百个用例不现实。使用方式:先 convert 批量转换,再 make -C testing/runner run-rust 验证,逐条处理警告。实际体验:转换能覆盖大多数测试,但 foreach 一类循环结构往往需要手工展开,且因为数据库从硬编码改为种子生成,预期结果要重新对齐——这一步最花时间,但方向明确,不会卡死。

场景三:Rust 绑定与 CLI 行为对齐。 角色:维护 Rust 绑定的开发者。痛点:同一个 SQL 在 CLI 正常、在绑定里结果不同。使用方式:把同一份 .sqltest 在不同后端上跑,差异立刻暴露。实际体验:这是 .sqltest 相对 TCL 最实在的收益——一次编写、多处验证,省掉了"每个入口各写一套测试"的重复劳动。

场景四:新人接手项目时快速理解测试体系。 角色:新加入的工程师。痛点:不知道测试放在哪、怎么跑、哪些是遗留的。使用方式:直接让 AI 助手基于该技能解释"我要测一个 SELECT 该写在哪"。实际体验:上手难度低,一张表加几条命令就能开始干活;注意事项是要严格遵循"不要发明新的测试格式",否则会制造出第三种没人维护的测试风格。


六、该技能能为用户带来的价值

效率层面:把"翻文档找测试放哪、试错跑哪个命令"的时间压缩到一次提问。.sqltest 的多后端复用特性意味着同一批用例不必为 CLI 和 Rust 绑定各写一遍,测试维护成本随后端数量增加而基本不增长。

质量层面:技能把"每个功能更改都需要一个测试""测试必须在没有改动时失败、有改动时通过"写成硬规则,直接对抗"测试写了但没测到点上"这个最常见的伪覆盖问题,让回归测试真正具备拦截能力。

门槛层面:TCL 测试正在淘汰、.sqltest 是新首选——这种代际切换对新人极不友好。技能给出 convert 命令和验证流程,让迁移从"不敢动"变成"可分批推进",也降低了新人误写进遗留目录的概率。

长期价值:测试规范一旦被固化进 AI 工作流,后续每一次代码改动都会自动带上符合项目约定的测试,形成"改代码 → 补测试 → 双向回归"的稳定闭环,减少对个别资深成员记忆的依赖。


七、常见问题 FAQ

Q1:这个技能怎么安装? 在支持 AI 技能的助手中,按技能ID 13734 或英文名 testing 检索并挂载即可,具体入口与命令以官方说明为准。安装后用"写一个 .sqltest 测试"这类问题验证是否生效,若返回的是通用测试框架写法,说明未加载成功。

Q2:安装后是不是就自动帮我跑测试了? 不是。该技能提供的是测试类型选择、编写格式、运行命令与工程规则等知识,实际的测试执行仍由你本地的 make test、cargo test、make -C testing/runner run-cli 完成。技能的价值在于让 AI 产出的测试符合项目既有模式,而不是替代构建系统。

Q3:新测试到底该写 .sqltest 还是 TCL .test? 新测试首选 .sqltest,放在 testing/runner/tests/ 下。TCL .test 属于遗留 SQL 兼容测试,正在逐步淘汰,只建议在维护历史用例时使用,或按 convert 流程迁移到 .sqltest。

Q4:TCL 转 .sqltest 后测试跑不过,是我转错了吗? 很可能是数据库差异造成的。TCL 测试使用硬编码数据库,.sqltest 使用不同种子生成的数据库,因此预期结果通常需要按新库输出调整。规则是:只改预期结果,尽量不要改动测试中的 SQL 语句;若转换过程有警告,还需要手工补齐被简化的结构(如 foreach 循环)。

Q5:这个技能适合谁用? 最适合参与该项目(SQL 引擎 / 数据库内核方向)开发与测试的工程师,尤其是需要写 SQL 兼容性用例、维护 Rust 集成测试、或推进 TCL 测试迁移的人。如果你做的是普通业务后端开发,通用测试框架会更合适。