Supertest API 测试 Skill:从服务接口到自动化集成测试

API 自动化测试先回答业务问题,再选择框架。登录失败该返回什么?订单重复提交怎么处理?库存不足时调用方依赖哪个错误码?这些答案来自接口定义、需求和现有行为。Supertest 负责把答案写成 Node.js 项目能执行的测试。

api-test-supertest Skill 的工作是读取多种 API 材料,整理场景和边界,再生成可运行的 Supertest 脚本。它不替项目定义接口,也不把没有执行过的测试写成已通过。

Awesome QA Skills 按语言和测试阶段组织 Skill。通用安装方式见系列总览;本文只讲 API 测试落到 Supertest 时该如何使用它。

先准备接口测试材料

Skill 可以读取 OpenAPI、Swagger、Postman/Bruno Collection、接口文档、需求说明和已有测试。材料越接近当前版本,生成结果越能直接进入回归。

至少明确这几件事:

  • 接口版本、基础地址和认证方式;
  • 本次业务范围,例如“创建订单”和“取消订单”;
  • 成功、权限、参数校验、状态冲突等关键场景;
  • 测试数据如何创建和清理;
  • 现有测试目录、运行命令和 CI 产物位置。

接口文档只写了 POST /orders 时,Skill 可以补出待确认问题;它不能凭空决定重复请求应返回 200201 还是 409。这一步省不了,后面所有断言都依赖它。

用统一场景描述 API 测试

框架会变,场景骨架保持稳定。先把接口行为写清楚,再把它交给 Supertest:

场景:已登录用户创建订单
前置:库存 book-001 为 2;用户拥有 buyer 权限
请求:POST /api/orders,body 为 { "sku": "book-001", "quantity": 1 }
预期响应:201;返回订单 ID、sku 和 PENDING 状态
预期副作用:库存变为 1;发布 order.created 事件
证据:测试报告、失败响应、构建号

一条完整的 API 用例至少验证响应语义;有状态变化时,再验证数据库、事件或下游调用。只断言状态码很快,接口把错误码、字段类型或副作用改坏时也容易漏过去。

从输入材料到回归入口

把接口材料交给 Skill 后,先要求它输出场景清单,再生成测试文件。这个顺序能把“缺少业务规则”和“代码还没接通”分开:

docs/openapi.yaml                 # 路径、参数、schema
docs/order-rules.md               # 幂等、库存和权限规则
tests/fixtures/orders.ts          # 数据创建与清理
tests/api/orders.api.test.ts      # Supertest 回归入口
artifacts/api/<run-id>/           # 报告、失败响应和日志

场景清单至少列出请求、预期响应、状态变化、数据负责人和待确认项。Skill 生成代码时使用这些字段;评审时也能从测试反查业务规则。

Supertest 在这里做什么

场景确定后,Supertest 负责发送 HTTP 请求和断言响应。它在 Node.js 测试栈里落地,不改变 API 测试本身的业务语义。

import request from 'supertest';

const response = await request(app)
  .post('/api/orders')
  .set('Authorization', `Bearer ${token}`)
  .send({ sku: 'book-001', quantity: 1 });

expect(response.status).toBe(201);
expect(response.body).toMatchObject({ sku: 'book-001', status: 'PENDING' });

认证、测试数据和外部依赖的具体写法由项目决定。Skill 应沿用项目已有的 fixture、helper 和断言库,避免生成一套没人维护的新约定。

用 Skill 生成第一版用例

安装:

npx skills add https://github.com/naodeng/awesome-qa-skills/tree/main/skills/zh/testing-types/api-test-supertest -g

调用时把通用 API 测试目标和 Supertest 的落地约束同时交代清楚:

请使用 api-test-supertest Skill。

接口材料:docs/openapi.yaml、docs/order-rules.md
测试范围:创建订单的成功、未登录、库存不足、重复提交
测试数据:tests/fixtures/orders.ts 创建;每个用例后清理
项目约定:Vitest;现有 API 测试在 tests/api;执行命令为 npm test
交付:生成或更新 Supertest 测试文件,列出覆盖场景、未确认规则和未执行命令。

响应断言覆盖状态码、错误码和关键字段;有状态变化时检查必要副作用。
不要把文档中没有定义的业务规则当成事实。

先检查生成的场景是否与接口规则逐条对应,再运行项目命令:

npm test -- orders.api.test.ts

命令输出、报告、失败请求与响应才是运行证据。生成的代码只是待验证产物。

怎么判断已经接入

检查项最低要求失败时的处理
场景覆盖成功、权限、参数、状态冲突都有明确结果回到接口材料补规则
可重复执行每次运行创建自己的数据并完成清理修正 fixture 或隔离策略
失败可定位请求、响应、版本和 run ID 能对应同一次运行补 reporter 或日志字段
CI 可判定测试退出码与门禁规则一致修正脚本和 threshold

先接一条高价值链路。它在本地和 CI 都能稳定复跑以后,再扩展分页、并发和跨服务场景。

这类 API 自动化最容易踩的坑

  1. 只给 Skill 一个 URL,没有接口版本、账号和业务范围,生成结果只能猜。
  2. 把 Bruno 或 Postman 的一次绿色执行当成长期回归证据,实际没有接入项目命令。
  3. 所有用例共用固定订单号或 Token,单独运行正常,并发运行就互相污染。
  4. 只断言 HTTP 状态码,错误体和关键副作用变化没有被发现。
  5. 生成文件放在仓库里,却没有报告目录、失败请求和构建号,问题无法回溯。

这些问题都能在交付前检查出来。先看入口能否被测试运行器发现,再看证据是否能回到具体请求。

Supertest 与其他 API 自动化框架的区别

测试目标相同:验证 HTTP 接口的业务行为与契约。差异在项目语言、测试生态和最终代码形态。

框架适合的项目栈生成产物
SupertestNode.js、JavaScript、TypeScriptSupertest 测试脚本
REST AssuredJava、JUnit、Gradle 或 MavenJava 测试类
PytestPythonPytest 接口测试
BrunoCollection 驱动的接口调试与回归Bruno Collection 与脚本

先按项目技术栈选框架,再复用同一份接口场景和验收规则。切换框架不该把业务测试重新想一遍。

相关 Skill

Skill何时接入
API 契约测试OpenAPI、字段或错误语义发生变化
回归测试选择需要按改动范围挑选接口回归集合
测试报告需要把命令、报告、失败信息交给评审或 CI

API 测试的重点一直在接口行为。Supertest 是把它落进 Node.js 工程的工具,别让框架细节盖住真正要验证的规则。

常见问题

没有 OpenAPI 也能用吗?

可以。提供现有 Collection、接口文档、调用示例或需求说明;缺失的状态码、错误码和业务规则要列为待确认项。

可以把 Bruno Collection 直接交给这个 Skill 吗?

可以把它作为接口材料。最终交付仍是 Supertest 测试脚本,Bruno 不需要成为项目依赖。

什么时候可以接入发布门禁?

本地和 CI 都用同一命令执行,测试数据可重置,失败报告可以定位到请求和版本后,再把它放进门禁。

参考

分享