Swagger 扩展学习
Redoc、Stoplight、AsyncAPI、契约测试与规范治理的进一步方向。
Key PointsSwagger 只是入口:文档渲染有 Redoc,设计协作有 Stoplight,异步接口用 AsyncAPI,防漂移靠契约测试。
文档渲染
| Tool | Style | Use when |
|---|---|---|
| Swagger UI | Interactive, try-it built in | Internal debugging |
| Redoc | Read-only, three columns | Public documentation |
| Stoplight Elements | Embeddable web components | Docs inside your product |
设计与协作
- Stoplight Studio — 可视化编辑规范,适合非后端同学参与
- SwaggerHub — 托管、版本、评论、团队权限
- Apicurio — 开源替代,可自托管
异步接口:AsyncAPI
Message-based interfaces (Kafka, RabbitMQ, WebSocket) have no URLs, so OpenAPI cannot describe them. AsyncAPI applies the same idea to events: channels, message schemas, protocol bindings.
YAML
asyncapi: 3.0.0
info:
title: Order Events
version: 1.0.0
channels:
orderCreated:
address: orders.created
messages:
orderCreated:
payload:
type: object
properties:
orderId: { type: integer }
total: { type: number }防漂移:契约测试
Specs drift when the implementation changes. Contract tests validate real responses against the spec, failing on missing fields or wrong types.
JavaScript
// 用 chai-openapi-response-validator 校验真实响应
import ChaiOpenApiResponseValidator from "chai-openapi-response-validator";
chai.use(ChaiOpenApiResponseValidator({ apiSpecPath: "./openapi.yaml" }));
it("GET /users/42 matches the spec", async () => {
const res = await request(app).get("/users/42");
expect(res).to.have.status(200).and.to.satisfyApiSpec;
});规范治理清单
operationId必须唯一且稳定——SDK 的方法名由它决定- 每个 operation 至少一个
example,否则 mock 与文档都很空 - 错误响应统一定义在
components/responses,不要每个接口重复写 - 破坏性变更必须升
info.version,并在 changelog 里写清楚 - 规范文件纳入代码评审,和接口实现一起 review
Making "spec passes lint" a required check is worth more than ten pages of guidelines. Whatever a tool can enforce should not rely on discipline.
文档渲染
| 工具 | 风格 | 适用 |
|---|---|---|
| Swagger UI | 可交互,内置调试 | 内部调试 |
| Redoc | 只读,三栏布局 | 对外文档 |
| Stoplight Elements | 可嵌入的 Web 组件 | 嵌进自己的产品 |
设计与协作
- Stoplight Studio —— 可视化编辑规范,适合非后端同学参与
- SwaggerHub —— 托管、版本、评论、团队权限
- Apicurio —— 开源替代,可自托管
异步接口:AsyncAPI
Kafka、RabbitMQ、WebSocket 这类「消息」接口没有 URL,OpenAPI 描述不了。AsyncAPI 是同一套思路在事件世界的对应物:描述 channel、消息结构、绑定协议。
YAML
asyncapi: 3.0.0
info:
title: Order Events
version: 1.0.0
channels:
orderCreated:
address: orders.created
messages:
orderCreated:
payload:
type: object
properties:
orderId: { type: integer }
total: { type: number }防漂移:契约测试
规范写了、实现改了,文档就又过期了。契约测试的做法是:拿规范去校验真实响应,字段缺失、类型不符直接让测试失败。
JavaScript
// 用 chai-openapi-response-validator 校验真实响应
import ChaiOpenApiResponseValidator from "chai-openapi-response-validator";
chai.use(ChaiOpenApiResponseValidator({ apiSpecPath: "./openapi.yaml" }));
it("GET /users/42 matches the spec", async () => {
const res = await request(app).get("/users/42");
expect(res).to.have.status(200).and.to.satisfyApiSpec;
});规范治理清单
operationId必须唯一且稳定——SDK 的方法名由它决定- 每个 operation 至少一个
example,否则 mock 与文档都很空 - 错误响应统一定义在
components/responses,不要每个接口重复写 - 破坏性变更必须升
info.version,并在 changelog 里写清楚 - 规范文件纳入代码评审,和接口实现一起 review
把「规范是否通过 lint」设成合并的必过项,比写十页规范文档更有效。工具能强制的东西,不要靠自觉。