在 AI 辅助编程(AI-Assisted Programming)日益普及的今天,开发者面临的核心挑战已从“如何写代码”转变为“如何与 AI 协作以获得确定性的结果”。传统的开发模式是 需求 -> 人 -> 代码,而新的范式正在演变为 意图 -> Spec (OpenSpec) -> AI -> 代码 & 验证。
本文以一个 小型电商系统 的从零构建到生产级演进为例,深度复盘基于 OpenSpec 的 AI 协同开发全流程。我们将展示 OpenSpec 如何作为“人机通用语言”,贯穿架构设计、系统实现、测试验证与迭代演进的每一个环节,确保 AI 生成的代码可控、可信、可维护。
用户输入:
/opsx:propose“构建一个小型电商网站 MVP,包含商品、购物车、订单、支付核心能力。”
AI 思考与动作:
在此阶段,AI 不急于编写具体代码,而是首先进行 领域建模 与 规格定义。这是 OpenSpec 方法论的核心——先想清楚,再动手。
openspec/changes/v1-mvp/ 下生成了 proposal.md、design.md、specs/ 及 tasks.md,明确了领域边界、SLO 指标和 API 契约,具体包括:
POST /api/orders)、错误码规范(OUT_OF_STOCK)及非功能指标(p99 < 100ms)。价值分析:
用户输入:
/opsx:apply“请根据规范实现代码。”
AI 动作:
基于已确定的 Spec,AI 生成了 examples/ecommerce-mini 下的完整代码结构。
价值分析:
用户输入: (AI 主动动作) 验证生成的代码是否符合预期。
AI 动作:
AI 不仅仅生成功能代码,还生成了配套的测试脚本来验证代码行为符合预期。
价值分析:
用户输入:
/opsx:propose“将此示例拓展为生产级实现(持久化、鉴权、幂等与观测)…”
AI 动作:
这是 AI 协同开发中最精彩的部分——增量演进。AI 并没有推翻重写,而是基于现有的 Spec 架构进行扩展。
Bearer Token 鉴权中间件(简化实现;完整 HMAC 签名逻辑可在此处扩展)。Idempotency-Key 请求头解析入口(stub,完整去重逻辑可接入 Redis 或内存缓存实现)。价值分析:
通过上述案例,我们可以总结出 OpenSpec 在 AI 软件工程中的三个关键角色:
在长对话或跨会话开发中,AI 容易丢失上下文。OpenSpec 的文档体系充当了 外部存储器:
openspec/config.yaml(v1.0.0 起):项目级持久上下文——技术栈、架构约束、规则等信息会被自动注入到每一次 AI 规划请求中,AI 无需每次重新输入项目背景。例如,本项目的 config.yaml 中声明了:
context: |
Project: ecommerce-mini - A minimal e-commerce system demonstrating OpenSpec Spec-Driven Development.
Architecture: Layered (HTTP -> Service -> Domain -> Repository), single-process monolith.
Storage: In-memory Map (dev), file-based JSON persistence (prod, Node.js only).
rules:
specs:
- Use Given/When/Then (Gherkin) format for all Scenarios
- Every Requirement must include Priority (P0/P1/P2) and Rationale
当 AI 执行 /opsx:apply 时,这些信息会被自动注入,确保生成的代码符合预设约束。
变更文档(Proposal/Design/Spec):单个变更的意图、技术方案与行为定义。当用户要求“添加持久化”时,AI 不需要重新分析“什么是订单”,而是直接引用已有的 Spec 进行扩展。
AI 生成代码往往具有随机性。OpenSpec 定义的接口契约(Schema)约束了 AI 的输出空间。在案例中,无论后端实现如何变化(内存 vs 文件),HTTP 接口的 JSON 结构始终保持一致,保证了客户端的兼容性。
OpenSpec 的核心价值之一是 语言无关性 (Language Agnostic)。为了验证这一点,我们记录了一次完整的实验:使用与 Node.js 版本完全相同的 Spec 文件,驱动 AI 从零生成一套全新的 Python 实现(基于 FastAPI + Pydantic)。
ecommerce-mini 的核心功能。openspec/ 目录下的 Markdown 定义。交互意图: 基于 domain-model/spec.md 生成 Python 数据类,确保类型定义与 Spec 一致。
User Prompt:
请读取 domain-model/spec.md。 请基于此 Spec,使用 Python 的 Pydantic 库定义 Domain Models。 要求:
- 文件路径:src/domain/models.py
- 严格遵循 Spec 中的字段类型和约束(如 non-negative)。
- 不包含任何业务逻辑,仅定义数据结构。
AI Response (代码片段):
# src/domain/models.py
from pydantic import BaseModel, Field
from typing import List, Literal
class Product(BaseModel):
id: str
name: str
# 对应 Spec: Requirement "商品实体定义"
# 使用 Field(..., ge=0) 确保非负约束
price_cents: int = Field(..., ge=0, alias="priceCents")
stock: int = Field(..., ge=0)
class CartItem(BaseModel):
id: str
product_id: str = Field(..., alias="productId")
# 对应 Spec: Requirement "购物车数量限制" - quantity <= 99
quantity: int = Field(..., gt=0, le=99)
class OrderItem(BaseModel):
product_id: str = Field(..., alias="productId")
# 对应 Spec: Requirement "订单条目定义" - 记录下单时的商品单价与数量
price_cents: int = Field(..., alias="priceCents")
quantity: int
class Order(BaseModel):
id: str
# 对应 Spec: Requirement "订单实体定义" - status 只能是 PENDING_PAYMENT 或 PAID
status: Literal["PENDING_PAYMENT", "PAID"]
total_cents: int = Field(..., ge=0, alias="totalCents")
items: List[OrderItem]
注:通过 alias 实现了 Python 命名规范(snake_case)与 API 契约(camelCase)的解耦,确保内外一致性。
交互意图: 实现核心业务规则,如库存扣减和订单创建。
User Prompt:
请基于 src/domain/models.py 和 design.md,实现 Service 层。 包含三个服务:
CatalogService: 处理库存扣减(原子性模拟)。CartService: 处理购物车增删。OrderService: 编排下单流程(检查购物车 -> 扣库存 -> 生成订单 -> 清空购物车)。 需实现一个简单的MemoryRepo用于数据存储。
AI Response (代码片段):
# src/services/order.py
class OrderService:
def create_order(self, user_id: str) -> Order:
# 1. 获取购物车
cart = self.cart_svc.get_cart(user_id)
if not cart.items:
raise ValueError("CART_EMPTY")
order_items = []
total_cents = 0
# 2. 验证并扣减库存 (Stock Check Rule)
for item in cart.items:
product = self.catalog.get_product(item.product_id)
if product.stock < item.quantity:
raise ValueError("OUT_OF_STOCK")
# 执行扣减
self.catalog.deduct_stock(product.id, item.quantity)
# 构建订单项
order_items.append(OrderItem(
productId=product.id,
priceCents=product.price_cents,
quantity=item.quantity
))
total_cents += product.price_cents * item.quantity
# 3. 生成订单与清空购物车
order = Order(
id=f"order_{uuid.uuid4().hex[:8]}",
status="PENDING_PAYMENT",
totalCents=total_cents,
items=order_items
)
self.repo.save(order.id, order)
self.cart_svc.clear_cart(user_id)
return order
交互意图: 将业务逻辑暴露为 RESTful API,并处理错误码映射。
User Prompt:
请基于
src/services/和specs/catalog-management/spec.md、specs/order-management/spec.md等能力规范,使用 FastAPI 实现 Web 接口。 要求:
- 映射所有 Spec 定义的路由。
- 处理错误码映射(如库存不足返回 409)。
- 在启动时初始化测试数据。
AI Response (代码片段):
# src/api/server.py
@app.post("/api/orders", status_code=201)
def create_order(req: CreateOrderRequest):
try:
order = order_svc.create_order(req.userId)
return order
except ValueError as e:
# Spec 要求: 通过异常消息字符串区分错误类型
if str(e) == "OUT_OF_STOCK":
# Spec 要求: 库存不足返回 409 Conflict
raise HTTPException(status_code=409, detail="Out of stock")
# Spec 要求: 购物车为空返回 400 Bad Request
raise HTTPException(status_code=400, detail=str(e))
注:此处为示例简洁采用字符串比较;生产环境建议定义 OutOfStockError 等自定义异常类,以获得更清晰的错误语义与可维护性。
交互意图: 编写自动化测试,验证实现是否符合 Spec 定义的行为。
User Prompt:
请编写 tests/test_smoke.py,使用
pytest模拟用户行为。 测试场景:
- 正常下单流程:加购 -> 下单 -> 验库存。
- 异常场景:库存不足时下单,预期返回 409。
AI Response (代码片段):
# tests/test_smoke.py
def test_out_of_stock():
user_id = "user_2"
# Add product with stock of 5
res = client.post("/api/products", json={
"name": "Limited Item",
"priceCents": 200,
"stock": 5
})
pid = res.json()["id"]
# 尝试购买 6 个 (库存仅 5 个)
client.post("/api/cart/items", json={
"userId": user_id,
"productId": pid,
"quantity": 6
})
# 验证是否返回 409
# 这证明了系统正确处理了业务规则边界
resp = client.post("/api/orders", json={"userId": user_id})
assert resp.status_code == 409
assert "out of stock" in resp.json()["detail"].lower()
执行结果:
$ pytest examples/ecommerce-mini-python/tests/test_smoke.py
...
examples/ecommerce-mini-python/tests/test_smoke.py .. [100%]
==================== 2 passed in 0.35s ====================
这证实了 Python 实现完全符合 Spec 的行为预期。
本案例展示了基于 OpenSpec 的 AI 开发并非简单的“提示词工程”,而是一套严谨的 工程方法论。它通过:
最终实现了从“玩具 Demo”到“生产级系统”的平滑演进。在未来的软件开发中,掌握这种 Spec-Driven AI Collaboration 模式,将是每一位工程师的核心竞争力。
快速导航:想了解 CLI 命令细节?→ OpenSpec 使用手册 想了解规范如何落地为代码?→ 实战指南 想复盘 AI 协作过程?→ 本文档
examples/openspec/config.yaml(技术栈、架构约束与规则,自动注入每次 AI 规划请求)examples/openspec/changes/v1-mvp/
proposal.md: 变更提案design.md: 架构设计specs/catalog-management/spec.md: 商品目录管理规范specs/cart-management/spec.md: 购物车管理规范specs/order-management/spec.md: 订单管理规范specs/payment/spec.md: 支付规范specs/domain-model/spec.md: 领域模型规范specs/error-handling/spec.md: 错误处理规范examples/ecommerce-mini/src/{domain,repo,services,http}examples/ecommerce-mini-python/src/{domain,services,api}examples/ecommerce-mini/__tests__/ 及 examples/ecommerce-mini-python/tests/