|
|
@@ -0,0 +1,531 @@
|
|
|
+# Story 1.5: 创建主导出和基础文档
|
|
|
+
|
|
|
+Status: ready-for-dev
|
|
|
+
|
|
|
+<!-- Note: Validation is optional. Run validate-create-story for quality check before dev-story. -->
|
|
|
+
|
|
|
+## Story
|
|
|
+
|
|
|
+作为测试开发者,
|
|
|
+我想要可以导入工具函数并查看快速入门文档,
|
|
|
+以便快速开始使用工具包。
|
|
|
+
|
|
|
+## Acceptance Criteria
|
|
|
+
|
|
|
+**Given** Select 工具函数已实现(Story 1.3、1.4 完成)
|
|
|
+**When** 创建/更新 `src/index.ts` 和 `README.md`
|
|
|
+**Then** `index.ts` 导出所有公共函数和类型(tree-shakeable)
|
|
|
+**And** README 包含:安装说明、快速入门、Select 使用示例
|
|
|
+**And** README 说明静态 Select 和异步 Select 的区别和使用场景
|
|
|
+**And** 所有导出函数有完整的 JSDoc 注释(已在 Story 1.3、1.4 完成)
|
|
|
+**And** 可以 `import { selectRadixOption } from '@d8d/e2e-test-utils'`
|
|
|
+
|
|
|
+## Tasks / Subtasks
|
|
|
+
|
|
|
+- [ ] 审查 `src/index.ts` 导出结构 (AC: 1)
|
|
|
+ - [ ] 确认使用显式导出(而非通配符)支持 tree-shaking
|
|
|
+ - [ ] 确认导出所有公共类型和函数
|
|
|
+ - [ ] 确认导出顺序合理(类型、错误、常量、工具函数)
|
|
|
+- [ ] 更新 `README.md` 添加 Select 工具使用文档 (AC: 2, 3, 4)
|
|
|
+ - [ ] 在 API 文档章节添加 `selectRadixOption` 完整说明
|
|
|
+ - [ ] 在 API 文档章节添加 `selectRadixOptionAsync` 完整说明
|
|
|
+ - [ ] 添加静态 Select vs 异步 Select 对比说明
|
|
|
+ - [ ] 添加快速入门示例代码
|
|
|
+- [ ] 验证导入语句可用性 (AC: 5)
|
|
|
+ - [ ] 验证 `import { selectRadixOption } from '@d8d/e2e-test-utils'` 可用
|
|
|
+ - [ ] 验证类型提示正常工作
|
|
|
+
|
|
|
+## Dev Notes
|
|
|
+
|
|
|
+### Epic 1 背景
|
|
|
+
|
|
|
+**Epic 1 目标:** 测试开发者可以安装 `@d8d/e2e-test-utils` 包,立即使用 Select 工具测试 Radix UI Select 组件。
|
|
|
+
|
|
|
+**本故事在 Epic 中的位置:** 第五个故事,完成主导出文档和 README,使工具包可以被外部项目使用和理解。
|
|
|
+
|
|
|
+### 当前包状态分析
|
|
|
+
|
|
|
+**已完成的工作(Story 1.1-1.4):**
|
|
|
+
|
|
|
+1. **Story 1.1 - 包基础结构**
|
|
|
+ - ✅ `package.json` 配置(peer dependencies: @playwright/test)
|
|
|
+ - ✅ `tsconfig.json` 严格模式配置
|
|
|
+ - ✅ `vitest.config.ts` 测试配置
|
|
|
+
|
|
|
+2. **Story 1.2 - 类型定义和错误处理**
|
|
|
+ - ✅ `src/types.ts` - BaseOptions, AsyncSelectOptions, ErrorContext
|
|
|
+ - ✅ `src/errors.ts` - E2ETestError 类
|
|
|
+ - ✅ `src/constants.ts` - DEFAULT_TIMEOUTS, SELECTOR_STRATEGIES
|
|
|
+
|
|
|
+3. **Story 1.3 - 静态 Select 工具**
|
|
|
+ - ✅ `selectRadixOption(page, label, value)` 函数
|
|
|
+ - ✅ 完整 JSDoc 注释
|
|
|
+ - ✅ 三层选择器策略(testid → ARIA → text)
|
|
|
+
|
|
|
+4. **Story 1.4 - 异步 Select 工具**
|
|
|
+ - ✅ `selectRadixOptionAsync(page, label, value, options?)` 函数
|
|
|
+ - ✅ 完整 JSDoc 注释
|
|
|
+ - ✅ 网络空闲等待 + 重试机制
|
|
|
+
|
|
|
+**当前 `src/index.ts` 状态:**
|
|
|
+```typescript
|
|
|
+// 当前使用显式导出(正确,支持 tree-shaking)
|
|
|
+export {
|
|
|
+ selectRadixOption,
|
|
|
+ selectRadixOptionAsync
|
|
|
+} from './radix-select';
|
|
|
+
|
|
|
+// 通配符导出类型(也正确)
|
|
|
+export * from './types';
|
|
|
+export * from './errors';
|
|
|
+export * from './constants';
|
|
|
+```
|
|
|
+
|
|
|
+**当前 `README.md` 状态:**
|
|
|
+- ✅ 已有项目简介和特性说明
|
|
|
+- ✅ 已有安装说明
|
|
|
+- ✅ 已有类型定义和错误类文档
|
|
|
+- ❌ **缺少 Select 工具函数使用示例**
|
|
|
+- ❌ **缺少静态 vs 异步 Select 区分说明**
|
|
|
+
|
|
|
+### 本故事的核心任务
|
|
|
+
|
|
|
+**任务 1:审查 index.ts 导出结构**
|
|
|
+
|
|
|
+当前导出结构已经正确:
|
|
|
+- 使用显式命名导出支持 tree-shaking
|
|
|
+- 类型使用通配符导出(可以,因为类型不增加运行时开销)
|
|
|
+- 导出顺序合理
|
|
|
+
|
|
|
+**可能需要的改进(可选):**
|
|
|
+- 如果未来工具函数增多,可以考虑为每个模块添加明确的 re-export
|
|
|
+- 保持当前的简洁性已经足够
|
|
|
+
|
|
|
+**任务 2:更新 README.md 添加 Select 工具文档**
|
|
|
+
|
|
|
+需要在 README 中添加以下内容:
|
|
|
+
|
|
|
+1. **Select 工具使用示例**(添加到"快速入门"或"API 文档"章节)
|
|
|
+2. **静态 vs 异步 Select 对比**(新增对比表格或说明)
|
|
|
+3. **实际使用场景示例**(残疾人管理测试案例)
|
|
|
+
|
|
|
+### 架构约束和模式
|
|
|
+
|
|
|
+**从架构文档中必须遵循的决策:**
|
|
|
+
|
|
|
+**文档结构需求(Architecture - Documentation Requirements):**
|
|
|
+- README 必须包含:项目简介、安装说明、快速入门、API 文档
|
|
|
+- 每个工具函数至少有 1 个实际使用示例
|
|
|
+- 文档说明静态 Select 和异步 Select 的区别和使用场景
|
|
|
+- 新测试开发者可以在 30 分钟内使用工具函数编写第一个测试(NFR37)
|
|
|
+
|
|
|
+**Tree-shaking 需求(Architecture - Bundle Optimization):**
|
|
|
+- 主导出使用命名导出(named exports),不使用默认导出
|
|
|
+- 避免导出整个模块,而是明确指定导出的函数和类型
|
|
|
+- 类型定义可以安全使用通配符导出(不增加运行时开销)
|
|
|
+
|
|
|
+**API 文档标准(Architecture - API Documentation):**
|
|
|
+- 所有公共 API 必须有 JSDoc 注释(已在 Story 1.3、1.4 完成)
|
|
|
+- README 中的示例应与 JSDoc 中的 @example 保持一致
|
|
|
+- 参数说明使用表格或列表格式,清晰展示每个参数的类型和用途
|
|
|
+
|
|
|
+### 技术实现要求
|
|
|
+
|
|
|
+**`src/index.ts` 审查指南:**
|
|
|
+
|
|
|
+**当前导出结构(已正确):**
|
|
|
+```typescript
|
|
|
+/**
|
|
|
+ * @d8d/e2e-test-utils
|
|
|
+ *
|
|
|
+ * E2E 测试工具集 - 专门用于测试 Radix UI 组件的 Playwright 工具函数
|
|
|
+ *
|
|
|
+ * @packageDocumentation
|
|
|
+ */
|
|
|
+
|
|
|
+// 导出类型定义(通配符导出可以,类型不增加运行时开销)
|
|
|
+export * from './types';
|
|
|
+
|
|
|
+// 导出错误类(通配符导出可以)
|
|
|
+export * from './errors';
|
|
|
+
|
|
|
+// 导出常量(通配符导出可以)
|
|
|
+export * from './constants';
|
|
|
+
|
|
|
+// Radix UI Select 工具(显式导出,支持 tree-shaking)
|
|
|
+export {
|
|
|
+ selectRadixOption,
|
|
|
+ selectRadixOptionAsync
|
|
|
+} from './radix-select';
|
|
|
+```
|
|
|
+
|
|
|
+**审查清单:**
|
|
|
+- ✅ 使用显式命名导出(非默认导出)
|
|
|
+- ✅ 工具函数使用显式导出列表(而非 `export * from './radix-select'`)
|
|
|
+- ✅ 类型定义使用通配符导出(可接受,类型不增加运行时开销)
|
|
|
+- ✅ 包级 JSDoc 注释完整
|
|
|
+- ✅ 导出顺序合理(类型 → 错误 → 常量 → 工具函数)
|
|
|
+
|
|
|
+**无需修改当前结构**,除非发现以下问题:
|
|
|
+- ❌ 如果有默认导出,需要改为命名导出
|
|
|
+- ❌ 如果有 `export * from './radix-select'`,需要改为显式导出
|
|
|
+
|
|
|
+**`README.md` 创建指南:**
|
|
|
+
|
|
|
+**必须包含的章节:**
|
|
|
+
|
|
|
+1. **项目简介**(1-2 段话)
|
|
|
+ - 说明工具包的用途
|
|
|
+ - 说明支持的组件类型(Radix UI)
|
|
|
+ - 说明核心价值(简化 E2E 测试)
|
|
|
+
|
|
|
+2. **安装说明**
|
|
|
+ ```bash
|
|
|
+ # 使用 pnpm workspace 协议(Monorepo 内)
|
|
|
+ pnpm add -D @d8d/e2e-test-utils@workspace:*
|
|
|
+
|
|
|
+ # 使用 npm(发布后)
|
|
|
+ npm install --save-dev @d8d/e2e-test-utils
|
|
|
+ ```
|
|
|
+
|
|
|
+3. **快速入门**(本故事核心任务)
|
|
|
+ ```typescript
|
|
|
+ import { selectRadixOption, selectRadixOptionAsync } from '@d8d/e2e-test-utils';
|
|
|
+
|
|
|
+ // 静态 Select 示例
|
|
|
+ await selectRadixOption(page, '残疾类型', '视力残疾');
|
|
|
+
|
|
|
+ // 异步 Select 示例
|
|
|
+ await selectRadixOptionAsync(page, '省份', '广东省');
|
|
|
+ ```
|
|
|
+
|
|
|
+4. **API 文档**(本故事核心任务)
|
|
|
+ - `selectRadixOption` - 静态 Select 工具
|
|
|
+ - `selectRadixOptionAsync` - 异步 Select 工具
|
|
|
+ - 参数表格说明
|
|
|
+ - 使用示例
|
|
|
+
|
|
|
+5. **静态 vs 异步 Select**(本故事核心任务)
|
|
|
+ - 区别对比表格
|
|
|
+ - 使用场景说明
|
|
|
+ - 选择建议
|
|
|
+
|
|
|
+6. **类型定义**(已存在,保持)
|
|
|
+7. **错误处理**(已存在,保持)
|
|
|
+8. **常量**(已存在,保持)
|
|
|
+
|
|
|
+### 与前一个故事的集成
|
|
|
+
|
|
|
+**Story 1.4 已完成的工作:**
|
|
|
+- ✅ 静态 Select 函数 `selectRadixOption()` 已实现并导出
|
|
|
+- ✅ 异步 Select 函数 `selectRadixOptionAsync()` 已实现并导出
|
|
|
+- ✅ 所有导出函数有完整的 JSDoc 注释
|
|
|
+- ✅ 类型定义完整(BaseOptions, AsyncSelectOptions)
|
|
|
+
|
|
|
+**本故事需要做的:**
|
|
|
+- 审查并确认 `src/index.ts` 导出结构正确(可能无需修改)
|
|
|
+- 创建 `README.md` 添加 Select 工具使用文档和示例
|
|
|
+- 区分静态 Select 和异步 Select 的使用场景
|
|
|
+
|
|
|
+### 前一个故事的关键经验
|
|
|
+
|
|
|
+**从 Story 1.3、1.4 中学习到的经验:**
|
|
|
+
|
|
|
+1. **JSDoc 注释标准:**
|
|
|
+ - 使用 `@description` 标签添加详细描述
|
|
|
+ - 使用 `@param` 标签说明每个参数
|
|
|
+ - 使用 `@throws` 标签说明可能抛出的错误
|
|
|
+ - 使用 `@example` 标签提供实际使用示例
|
|
|
+
|
|
|
+2. **错误处理模式:**
|
|
|
+ - 使用 `E2ETestError` 类提供结构化错误信息
|
|
|
+ - 错误消息包含:操作类型、目标、期望值、可用选项、修复建议
|
|
|
+
|
|
|
+3. **选择器策略:**
|
|
|
+ - 优先级:`data-testid` → `aria-label` + `role` → `text content`
|
|
|
+ - 推荐在 Radix 组件上添加 `data-testid` 属性
|
|
|
+
|
|
|
+### 静态 Select vs 异步 Select
|
|
|
+
|
|
|
+| 特性 | 静态 Select (`selectRadixOption`) | 异步 Select (`selectRadixOptionAsync`) |
|
|
|
+|------|----------------------------------|----------------------------------------|
|
|
|
+| **选项加载时机** | 页面加载时已存在 DOM 中 | 点击触发器后 API 加载 |
|
|
|
+| **使用场景** | 枚举类型(残疾类型、性别等) | 动态数据(省份、城市、银行等) |
|
|
|
+| **等待策略** | 立即查找选项 | 等待网络请求 + 选项出现 |
|
|
|
+| **默认超时** | 2000ms | 5000ms |
|
|
|
+| **配置对象** | 无 | `AsyncSelectOptions` |
|
|
|
+| **网络空闲等待** | 不需要 | 默认启用 |
|
|
|
+| **函数签名** | `selectRadixOption(page, label, value)` | `selectRadixOptionAsync(page, label, value, options?)` |
|
|
|
+
|
|
|
+**选择建议:**
|
|
|
+- 如果下拉框选项在页面加载时已存在 → 使用 `selectRadixOption()`
|
|
|
+- 如果下拉框选项需要从 API 动态加载 → 使用 `selectRadixOptionAsync()`
|
|
|
+- 不确定时,可以使用异步版本(会有额外等待,但更稳定)
|
|
|
+
|
|
|
+### README 模板参考
|
|
|
+
|
|
|
+**快速入门章节建议内容:**
|
|
|
+
|
|
|
+```markdown
|
|
|
+## 快速入门
|
|
|
+
|
|
|
+### 安装
|
|
|
+
|
|
|
+\`\`\`bash
|
|
|
+# Monorepo 内使用 workspace 协议
|
|
|
+pnpm add -D @d8d/e2e-test-utils@workspace:*
|
|
|
+
|
|
|
+# 或使用 npm(发布后)
|
|
|
+npm install --save-dev @d8d/e2e-test-utils
|
|
|
+\`\`\`
|
|
|
+
|
|
|
+### 基本使用
|
|
|
+
|
|
|
+\`\`\`typescript
|
|
|
+import { selectRadixOption, selectRadixOptionAsync } from '@d8d/e2e-test-utils';
|
|
|
+
|
|
|
+// 选择静态下拉框选项(如残疾类型)
|
|
|
+await selectRadixOption(page, '残疾类型', '视力残疾');
|
|
|
+
|
|
|
+// 选择异步加载的下拉框选项(如省份)
|
|
|
+await selectRadixOptionAsync(page, '省份', '广东省');
|
|
|
+\`\`\`
|
|
|
+
|
|
|
+### 选择器策略
|
|
|
+
|
|
|
+工具函数按以下优先级查找下拉框触发器:
|
|
|
+1. `data-testid="标签-trigger"` - 推荐,最稳定
|
|
|
+2. `aria-label="标签"` + `role="combobox"` - 无障碍属性
|
|
|
+3. `text="标签"` - 文本匹配(兜底)
|
|
|
+
|
|
|
+**推荐做法:** 在测试代码或应用中为 Radix Select 添加 `data-testid` 属性。
|
|
|
+```
|
|
|
+
|
|
|
+**API 文档章节建议内容:**
|
|
|
+
|
|
|
+```markdown
|
|
|
+## API 文档
|
|
|
+
|
|
|
+### selectRadixOption()
|
|
|
+
|
|
|
+选择静态枚举型 Radix UI Select 选项。
|
|
|
+
|
|
|
+**函数签名:**
|
|
|
+\`\`\`typescript
|
|
|
+function selectRadixOption(
|
|
|
+ page: Page,
|
|
|
+ label: string,
|
|
|
+ value: string
|
|
|
+): Promise<void>
|
|
|
+\`\`\`
|
|
|
+
|
|
|
+**参数:**
|
|
|
+| 参数 | 类型 | 说明 |
|
|
|
+|------|------|------|
|
|
|
+| `page` | `Page` | Playwright Page 对象 |
|
|
|
+| `label` | `string` | 下拉框的标签文本 |
|
|
|
+| `value` | `string` | 要选择的选项值 |
|
|
|
+
|
|
|
+**示例:**
|
|
|
+\`\`\`typescript
|
|
|
+// 选择残疾类型
|
|
|
+await selectRadixOption(page, '残疾类型', '视力残疾');
|
|
|
+
|
|
|
+// 选择性别
|
|
|
+await selectRadixOption(page, '性别', '男');
|
|
|
+\`\`\`
|
|
|
+
|
|
|
+---
|
|
|
+
|
|
|
+### selectRadixOptionAsync()
|
|
|
+
|
|
|
+选择异步加载的 Radix UI Select 选项。
|
|
|
+
|
|
|
+**函数签名:**
|
|
|
+\`\`\`typescript
|
|
|
+function selectRadixOptionAsync(
|
|
|
+ page: Page,
|
|
|
+ label: string,
|
|
|
+ value: string,
|
|
|
+ options?: AsyncSelectOptions
|
|
|
+): Promise<void>
|
|
|
+\`\`\`
|
|
|
+
|
|
|
+**参数:**
|
|
|
+| 参数 | 类型 | 说明 |
|
|
|
+|------|------|------|
|
|
|
+| `page` | `Page` | Playwright Page 对象 |
|
|
|
+| `label` | `string` | 下拉框的标签文本 |
|
|
|
+| `value` | `string` | 要选择的选项值 |
|
|
|
+| `options` | `AsyncSelectOptions` | 可选配置对象 |
|
|
|
+| `options.timeout` | `number` | 超时时间(毫秒),默认 5000 |
|
|
|
+| `options.waitForOption` | `boolean` | 是否等待选项加载,默认 true |
|
|
|
+| `options.waitForNetworkIdle` | `boolean` | 是否等待网络空闲,默认 true |
|
|
|
+
|
|
|
+**示例:**
|
|
|
+\`\`\`typescript
|
|
|
+// 选择省份(使用默认配置)
|
|
|
+await selectRadixOptionAsync(page, '省份', '广东省');
|
|
|
+
|
|
|
+// 选择城市(自定义超时)
|
|
|
+await selectRadixOptionAsync(page, '城市', '深圳市', {
|
|
|
+ timeout: 10000
|
|
|
+});
|
|
|
+
|
|
|
+// 禁用网络空闲等待(网络不稳定时)
|
|
|
+await selectRadixOptionAsync(page, '地区', '华南', {
|
|
|
+ waitForNetworkIdle: false
|
|
|
+});
|
|
|
+\`\`\`
|
|
|
+```
|
|
|
+
|
|
|
+### 项目标准对齐
|
|
|
+
|
|
|
+**与项目标准对齐:**
|
|
|
+- 遵循 `docs/standards/testing-standards.md` 中的测试规范
|
|
|
+- 遵循 `docs/standards/e2e-radix-testing.md` 中的 Radix UI E2E 测试标准
|
|
|
+- 遵循 `docs/standards/coding-standards.md` 中的编码标准
|
|
|
+
|
|
|
+**文档标准:**
|
|
|
+- README 使用 Markdown 格式
|
|
|
+- 代码示例使用 TypeScript 语法高亮
|
|
|
+- 参数说明使用表格格式
|
|
|
+- 添加实际可运行的示例代码
|
|
|
+
|
|
|
+**TypeScript 配置:**
|
|
|
+- 严格模式已启用(`strict: true`)
|
|
|
+- 所有类型定义支持 IDE 自动补全
|
|
|
+- 导入语句支持类型推导
|
|
|
+
|
|
|
+### 性能约束
|
|
|
+
|
|
|
+**从 NFR 提取的性能要求:**
|
|
|
+- **NFR37**: 新测试开发者可以在 30 分钟内使用工具函数编写第一个测试
|
|
|
+- **NFR39**: 函数命名清晰直观,不需要频繁查看文档
|
|
|
+- **NFR40**: 错误消息对新手友好,包含问题诊断和建议修复步骤
|
|
|
+
|
|
|
+**README 设计考虑:**
|
|
|
+- 提供简洁的快速入门章节(5 分钟内理解)
|
|
|
+- 提供完整的 API 参考文档
|
|
|
+- 提供静态 vs 异步 Select 对比说明
|
|
|
+- 提供实际使用场景示例
|
|
|
+
|
|
|
+### 文件结构约束
|
|
|
+
|
|
|
+**必须遵循的文件结构:**
|
|
|
+```
|
|
|
+packages/e2e-test-utils/
|
|
|
+├── src/
|
|
|
+│ ├── index.ts # 主导出(审查,可能无需修改)
|
|
|
+│ ├── types.ts # 共享类型定义
|
|
|
+│ ├── errors.ts # 错误类
|
|
|
+│ ├── constants.ts # 常量定义
|
|
|
+│ └── radix-select.ts # Radix UI Select 工具
|
|
|
+├── README.md # 包文档(本故事创建)
|
|
|
+├── package.json # 包配置
|
|
|
+├── tsconfig.json # TypeScript 配置
|
|
|
+└── vitest.config.ts # 测试配置
|
|
|
+```
|
|
|
+
|
|
|
+**禁止事项(Anti-Patterns):**
|
|
|
+- ❌ 使用默认导出(`export default`)
|
|
|
+- ❌ 在 README 中使用不准确的示例代码
|
|
|
+- ❌ 缺少静态 vs 异步 Select 的区分说明
|
|
|
+- ❌ 示例代码与实际 API 不匹配
|
|
|
+
|
|
|
+### 测试要求
|
|
|
+
|
|
|
+**文档验证方法:**
|
|
|
+- 手动验证 README 中的示例代码可以正确运行
|
|
|
+- 验证导入语句 `import { selectRadixOption } from '@d8d/e2e-test-utils'` 可用
|
|
|
+- 验证类型提示在 IDE 中正常工作
|
|
|
+- 验证快速入门章节可在 30 分钟内完成(NFR37)
|
|
|
+
|
|
|
+**集成测试(在 Epic 3 中实现):**
|
|
|
+- 本故事创建的文档将在 Epic 3 中通过实际 E2E 测试验证
|
|
|
+- 残疾人管理测试将作为完整的使用示例
|
|
|
+
|
|
|
+### Project Structure Notes
|
|
|
+
|
|
|
+**对齐项目 Monorepo 架构:**
|
|
|
+- 包位于 `packages/e2e-test-utils/`
|
|
|
+- 使用 workspace 协议安装:`@d8d/e2e-test-utils@workspace:*`
|
|
|
+- 与现有 `@d8d/shared-test-util`(后端集成测试)分离
|
|
|
+
|
|
|
+**与项目标准对齐:**
|
|
|
+- 遵循 `docs/standards/testing-standards.md` 中的测试规范
|
|
|
+- 遵循 `docs/standards/web-ui-testing-standards.md` 中的 Web UI 测试规范
|
|
|
+- 遵循 `docs/standards/e2e-radix-testing.md` 中的 Radix UI E2E 测试标准(核心标准文档)
|
|
|
+
|
|
|
+### References
|
|
|
+
|
|
|
+**PRD 来源:**
|
|
|
+- [PRD - E2E测试工具包](_bmad-output/planning-artifacts/prd.md) - 项目需求概述
|
|
|
+- [PRD - 文档和开发者支持](_bmad-output/planning-artifacts/epics.md#文档和开发者支持-fr33-fr40) - FR33-FR40 需求
|
|
|
+
|
|
|
+**Architecture 来源:**
|
|
|
+- [Architecture - 文档需求](_bmad-output/planning-artifacts/architecture.md#documentation-requirements) - README 和 JSDoc 要求
|
|
|
+- [Architecture - 包结构需求](_bmad-output/planning-artifacts/architecture.md#package-structure-requirements) - 导出规范
|
|
|
+
|
|
|
+**标准文档来源:**
|
|
|
+- [E2E Radix UI 测试标准](docs/standards/e2e-radix-testing.md) - 核心测试标准文档
|
|
|
+- [Project Context](_bmad-output/project-context.md) - 项目技术栈和规则
|
|
|
+
|
|
|
+**Epic 来源:**
|
|
|
+- [Epic 1 - Story 1.5](_bmad-output/planning-artifacts/epics.md#story-15-创建主导出和基础文档) - 原始用户故事和验收标准
|
|
|
+
|
|
|
+**前一个故事:**
|
|
|
+- [Story 1.1 - 创建包基础结构和配置](_bmad-output/implementation-artifacts/1-1-create-package-structure.md) - 包基础设施
|
|
|
+- [Story 1.2 - 实现类型定义和错误处理](_bmad-output/implementation-artifacts/1-2-implement-types-errors.md) - 类型、错误、常量
|
|
|
+- [Story 1.3 - 实现静态 Select 工具函数](_bmad-output/implementation-artifacts/1-3-static-select-tool.md) - 静态 Select 函数
|
|
|
+- [Story 1.4 - 实现异步 Select 工具函数](_bmad-output/implementation-artifacts/1-4-async-select-tool.md) - 异步 Select 函数
|
|
|
+
|
|
|
+## Dev Agent Record
|
|
|
+
|
|
|
+### Agent Model Used
|
|
|
+
|
|
|
+Claude (d8d-model) via create-story workflow
|
|
|
+
|
|
|
+### Debug Log References
|
|
|
+
|
|
|
+### Completion Notes List
|
|
|
+
|
|
|
+- 故事创建时间: 2026-01-09
|
|
|
+- 基于 PRD、Architecture、E2E Radix 测试标准文档创建
|
|
|
+- 基于 Story 1.3、1.4 的实现状态创建
|
|
|
+- 包含完整的 README 创建指南和模板
|
|
|
+- 区分静态和异步 Select 的使用场景
|
|
|
+- 包含 tree-shaking 导出最佳实践
|
|
|
+
|
|
|
+**实现建议:**
|
|
|
+- `src/index.ts` 当前结构已经正确,可能无需修改
|
|
|
+- 主要任务是创建 `README.md` 添加 Select 工具使用文档
|
|
|
+- README 应包含:安装说明、快速入门、API 文档、静态 vs 异步 Select 对比
|
|
|
+- 确保示例代码与实际 API 一致
|
|
|
+- 确保文档简洁清晰,新开发者可在 30 分钟内上手
|
|
|
+
|
|
|
+**关键检查点:**
|
|
|
+- ✅ `src/index.ts` 使用显式命名导出(支持 tree-shaking)
|
|
|
+- ✅ 所有 Select 函数有完整 JSDoc(已在 Story 1.3、1.4 完成)
|
|
|
+- ❌ README.md 需要创建 Select 工具使用文档
|
|
|
+- ❌ README.md 需要添加静态 vs 异步 Select 对比说明
|
|
|
+
|
|
|
+### File List
|
|
|
+
|
|
|
+**本故事可能修改的文件:**
|
|
|
+- `packages/e2e-test-utils/src/index.ts` - 审查导出结构(可能无需修改)
|
|
|
+- `packages/e2e-test-utils/README.md` - 创建 Select 工具使用文档(主要任务)
|
|
|
+
|
|
|
+**相关文件(已在 Story 1.1-1.4 中完成,本故事使用):**
|
|
|
+- `packages/e2e-test-utils/src/radix-select.ts` - Select 工具函数实现
|
|
|
+- `packages/e2e-test-utils/src/types.ts` - 类型定义
|
|
|
+- `packages/e2e-test-utils/src/errors.ts` - 错误类
|
|
|
+- `packages/e2e-test-utils/src/constants.ts` - 常量定义
|
|
|
+
|
|
|
+**只读参考文件:**
|
|
|
+- `_bmad-output/implementation-artifacts/1-3-static-select-tool.md` - 静态 Select 实现
|
|
|
+- `_bmad-output/implementation-artifacts/1-4-async-select-tool.md` - 异步 Select 实现
|
|
|
+- `_bmad-output/planning-artifacts/epics.md` - Epic 和故事定义
|
|
|
+- `_bmad-output/planning-artifacts/architecture.md` - 架构决策和模式
|
|
|
+- `docs/standards/e2e-radix-testing.md` - E2E Radix UI 测试标准
|
|
|
+
|