Playwright+CucumberJS问题:Chromium中页面加载await超时
问题:Playwright+Cucumber-JS环境下页面加载超时问题
我按照某指南搭建了Playwright与Cucumber-JS环境,将测试目标指向公司内部网站后,即便设置了超长超时时间(如1000000ms),页面仍无法加载。使用await会触发页面加载超时,移除await则后续元素定位失败。以下是相关代码、运行命令及控制台输出:
Step Definitions文件(steps.js)
const { Before, Given, When, Then } = require("@cucumber/cucumber"); const playwright = require("@playwright/test"); var page; Before( async function() { var browser = await playwright.chromium.launch({ headless: false, }); var context = await browser.newContext(); page = await context.newPage(); }); Given("a {string} is not logged in", { timeout: 1000 * 1000 }, async function (stringParam) { await page.goto('[MY-WEBSITE]'); await page.getByText("[SOME-TEXT-TO-VERIFY-I-AM-AT-MY-WEBSITE]"); }); When("a {string} signs in at the start", { timeout: 1000 * 1000 }, async function (stringParam) { await page.getByText('Enter your email'); page.getByText('Enter your email').fill("[FILL-IN-FORM-HERE]"); await page.getByText('Password (8+ characters)'); page.getByText('Password (8+ characters)').fill("[FILL-IN-FORM-HERE]"); await page.getByText('Join now for free'); page.getByText('Join now for free').click(); });
Feature文件(login.feature)
Feature: MY-FEATURE Scenario Outline: Sign in to the webpage from the signed-out home screen Given a "<UserType>" is not logged in When a "<UserType>" signs in at the start Then the user is signed in Examples: | UserType | | User1 |
运行命令
./node_modules/.bin/cucumber-js --exit
控制台输出
.F- Failures: 1) Scenario: Sign in to the website from the signed-out home screen # features/login.feature:15 ✔ Before # features/support/steps.js:5 ✖ Given a "User1" is not logged in # features/support/steps.js:13 page.goto: Timeout 30000ms exceeded. =========================== logs =========================== navigating to "[MY-WEBSITE]", waiting until "load" ============================================================ at World.<anonymous> (/Users/sam.levene/Git/playwright-poc/features/support/steps.js:14:16) - When a "User1" signs in at the start # features/support/steps.js:18
我的页面结构简单,加载后会显示模拟登录表单,后端基于PHP,理论上不会出现长时间加载的情况。想请教为什么await无法生效,页面始终在超时时间内无法加载?
解决方案
1. 超时设置未生效的核心原因
你给Cucumber步骤设置的timeout: 1000 * 1000只作用于Cucumber的步骤执行超时,但Playwright自身的page.goto有独立的默认超时(30000ms),控制台输出里的Timeout 30000ms exceeded就是明证。你的Cucumber步骤超时设置覆盖不了Playwright API的默认超时。
2. 针对性修复方案
方案一:给page.goto单独设置超时
修改Given步骤里的page.goto调用,直接传入超时参数:
await page.goto('[MY-WEBSITE]', { timeout: 1000 * 1000 }); // 匹配你设置的步骤超时
方案二:调整等待的页面状态
如果网站本身不需要等到完全load状态(比如单页应用或静态表单页面),可以修改page.goto的等待状态,减少不必要的等待时间:
await page.goto('[MY-WEBSITE]', { waitUntil: 'domcontentloaded' }); // 等待DOM加载完成即可
或者先导航,直接等待目标元素出现再确认:
// 先导航到页面,不等待完全加载,直接等待目标文本出现 await page.goto('[MY-WEBSITE]', { waitUntil: 'commit' }); await page.getByText("[SOME-TEXT-TO-VERIFY-I-AM-AT-MY-WEBSITE]").waitFor();
方案三:全局设置Playwright超时
如果所有API都需要统一超时,可以在创建context时设置:
var context = await browser.newContext({ defaultNavigationTimeout: 1000 * 1000, // 导航类操作超时 defaultTimeout: 1000 * 1000 // 元素操作类超时 });
3. 其他优化点
- 你的
When步骤里,fill和click操作没有加await,这会导致异步操作未完成就执行下一步,容易出现元素定位失败,必须补上:await page.getByText('Enter your email').fill("[FILL-IN-FORM-HERE]"); await page.getByText('Password (8+ characters)').fill("[FILL-IN-FORM-HERE]"); await page.getByText('Join now for free').click(); - 建议用更精确的元素定位器,比如
getByPlaceholder代替getByText来定位输入框,避免文本匹配不准确:await page.getByPlaceholder('Enter your email').fill("[FILL-IN-FORM-HERE]");
内容的提问来源于stack exchange,提问作者Raisus
相关产品推荐
相关产品推荐

