Files
zclaw_openfang/desktop/tests/e2e/specs/agent-chat-comprehensive.spec.ts
iven 5db2907420
Some checks failed
CI / Lint & TypeCheck (push) Has been cancelled
CI / Unit Tests (push) Has been cancelled
CI / Build Frontend (push) Has been cancelled
CI / Rust Check (push) Has been cancelled
CI / Security Scan (push) Has been cancelled
CI / E2E Tests (push) Has been cancelled
test(desktop): add agent-chat comprehensive E2E test spec
Full E2E test suite for agent chat functionality including:
- Message send/receive flow
- Streaming response verification
- Model switching behavior
- Error handling scenarios
- Multi-turn conversation context

Includes test report documenting coverage and known gaps.
2026-04-03 23:02:00 +08:00

1016 lines
31 KiB
TypeScript
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/**
* Agent 对话功能全面验证测试
*
* 测试范围:
* 1. Agent 对话初始化
* 2. 消息发送与接收
* 3. 对话历史记录
* 4. 上下文保持
* 5. 功能按钮交互
* 6. 异常状态处理
* 7. 边界条件测试
* 8. 异常输入测试
* 9. 错误流程测试
*
* 使用 Chrome DevTools Protocol 进行深度验证
*/
import { test, expect, Page, CDPSession } from '@playwright/test';
import { execSync } from 'child_process';
// 测试配置
const TEST_CONFIG = {
baseURL: 'http://localhost:3000',
timeouts: {
navigation: 30000,
element: 10000,
message: 60000,
stream: 120000,
},
};
// 测试数据
const TEST_MESSAGES = {
normal: [
'你好,请介绍一下自己',
'你能帮我做什么?',
'请用 Python 写一个快速排序算法',
],
boundary: {
empty: '',
whitespace: ' ',
long: 'a'.repeat(5000),
special: '!@#$%^&*()_+-=[]{}|;\':",./<>?',
multiline: '第一行\n第二行\n第三行',
unicode: '你好世界 🌍 Привет мир こんにちは世界',
code: '```python\ndef hello():\n print("Hello")\n```',
},
edge: {
sqlInjection: "'; DROP TABLE users; --",
xss: '<script>alert("xss")</script>',
json: '{"key": "value", "nested": {"array": [1,2,3]}}',
xml: '<?xml version="1.0"?><root><item>test</item></root>',
},
};
// 辅助函数:等待指定时间
const wait = (ms: number) => new Promise(resolve => setTimeout(resolve, ms));
// 辅助函数:获取 CDP Session
async function getCDPSession(page: Page): Promise<CDPSession> {
return await page.context().newCDPSession(page);
}
// 辅助函数:清除浏览器存储
async function clearBrowserStorage(page: Page) {
await page.evaluate(() => {
localStorage.clear();
sessionStorage.clear();
indexedDB.databases().then(dbs => {
dbs.forEach(db => {
if (db.name) indexedDB.deleteDatabase(db.name);
});
});
});
}
// 辅助函数:获取控制台日志
async function getConsoleLogs(page: Page): Promise<string[]> {
const logs: string[] = [];
page.on('console', msg => {
logs.push(`[${msg.type()}] ${msg.text()}`);
});
return logs;
}
// 辅助函数:获取网络请求
async function getNetworkRequests(page: Page): Promise<any[]> {
const requests: any[] = [];
page.on('request', request => {
requests.push({
url: request.url(),
method: request.method(),
headers: request.headers(),
});
});
return requests;
}
test.describe('Agent 对话功能全面验证', () => {
let page: Page;
let cdp: CDPSession;
let consoleLogs: string[] = [];
let networkRequests: any[] = [];
test.beforeEach(async ({ browser }) => {
// 创建新页面
const context = await browser.newContext({
viewport: { width: 1280, height: 720 },
deviceScaleFactor: 1,
});
page = await context.newPage();
// 获取 CDP Session
cdp = await getCDPSession(page);
// 启用 CDP 域
await cdp.send('Console.enable');
await cdp.send('Network.enable');
await cdp.send('Runtime.enable');
await cdp.send('Page.enable');
// 收集控制台日志
consoleLogs = [];
page.on('console', msg => {
consoleLogs.push(`[${msg.type()}] ${msg.text()}`);
});
// 收集网络请求
networkRequests = [];
page.on('request', request => {
networkRequests.push({
url: request.url(),
method: request.method(),
timestamp: Date.now(),
});
});
// 收集页面错误
page.on('pageerror', error => {
consoleLogs.push(`[PAGE_ERROR] ${error.message}`);
});
// 清除存储并导航到应用
await clearBrowserStorage(page);
await page.goto(TEST_CONFIG.baseURL, {
timeout: TEST_CONFIG.timeouts.navigation,
waitUntil: 'networkidle',
});
// 等待应用初始化
await wait(2000);
});
test.afterEach(async () => {
// 输出收集的日志
if (consoleLogs.length > 0) {
console.log('\n=== 控制台日志 ===');
consoleLogs.forEach(log => console.log(log));
}
if (networkRequests.length > 0) {
console.log('\n=== 网络请求 ===');
console.log(`总请求数: ${networkRequests.length}`);
}
await page.close();
});
// ============================================
// 测试套件 1: Agent 对话初始化
// ============================================
test.describe('1. Agent 对话初始化', () => {
test('1.1 页面加载后应显示初始界面', async () => {
// 验证页面标题
const title = await page.title();
expect(title).toBeTruthy();
// 验证主要元素存在
const chatArea = await page.locator('[data-testid="chat-area"], .chat-area, [class*="ChatArea"]').first();
const inputArea = await page.locator('textarea, input[type="text"], [data-testid="chat-input"]').first();
// 截图记录初始状态
await page.screenshot({
path: 'test-results/agent-chat-init.png',
fullPage: true,
});
// 验证至少有一个输入区域
const hasInput = await inputArea.isVisible().catch(() => false);
expect(hasInput || await chatArea.isVisible().catch(() => false)).toBeTruthy();
});
test('1.2 应正确加载默认 Agent 配置', async () => {
// 使用 CDP 检查 localStorage
const localStorage = await cdp.send('Runtime.evaluate', {
expression: 'JSON.stringify(localStorage)',
});
console.log('LocalStorage 内容:', localStorage.result.value);
// 检查 IndexedDB
const indexedDBData = await cdp.send('Runtime.evaluate', {
expression: `
(async () => {
const dbs = await indexedDB.databases();
return JSON.stringify(dbs.map(db => db.name));
})()
`,
awaitPromise: true,
});
console.log('IndexedDB 数据库:', indexedDBData.result.value);
});
test('1.3 网络连接状态应正确显示', async () => {
// 检查连接状态指示器
const connectionIndicators = await page.locator(
'[data-testid="connection-status"], .connection-status, [class*="Connection"], [class*="connection"]'
).all();
console.log(`找到 ${connectionIndicators.length} 个连接状态指示器`);
// 验证没有连接错误
const errorLogs = consoleLogs.filter(log =>
log.includes('error') || log.includes('Error') || log.includes('failed')
);
// 允许初始连接尝试的错误
const criticalErrors = errorLogs.filter(log =>
!log.includes('WebSocket') && !log.includes('connection')
);
expect(criticalErrors.length).toBeLessThan(5);
});
test('1.4 首次加载应显示欢迎界面或引导', async () => {
// 检查是否有欢迎消息或引导
const welcomeElements = await page.locator(
'text=/欢迎|Welcome|开始|Start|你好|Hello/i'
).all();
console.log(`找到 ${welcomeElements.length} 个欢迎元素`);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-welcome.png',
fullPage: true,
});
});
});
// ============================================
// 测试套件 2: 消息发送与接收
// ============================================
test.describe('2. 消息发送与接收', () => {
test('2.1 正常消息发送应成功', async () => {
const testMessage = TEST_MESSAGES.normal[0];
// 找到输入框
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(testMessage);
// 找到发送按钮
const sendButton = await page.locator(
'button[type="submit"], button:has-text("发送"), button:has-text("Send"), [data-testid="send-button"]'
).first();
// 点击发送或按回车
if (await sendButton.isVisible().catch(() => false)) {
await sendButton.click();
} else {
await input.press('Enter');
}
// 等待消息发送
await wait(1000);
// 验证消息出现在对话中
const messages = await page.locator(
'[data-testid="message"], .message, [class*="Message"], [class*="message"]'
).all();
console.log(`找到 ${messages.length} 条消息`);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-message-sent.png',
fullPage: true,
});
});
test('2.2 流式响应应正确显示', async () => {
const testMessage = '请详细介绍一下人工智能的发展历程';
// 发送消息
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(testMessage);
await input.press('Enter');
// 等待流式响应开始
await wait(2000);
// 使用 CDP 监控 DOM 变化
const initialDOM = await cdp.send('Runtime.evaluate', {
expression: 'document.body.innerHTML.length',
});
console.log('初始 DOM 长度:', initialDOM.result.value);
// 等待一段时间观察流式更新
await wait(5000);
const updatedDOM = await cdp.send('Runtime.evaluate', {
expression: 'document.body.innerHTML.length',
});
console.log('更新后 DOM 长度:', updatedDOM.result.value);
// 截图记录流式响应状态
await page.screenshot({
path: 'test-results/agent-chat-streaming.png',
fullPage: true,
});
});
test('2.3 多轮对话应保持上下文', async () => {
const messages = [
'我的名字叫张三',
'我叫什么名字?',
'请用我的名字写一首短诗',
];
for (const message of messages) {
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(message);
await input.press('Enter');
// 等待响应
await wait(3000);
// 截图记录每轮对话
await page.screenshot({
path: `test-results/agent-chat-context-${messages.indexOf(message)}.png`,
fullPage: true,
});
}
// 验证所有消息都存在于对话中
const allMessages = await page.locator(
'[data-testid="message"], .message, [class*="Message"]'
).all();
console.log(`对话中共有 ${allMessages.length} 条消息`);
expect(allMessages.length).toBeGreaterThanOrEqual(messages.length * 2);
});
test('2.4 代码块应正确渲染', async () => {
const codeMessage = '请写一个 Python 函数来计算斐波那契数列';
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(codeMessage);
await input.press('Enter');
// 等待响应
await wait(8000);
// 检查代码块
const codeBlocks = await page.locator(
'pre, code, [class*="code"], [class*="Code"]'
).all();
console.log(`找到 ${codeBlocks.length} 个代码块元素`);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-code-block.png',
fullPage: true,
});
});
});
// ============================================
// 测试套件 3: 对话历史记录
// ============================================
test.describe('3. 对话历史记录', () => {
test('3.1 对话列表应正确显示', async () => {
// 查找对话列表
const conversationList = await page.locator(
'[data-testid="conversation-list"], .conversation-list, [class*="Conversation"], [class*="conversation"]'
).all();
console.log(`找到 ${conversationList.length} 个对话列表元素`);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-conversation-list.png',
fullPage: true,
});
});
test('3.2 新建对话应创建新会话', async () => {
// 查找新建对话按钮
const newChatButton = await page.locator(
'button:has-text("新对话"), button:has-text("New Chat"), [data-testid="new-conversation"], button:has([svg])'
).first();
if (await newChatButton.isVisible().catch(() => false)) {
await newChatButton.click();
await wait(1000);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-new-conversation.png',
fullPage: true,
});
}
});
test('3.3 切换对话应加载正确内容', async () => {
// 先发送一条消息创建对话
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill('这是测试对话 1');
await input.press('Enter');
await wait(2000);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-switch-conversation.png',
fullPage: true,
});
});
test('3.4 对话标题应正确生成', async () => {
// 发送消息
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill('讨论机器学习算法');
await input.press('Enter');
await wait(2000);
// 检查对话标题
const titles = await page.locator(
'[class*="title"], [class*="Title"], h1, h2, h3'
).allInnerTexts();
console.log('找到的对话标题:', titles);
});
});
// ============================================
// 测试套件 4: 上下文保持
// ============================================
test.describe('4. 上下文保持', () => {
test('4.1 页面刷新后应恢复对话状态', async () => {
// 发送消息
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill('记住这个数字42');
await input.press('Enter');
await wait(3000);
// 刷新页面
await page.reload({ waitUntil: 'networkidle' });
await wait(2000);
// 验证对话恢复
const messages = await page.locator(
'[data-testid="message"], .message, [class*="Message"]'
).all();
console.log(`刷新后找到 ${messages.length} 条消息`);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-refresh-recovery.png',
fullPage: true,
});
});
test('4.2 长对话上下文应正确处理', async () => {
// 发送多条消息建立长对话
for (let i = 0; i < 5; i++) {
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(`消息 ${i + 1}: 这是测试消息`);
await input.press('Enter');
await wait(2000);
}
// 询问关于之前的内容
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill('我发送的第一条消息是什么?');
await input.press('Enter');
await wait(5000);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-long-context.png',
fullPage: true,
});
});
});
// ============================================
// 测试套件 5: 功能按钮交互
// ============================================
test.describe('5. 功能按钮交互', () => {
test('5.1 聊天模式切换应正常工作', async () => {
// 查找模式切换按钮
const modeButtons = await page.locator(
'button:has-text("闪速"), button:has-text("思考"), button:has-text("Pro"), button:has-text("Ultra"), [data-testid="chat-mode"]'
).all();
console.log(`找到 ${modeButtons.length} 个模式按钮`);
if (modeButtons.length > 0) {
await modeButtons[0].click();
await wait(500);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-mode-switch.png',
fullPage: true,
});
}
});
test('5.2 文件上传按钮应可点击', async () => {
// 查找文件上传按钮
const fileButton = await page.locator(
'button:has([name="paperclip"]), button:has-text("附件"), [data-testid="file-upload"], input[type="file"]'
).first();
const isVisible = await fileButton.isVisible().catch(() => false);
console.log('文件上传按钮可见:', isVisible);
if (isVisible) {
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-file-button.png',
fullPage: true,
});
}
});
test('5.3 停止生成按钮应在流式响应时显示', async () => {
// 发送长消息触发流式响应
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill('请详细解释量子计算的原理和应用,包括量子比特、量子纠缠等概念');
await input.press('Enter');
// 等待流式响应开始
await wait(1000);
// 查找停止按钮
const stopButton = await page.locator(
'button:has-text("停止"), button:has-text("Stop"), [data-testid="stop-generation"], button:has([name="square"])'
).first();
const isVisible = await stopButton.isVisible().catch(() => false);
console.log('停止按钮可见:', isVisible);
if (isVisible) {
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-stop-button.png',
fullPage: true,
});
}
});
test('5.4 重新生成按钮应在响应完成后显示', async () => {
// 发送消息并等待完成
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill('你好');
await input.press('Enter');
await wait(5000);
// 查找重新生成按钮
const regenerateButton = await page.locator(
'button:has-text("重新生成"), button:has-text("Regenerate"), [data-testid="regenerate"], button:has([name="refresh"])'
).first();
const isVisible = await regenerateButton.isVisible().catch(() => false);
console.log('重新生成按钮可见:', isVisible);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-regenerate-button.png',
fullPage: true,
});
});
});
// ============================================
// 测试套件 6: 异常状态处理
// ============================================
test.describe('6. 异常状态处理', () => {
test('6.1 网络断开时应显示离线提示', async () => {
// 模拟网络断开
await cdp.send('Network.emulateNetworkConditions', {
offline: true,
latency: 0,
downloadThroughput: 0,
uploadThroughput: 0,
});
await wait(1000);
// 检查离线提示
const offlineIndicator = await page.locator(
'text=/离线|Offline|网络|Network/i, [class*="offline"], [class*="Offline"]'
).first();
const isVisible = await offlineIndicator.isVisible().catch(() => false);
console.log('离线提示可见:', isVisible);
// 恢复网络
await cdp.send('Network.emulateNetworkConditions', {
offline: false,
latency: 0,
downloadThroughput: -1,
uploadThroughput: -1,
});
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-offline.png',
fullPage: true,
});
});
test('6.2 发送空消息应被阻止或提示', async () => {
const input = await page.locator('textarea, input[type="text"]').first();
// 尝试发送空消息
await input.fill('');
await input.press('Enter');
await wait(500);
// 检查是否有错误提示
const errorMessages = await page.locator(
'text=/不能为空|Cannot be empty|请输入|Please enter/i, [class*="error"], [class*="Error"]'
).all();
console.log(`找到 ${errorMessages.length} 个错误提示`);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-empty-message.png',
fullPage: true,
});
});
test('6.3 快速连续发送应被正确处理', async () => {
const input = await page.locator('textarea, input[type="text"]').first();
// 快速发送多条消息
for (let i = 0; i < 5; i++) {
await input.fill(`快速消息 ${i + 1}`);
await input.press('Enter');
}
await wait(2000);
// 检查消息数量
const messages = await page.locator(
'[data-testid="message"], .message, [class*="Message"]'
).all();
console.log(`快速发送后找到 ${messages.length} 条消息`);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-rapid-send.png',
fullPage: true,
});
});
});
// ============================================
// 测试套件 7: 边界条件测试
// ============================================
test.describe('7. 边界条件测试', () => {
test('7.1 超长消息应被正确处理', async () => {
const longMessage = TEST_MESSAGES.boundary.long;
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(longMessage);
// 检查输入框内容
const inputValue = await input.inputValue();
console.log(`输入框内容长度: ${inputValue.length}`);
await input.press('Enter');
await wait(2000);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-long-message.png',
fullPage: true,
});
});
test('7.2 特殊字符应正确显示', async () => {
const specialMessage = TEST_MESSAGES.boundary.special;
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(specialMessage);
await input.press('Enter');
await wait(2000);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-special-chars.png',
fullPage: true,
});
});
test('7.3 Unicode 字符应正确显示', async () => {
const unicodeMessage = TEST_MESSAGES.boundary.unicode;
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(unicodeMessage);
await input.press('Enter');
await wait(2000);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-unicode.png',
fullPage: true,
});
});
test('7.4 多行消息应正确渲染', async () => {
const multilineMessage = TEST_MESSAGES.boundary.multiline;
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(multilineMessage);
await input.press('Enter');
await wait(2000);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-multiline.png',
fullPage: true,
});
});
});
// ============================================
// 测试套件 8: 异常输入测试
// ============================================
test.describe('8. 异常输入测试', () => {
test('8.1 SQL 注入尝试应被安全处理', async () => {
const sqlInjection = TEST_MESSAGES.edge.sqlInjection;
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(sqlInjection);
await input.press('Enter');
await wait(2000);
// 检查控制台是否有错误
const securityErrors = consoleLogs.filter(log =>
log.includes('SQL') || log.includes('injection') || log.includes('security')
);
console.log('安全相关日志:', securityErrors);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-sql-injection.png',
fullPage: true,
});
});
test('8.2 XSS 尝试应被安全处理', async () => {
const xssAttempt = TEST_MESSAGES.edge.xss;
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(xssAttempt);
await input.press('Enter');
await wait(2000);
// 检查页面是否执行了脚本
const alertTriggered = consoleLogs.some(log =>
log.includes('alert') || log.includes('xss')
);
expect(alertTriggered).toBe(false);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-xss.png',
fullPage: true,
});
});
test('8.3 JSON 数据应被正确格式化', async () => {
const jsonMessage = TEST_MESSAGES.edge.json;
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(jsonMessage);
await input.press('Enter');
await wait(2000);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-json.png',
fullPage: true,
});
});
test('8.4 XML 数据应被正确处理', async () => {
const xmlMessage = TEST_MESSAGES.edge.xml;
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(xmlMessage);
await input.press('Enter');
await wait(2000);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-xml.png',
fullPage: true,
});
});
});
// ============================================
// 测试套件 9: 错误流程测试
// ============================================
test.describe('9. 错误流程测试', () => {
test('9.1 后端服务不可用时应有降级处理', async () => {
// 模拟后端服务不可用
await cdp.send('Network.setBlockedURLs', {
urls: ['*localhost*', '*127.0.0.1*'],
});
await wait(1000);
// 尝试发送消息
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill('测试消息');
await input.press('Enter');
await wait(2000);
// 检查错误提示
const errorMessages = await page.locator(
'text=/错误|Error|失败|Failed|连接|Connection/i, [class*="error"], [class*="Error"]'
).all();
console.log(`找到 ${errorMessages.length} 个错误提示`);
// 恢复网络
await cdp.send('Network.setBlockedURLs', {
urls: [],
});
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-backend-down.png',
fullPage: true,
});
});
test('9.2 超时情况应有正确处理', async () => {
// 发送消息
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill('这是一个测试');
await input.press('Enter');
// 等待较长时间
await wait(10000);
// 检查是否有超时提示
const timeoutMessages = await page.locator(
'text=/超时|Timeout|等待|Waiting/i'
).all();
console.log(`找到 ${timeoutMessages.length} 个超时相关提示`);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-timeout.png',
fullPage: true,
});
});
test('9.3 内存使用情况监控', async () => {
// 使用 CDP 获取内存信息
const memoryInfo = await cdp.send('Runtime.getHeapUsage');
console.log('堆内存使用:', memoryInfo);
// 发送多条消息
for (let i = 0; i < 10; i++) {
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(`内存测试消息 ${i + 1}`);
await input.press('Enter');
await wait(1000);
}
// 再次获取内存信息
const memoryInfoAfter = await cdp.send('Runtime.getHeapUsage');
console.log('发送消息后堆内存使用:', memoryInfoAfter);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-memory.png',
fullPage: true,
});
});
});
// ============================================
// 测试套件 10: 性能测试
// ============================================
test.describe('10. 性能测试', () => {
test('10.1 首屏加载时间', async () => {
// 使用 CDP 测量性能
const metrics = await cdp.send('Performance.getMetrics');
console.log('性能指标:', metrics);
// 使用 Navigation Timing API
const timing = await cdp.send('Runtime.evaluate', {
expression: `
JSON.stringify({
navigationStart: performance.timing.navigationStart,
loadEventEnd: performance.timing.loadEventEnd,
domContentLoaded: performance.timing.domContentLoadedEventEnd,
firstPaint: performance.getEntriesByType('paint')[0]?.startTime,
firstContentfulPaint: performance.getEntriesByType('paint')[1]?.startTime,
})
`,
});
console.log('页面加载时间:', timing.result.value);
});
test('10.2 消息渲染性能', async () => {
const startTime = Date.now();
// 发送消息
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill('性能测试消息');
await input.press('Enter');
// 等待响应
await wait(5000);
const endTime = Date.now();
console.log(`消息响应时间: ${endTime - startTime}ms`);
// 使用 CDP 获取渲染性能
const renderMetrics = await cdp.send('Runtime.evaluate', {
expression: `
JSON.stringify(performance.getEntriesByType('measure'))
`,
});
console.log('渲染性能指标:', renderMetrics.result.value);
});
test('10.3 大量消息滚动性能', async () => {
// 发送大量消息
for (let i = 0; i < 20; i++) {
const input = await page.locator('textarea, input[type="text"]').first();
await input.fill(`滚动性能测试消息 ${i + 1}`);
await input.press('Enter');
await wait(500);
}
// 滚动到顶部
await page.evaluate(() => {
window.scrollTo(0, 0);
});
await wait(500);
// 滚动到底部
await page.evaluate(() => {
window.scrollTo(0, document.body.scrollHeight);
});
await wait(500);
// 截图记录
await page.screenshot({
path: 'test-results/agent-chat-scroll-performance.png',
fullPage: true,
});
});
});
});
// 测试总结报告
test.describe('测试总结', () => {
test('生成测试报告', async () => {
console.log('\n');
console.log('==============================================');
console.log('Agent 对话功能全面验证测试完成');
console.log('==============================================');
console.log('测试范围:');
console.log(' 1. Agent 对话初始化');
console.log(' 2. 消息发送与接收');
console.log(' 3. 对话历史记录');
console.log(' 4. 上下文保持');
console.log(' 5. 功能按钮交互');
console.log(' 6. 异常状态处理');
console.log(' 7. 边界条件测试');
console.log(' 8. 异常输入测试');
console.log(' 9. 错误流程测试');
console.log(' 10. 性能测试');
console.log('==============================================');
});
});