e2e
This slash command invokes the e2e-runner agent to generate, maintain, and execute end-to-end tests using Playwright across multiple browsers. Use it to create and run automated test journeys for critical user flows, capture failure artifacts like screenshots and video traces, and generate HTML reports to verify application functionality before production deployment.
mkdir -p ~/.claude/commands && curl -fsSL https://raw.githubusercontent.com/xu-xiang/everything-claude-code-zh/HEAD/commands/e2e.md -o ~/.claude/commands/e2e.mde2e.md
# E2E 命令
此命令调用 **e2e-runner** 智能体(Agent)来使用 Playwright 生成、维护和执行端到端测试(End-to-End Tests/E2E)。
## 此命令的作用
1. **生成测试旅程(Test Journeys)** - 为用户流创建 Playwright 测试
2. **运行 E2E 测试** - 在不同浏览器上执行测试
3. **捕获产物(Artifacts)** - 在失败时捕获截图、视频和追踪(Traces)
4. **上传结果** - 生成 HTML 报告和 JUnit XML
5. **识别不稳定测试(Flaky Tests)** - 隔离不稳定的测试
## 何时使用
在以下场景使用 `/e2e`:
- 测试关键用户旅程(登录、交易、支付)
- 验证多步骤流程的端到端运行情况
- 测试 UI 交互和导航
- 验证前端与后端之间的集成
- 为生产环境部署做准备
## 工作原理
e2e-runner 智能体将执行以下操作:
1. **分析用户流**并识别测试场景
2. 使用页面对象模型(Page Object Model/POM)模式**生成 Playwright 测试**
3. 在多个浏览器(Chrome、Firefox、Safari)上**运行测试**
4. 通过截图、视频和追踪**捕获失败信息**
5. **生成报告**,包含结果和产物
6. **识别不稳定测试**并推荐修复方案
## 使用示例
```
用户:/e2e 测试市场搜索和查看流程
智能体 (e2e-runner):
# E2E 测试生成:市场搜索和查看流程
## 识别出的测试场景
**用户旅程:** 市场搜索 → 查看结果 → 点击市场 → 查看详情
**测试覆盖范围:**
1. 导航到市场页面
2. 执行语义搜索
3. 验证搜索结果
4. 点击第一个结果
5. 验证市场详情页面加载
6. 验证图表渲染
## 生成的测试代码
```typescript
// tests/e2e/markets/search-and-view.spec.ts
import { test, expect } from '@playwright/test'
import { MarketsPage } from '../../pages/MarketsPage'
import { MarketDetailsPage } from '../../pages/MarketDetailsPage'
test.describe('Market Search and View Flow', () => {
test('user can search markets and view details', async ({ page }) => {
// 1. 导航到市场页面
const marketsPage = new MarketsPage(page)
await marketsPage.goto()
// 验证页面加载
await expect(page).toHaveTitle(/Markets/)
await expect(page.locator('h1')).toContainText('Markets')
// 2. 执行语义搜索
await marketsPage.searchMarkets('election')
// 等待 API 响应
await page.waitForResponse(resp =>
resp.url().includes('/api/markets/search') && resp.status() === 200
)
// 3. 验证搜索结果
const marketCards = marketsPage.marketCards
await expect(marketCards.first()).toBeVisible()
const resultCount = await marketCards.count()
expect(resultCount).toBeGreaterThan(0)
// 截取搜索结果截图
await page.screenshot({ path: 'artifacts/search-results.png' })
// 4. 点击第一个结果
const firstMarketTitle = await marketCards.first().textContent()
await marketCards.first().click()
// 5. 验证市场详情页面加载
await expect(page).toHaveURL(/\/markets\/[a-z0-9-]+/)
const detailsPage = new MarketDetailsPage(page)
await expect(detailsPage.marketName).toBeVisible()
await expect(detailsPage.marketDescription).toBeVisible()
// 6. 验证图表渲染
await expect(detailsPage.priceChart).toBeVisible()
// 验证市场名称匹配
const detailsTitle = await detailsPage.marketName.textContent()
expect(detailsTitle?.toLowerCase()).toContain(
firstMarketTitle?.toLowerCase().substring(0, 20) || ''
)
// 截取市场详情截图
await page.screenshot({ path: 'artifacts/market-details.png' })
})
test('search with no results shows empty state', async ({ page }) => {
const marketsPage = new MarketsPage(page)
await marketsPage.goto()
// 搜索不存在的市场
await marketsPage.searchMarkets('xyznonexistentmarket123456')
// 验证空状态
await expect(page.locator('[data-testid="no-results"]')).toBeVisible()
await expect(page.locator('[data-testid="no-results"]')).toContainText(
/no.*results|no.*markets/i
)
const marketCount = await marketsPage.marketCards.count()
expect(marketCount).toBe(0)
})
test('can clear search and see all markets again', async ({ page }) => {
const marketsPage = new MarketsPage(page)
await marketsPage.goto()
// 初始市场数量
const initialCount = await marketsPage.marketCards.count()
// 执行搜索
await marketsPage.searchMarkets('trump')
await page.waitForLoadState('networkidle')
// 验证过滤后的结果
const filteredCount = await marketsPage.marketCards.count()
expect(filteredCount).toBeLessThan(initialCount)
// 清除搜索
await marketsPage.searchInput.clear()
await page.waitForLoadState('networkidle')
// 验证再次显示所有市场
const finalCount = await marketsPage.marketCards.count()
expect(finalCount).toBe(initialCount)
})
})
```
## 运行测试
```bash
# 运行生成的测试
npx playwright test tests/e2e/markets/search-and-view.spec.ts
Running 3 tests using 3 workers
✓ [chromium] › search-and-view.spec.ts:5:3 › user can search markets and view details (4.2s)
✓ [chromium] › search-and-view.spec.ts:52:3 › search with no results shows empty state (1.8s)
✓ [chromium] › search-and-view.spec.ts:67:3 › can clear search and see all markets again (2.9s)
3 passed (9.1s)
生成的产物:
- artifacts/search-results.png
- artifacts/market-details.png
- playwright-report/index.html
```
## 测试报告
```
╔══════════════════════════════════════════════════════════════╗
║ E2E 测试结果 ║
╠══════════════════════════════════════════════════════════════╣
║ 状态: ✅ 所有测试通过 ║
║ 总计: 3 个测试 ║
║ 通过: 3 (100%) ║
║ 失败: 0 ║
║ 不稳定: 0 ║
║ 耗时: 9.1s ║
╚══════════════════════════════════════════════════════════════╝
产物:
📸 截图: 2 个文件
📹 视频: 0 个文件 (仅在失败时生成)
🔍 追踪: 0 个文件 (仅在失败时生成)
📊 HTML 报告: playwright-report/index.html
查看报告: npx playwright show-report
```
✅ E2E 测试套件已就绪,可进行 CI/CD 集成!
```
## 测试产物(Artifacts)
测试运行时,会捕获以下产物:
**所有测试均会捕获:**
- 包含时间线和结果的 HTML 报告
- 用于 CI 集成的 JUnit XML
**仅在失败时捕获:**
- 失败状态的截图
- 测试过程的录屏视频
- 用于调试的追踪文件(单步回放)
- 网络日志
- 控制台日志
## 查看产物
```bash
# 在浏览器中查看 HTML 报告
npx playwright show-report
# 查看特定的追踪文件
npx playwright show-trace artifacts/trace-abc123.zip
# 截图保存在 artifacts/ 目录下
open artifacts/search-results.png
```
## 不稳定测试检测
如果测试间歇性失败:
```
⚠️ 检测到不稳定测试 (FLAKY TEST): tests/e2e/markets/trade.spec.ts
测试在 10 次运行中通过了 7 次 (70% 通过率)
常见失败原因:
"Timeout waiting for element '[data-testid="confirm-btn"]'"
推荐修复建议:
1. 添加显式等待: await page.waitForSelector('[data-testid="confirm-btn"]')
2. 增加超时时间: { timeout: 10000 }
3. 检查组件中的竞态条件
4. 验证元素未被动画隐藏
隔离建议: 在修复前标记为 test.fixme()
```
## 浏览器配置
测试默认在多个浏览器上运行:
- ✅ Ch生产级 API 的 REST API 设计模式,包括资源命名、状态码、分页、过滤、错误响应、版本控制和速率限制。
编写文章、指南、博客、教程、时事通讯(Newsletter)等长内容,支持从示例或品牌指南中提取独特的语感语调。适用于需要撰写超过一个段落的精炼文本,尤其是对语气一致性、结构和可信度有较高要求时。
后端架构模式、API 设计、数据库优化以及 Node.js、Express 和 Next.js API 路由的服务端最佳实践。
TypeScript、JavaScript、React、Node.js 开发的通用编码标准、最佳实践和模式。
为 X、LinkedIn、TikTok、YouTube、时事通讯(Newsletters)以及跨平台内容重加工营销活动(Repurposed multi-platform campaigns)创建平台原生的内容系统。当用户需要社交媒体帖子、推文串(Threads)、脚本、内容日历,或将单一源素材清晰地适配到多个平台时使用。
Playwright E2E 测试模式、页面对象模型(POM)、配置、CI/CD 集成、产物管理以及不稳定测试(flaky test)策略。
适用于 Claude Code 会话的正规评测框架(Evaluation Framework),实现了评测驱动开发(Eval-Driven Development, EDD)原则
React、Next.js、状态管理(State Management)、性能优化(Performance Optimization)及 UI 最佳实践的前端开发模式。