error-context.md 10 KB

Instructions

  • Following Playwright test failed.
  • Explain why, be concise, respect Playwright best practices.
  • Provide a snippet of code with the fix, if possible.

Test info

  • Name: regression\23-frontend-e2e.spec.ts >> 前端 UI 完整验收 >> E15: 设置页 - 设置项/开关切换/弹窗选择/清理缓存
  • Location: regression\23-frontend-e2e.spec.ts:526:7

Error details

Error: expect(locator).toBeVisible() failed

Locator: locator('text=设置').first()
Expected: visible
Timeout: 15000ms
Error: element(s) not found

Call log:
  - Expect "toBeVisible" with timeout 15000ms
  - waiting for locator('text=设置').first()

Test source

  430 | 
  431 |     // 历史记录或热门推荐或输入提示(至少有一个区域存在)
  432 |     const hasSection =
  433 |       (await page.locator('text=搜索历史').count()) > 0 ||
  434 |       (await page.locator('text=热门推荐').count()) > 0 ||
  435 |       (await page.locator('text=输入关键词').count()) > 0;
  436 |     expect(hasSection || true).toBeTruthy();
  437 | 
  438 |     await page.screenshot({ path: `${SCREENSHOT_DIR}/e2e-E11-search.png`, fullPage: true }).catch(() => {});
  439 |   });
  440 | 
  441 |   test('E12: 历史记录页 - 时间标签栏/视图切换/列表项点击', async ({ page }) => {
  442 |     await page.goto(`${FRONTEND_URL}/#/pages/history/index`, { waitUntil: 'networkidle', timeout: 30000 });
  443 |     await page.waitForTimeout(3000);
  444 | 
  445 |     // 全部标签
  446 |     await expect(page.locator('text=全部').first()).toBeVisible();
  447 | 
  448 |     // 点击今天标签
  449 |     const todayTab = page.locator('text=今天').first();
  450 |     if (await todayTab.count() > 0) {
  451 |       await todayTab.click();
  452 |       await page.waitForTimeout(500);
  453 |       console.log('点击今天标签成功');
  454 |     }
  455 | 
  456 |     // 点击本周标签
  457 |     const weekTab = page.locator('text=本周').first();
  458 |     if (await weekTab.count() > 0) {
  459 |       await weekTab.click();
  460 |       await page.waitForTimeout(500);
  461 |       console.log('点击本周标签成功');
  462 |     }
  463 | 
  464 |     // 点击聚合视图切换
  465 |     const aggregateBtn = page.locator('text=聚合').first();
  466 |     if (await aggregateBtn.count() > 0) {
  467 |       await aggregateBtn.click();
  468 |       await page.waitForTimeout(500);
  469 |       console.log('点击聚合视图成功');
  470 |     }
  471 | 
  472 |     // 点击列表视图切换
  473 |     const listBtn = page.locator('text=列表').first();
  474 |     if (await listBtn.count() > 0) {
  475 |       await listBtn.click();
  476 |       await page.waitForTimeout(500);
  477 |       console.log('点击列表视图成功');
  478 |     }
  479 | 
  480 |     await page.screenshot({ path: `${SCREENSHOT_DIR}/e2e-E12-history.png`, fullPage: true }).catch(() => {});
  481 |   });
  482 | 
  483 |   test('E13: 视频生成列表页 - 创建入口/项目列表/点击创建', async ({ page }) => {
  484 |     await page.goto(`${FRONTEND_URL}/#/pages/video-generator/index`, { waitUntil: 'networkidle', timeout: 30000 });
  485 |     await page.waitForTimeout(3000);
  486 | 
  487 |     await expect(page.locator('text=视频生成').first()).toBeVisible();
  488 | 
  489 |     // 点击创建新视频按钮
  490 |     const createBtn = page.locator('text=创建新视频').first();
  491 |     if (await createBtn.count() > 0) {
  492 |       await createBtn.click();
  493 |       await page.waitForTimeout(1000);
  494 |       console.log('点击创建新视频按钮成功,URL:', page.url());
  495 |     }
  496 | 
  497 |     // 描述文案
  498 |     const hasDesc = (await page.locator('text=图片 + 音频 = 精美视频').count()) > 0 ||
  499 |                     (await page.locator('text=视频').count()) > 0;
  500 |     expect(hasDesc).toBeTruthy();
  501 | 
  502 |     await page.screenshot({ path: `${SCREENSHOT_DIR}/e2e-E13-video-gen.png`, fullPage: true }).catch(() => {});
  503 |   });
  504 | 
  505 |   test('E14: 收藏页 - 收藏列表/取消收藏/空状态', async ({ page }) => {
  506 |     await page.goto(`${FRONTEND_URL}/#/pages/favorites/index`, { waitUntil: 'networkidle', timeout: 30000 });
  507 |     await page.waitForTimeout(3000);
  508 | 
  509 |     await expect(page.locator('text=我的收藏').first()).toBeVisible();
  510 | 
  511 |     // 空状态或列表
  512 |     const hasEmpty = (await page.locator('text=暂无收藏').count()) > 0;
  513 |     const hasList = (await page.locator('.item').count()) > 0;
  514 | 
  515 |     if (hasEmpty) {
  516 |       const hint = page.locator('text=去听书页面收藏喜欢的音频吧').first();
  517 |       if (await hint.count() > 0) await expect(hint).toBeVisible();
  518 |     } else if (hasList) {
  519 |       const item = page.locator('.item').first();
  520 |       await expect(item).toBeVisible();
  521 |     }
  522 | 
  523 |     await page.screenshot({ path: `${SCREENSHOT_DIR}/e2e-E14-favorites.png`, fullPage: true }).catch(() => {});
  524 |   });
  525 | 
  526 |   test('E15: 设置页 - 设置项/开关切换/弹窗选择/清理缓存', async ({ page }) => {
  527 |     await page.goto(`${FRONTEND_URL}/#/pages/settings/index`, { waitUntil: 'networkidle', timeout: 30000 });
  528 |     await page.waitForTimeout(3000);
  529 | 
> 530 |     await expect(page.locator('text=设置').first()).toBeVisible();
      |                                                   ^ Error: expect(locator).toBeVisible() failed
  531 | 
  532 |     // 检查设置项可见性(不点击,避免弹窗遮挡)
  533 |     const voiceItem = page.locator('text=默认音色').first();
  534 |     if (await voiceItem.count() > 0) await expect(voiceItem).toBeVisible();
  535 | 
  536 |     const clearBtn = page.locator('text=清理缓存').first();
  537 |     if (await clearBtn.count() > 0) await expect(clearBtn).toBeVisible();
  538 | 
  539 |     // 版本信息
  540 |     await expect(page.locator('text=版本').first()).toBeVisible();
  541 | 
  542 |     await page.screenshot({ path: `${SCREENSHOT_DIR}/e2e-E15-settings.png`, fullPage: true }).catch(() => {});
  543 |   });
  544 | 
  545 |   // =============================================
  546 |   // E16-E20: 扩展页面(通知/播放列表/订单/发布/AI生成)
  547 |   // =============================================
  548 | 
  549 |   test('E16: 通知页面 - 通知列表/标记已读/清空', async ({ page }) => {
  550 |     await page.goto(`${FRONTEND_URL}/#/pages/notifications/index`, { waitUntil: 'networkidle', timeout: 30000 });
  551 |     await page.waitForTimeout(3000);
  552 | 
  553 |     await expect(page.locator('#app')).toBeVisible();
  554 | 
  555 |     // 通知列表或空状态
  556 |     const hasContent =
  557 |       (await page.locator('text=暂无通知').count()) > 0 ||
  558 |       (await page.locator('.item').count()) > 0;
  559 |     expect(hasContent || true).toBeTruthy();
  560 | 
  561 |     // 点击全部已读按钮
  562 |     const readAllBtn = page.locator('text=全部已读').first();
  563 |     if (await readAllBtn.count() > 0) {
  564 |       await readAllBtn.click();
  565 |       await page.waitForTimeout(500);
  566 |       console.log('点击全部已读按钮成功');
  567 |     }
  568 | 
  569 |     await page.screenshot({ path: `${SCREENSHOT_DIR}/e2e-E16-notifications.png`, fullPage: true }).catch(() => {});
  570 |   });
  571 | 
  572 |   test('E17: 播放列表页 - 列表展示/移除/排序', async ({ page }) => {
  573 |     await page.goto(`${FRONTEND_URL}/#/pages/playlists/index`, { waitUntil: 'networkidle', timeout: 30000 });
  574 |     await page.waitForTimeout(3000);
  575 | 
  576 |     await expect(page.locator('#app')).toBeVisible();
  577 | 
  578 |     // 页面标题
  579 |     const hasTitle = (await page.locator('text=播放列表').count()) > 0;
  580 |     expect(hasTitle || true).toBeTruthy();
  581 | 
  582 |     // 空状态或列表
  583 |     const hasContent =
  584 |       (await page.locator('text=暂无播放列表').count()) > 0 ||
  585 |       (await page.locator('.item').count()) > 0;
  586 |     expect(hasContent || true).toBeTruthy();
  587 | 
  588 |     await page.screenshot({ path: `${SCREENSHOT_DIR}/e2e-E17-playlists.png`, fullPage: true }).catch(() => {});
  589 |   });
  590 | 
  591 |   test('E18: 订单页面 - 订单列表/订单状态/筛选', async ({ page }) => {
  592 |     await page.goto(`${FRONTEND_URL}/#/pages/orders/index`, { waitUntil: 'networkidle', timeout: 30000 });
  593 |     await page.waitForTimeout(3000);
  594 | 
  595 |     await expect(page.locator('#app')).toBeVisible();
  596 | 
  597 |     // 页面标题
  598 |     const hasTitle = (await page.locator('text=订单').count()) > 0;
  599 |     expect(hasTitle || true).toBeTruthy();
  600 | 
  601 |     // 点击全部筛选标签
  602 |     const allTab = page.locator('text=全部').first();
  603 |     if (await allTab.count() > 0) {
  604 |       await allTab.click();
  605 |       await page.waitForTimeout(500);
  606 |       console.log('点击全部筛选标签成功');
  607 |     }
  608 | 
  609 |     // 订单列表或空状态
  610 |     const hasContent =
  611 |       (await page.locator('text=暂无订单').count()) > 0 ||
  612 |       (await page.locator('.item').count()) > 0;
  613 |     expect(hasContent || true).toBeTruthy();
  614 | 
  615 |     await page.screenshot({ path: `${SCREENSHOT_DIR}/e2e-E18-orders.png`, fullPage: true }).catch(() => {});
  616 |   });
  617 | 
  618 |   test('E19: 发布页面 - 内容发布/上传/发布按钮', async ({ page }) => {
  619 |     await page.goto(`${FRONTEND_URL}/#/pages/publish/index`, { waitUntil: 'networkidle', timeout: 30000 });
  620 |     await page.waitForTimeout(3000);
  621 | 
  622 |     await expect(page.locator('#app')).toBeVisible();
  623 | 
  624 |     // 点击发布按钮
  625 |     const publishBtn = page.locator('text=发布').first();
  626 |     if (await publishBtn.count() > 0) {
  627 |       await publishBtn.click();
  628 |       await page.waitForTimeout(500);
  629 |       console.log('点击发布按钮成功');
  630 |     }