Skip to main content

超时

介绍

Introduction

Playwright Test 对于各种任务有多个可配置的超时。

Playwright Test has multiple configurable timeouts for various tasks.

TimeoutDefaultDescription
Test timeout30000 msTimeout for each test, includes test, hooks and fixtures:
Set default
config = { timeout: 60000 }
Override
test.setTimeout(120000)
Expect timeout5000 msTimeout for each assertion:
Set default
config = { expect: { timeout: 10000 } }
Override
expect(locator).toBeVisible({ timeout: 10000 })

测试超时

Test timeout

Playwright Test 强制每个测试超时,默认为 30 秒。测试函数、装置、beforeEachafterEach 钩子所花费的时间包含在测试超时中。

Playwright Test enforces a timeout for each test, 30 seconds by default. Time spent by the test function, fixtures, beforeEach and afterEach hooks is included in the test timeout.

超时测试会产生以下错误:

Timed out test produces the following error:

example.spec.ts:3:1 › basic test ===========================

Timeout of 30000ms exceeded.

相同的超时值也适用于 beforeAllafterAll 钩子,但它们不与任何测试共享时间。

The same timeout value also applies to beforeAll and afterAll hooks, but they do not share time with any test.

在配置中设置测试超时

Set test timeout in the config

playwright.config.ts
import { defineConfig } from '@playwright/test';

export default defineConfig({
timeout: 5 * 60 * 1000,
});

API 参考:testConfig.timeout

API reference: testConfig.timeout.

设置单个测试的超时时间

Set timeout for a single test

import { test, expect } from '@playwright/test';

test('slow test', async ({ page }) => {
test.slow(); // Easy way to triple the default timeout
// ...
});

test('very slow test', async ({ page }) => {
test.setTimeout(120000);
// ...
});

API 参考:test.setTimeout()test.slow()

API reference: test.setTimeout() and test.slow().

更改 beforeEach 钩子的超时

Change timeout from a beforeEach hook

import { test, expect } from '@playwright/test';

test.beforeEach(async ({ page }, testInfo) => {
// Extend timeout for all tests running this hook by 30 seconds.
testInfo.setTimeout(testInfo.timeout + 30000);
});

API 参考:testInfo.setTimeout()

API reference: testInfo.setTimeout().

更改 beforeAll/afterAll 钩子的超时

Change timeout for beforeAll/afterAll hook

beforeAllafterAll 钩子具有单独的超时,默认情况下等于测试超时。你可以通过在钩子内调用 testInfo.setTimeout() 为每个钩子单独更改它。

beforeAll and afterAll hooks have a separate timeout, by default equal to test timeout. You can change it separately for each hook by calling testInfo.setTimeout() inside the hook.

import { test, expect } from '@playwright/test';

test.beforeAll(async () => {
// Set timeout for this hook.
test.setTimeout(60000);
});

API 参考:testInfo.setTimeout()

API reference: testInfo.setTimeout().

期望超时

Expect timeout

expect(locator).toHaveText() 这样的 Web 优先断言有一个单独的超时,默认为 5 秒。断言超时与测试超时无关。它会产生以下错误:

Web-first assertions like expect(locator).toHaveText() have a separate timeout, 5 seconds by default. Assertion timeout is unrelated to the test timeout. It produces the following error:

example.spec.ts:3:1 › basic test ===========================

Error: expect(received).toHaveText(expected)

Expected string: "my text"
Received string: ""
Call log:
- expect.toHaveText with timeout 5000ms
- waiting for "locator('button')"

在配置中设置期望超时

Set expect timeout in the config

playwright.config.ts
import { defineConfig } from '@playwright/test';

export default defineConfig({
expect: {
timeout: 10 * 1000,
},
});

全局超时

Global timeout

Playwright Test 支持整个测试运行超时。这可以防止出现问题时过度使用资源。没有默认的全局超时,但你可以在配置中设置合理的超时,例如一小时。全局超时会产生以下错误:

Playwright Test supports a timeout for the whole test run. This prevents excess resource usage when everything went wrong. There is no default global timeout, but you can set a reasonable one in the config, for example one hour. Global timeout produces the following error:

Running 1000 tests using 10 workers

514 skipped
486 passed
Timed out waiting 3600s for the entire test run

你可以在配置中设置全局超时。

You can set global timeout in the config.

// playwright.config.ts
import { defineConfig } from '@playwright/test';

export default defineConfig({
globalTimeout: 60 * 60 * 1000,
});

API 参考:testConfig.globalTimeout

API reference: testConfig.globalTimeout.

高级:底层超时

Advanced: low level timeouts

这些是测试运行程序预先配置的底层超时,你不需要更改它们。如果你碰巧在本节中是因为你的测试不稳定,那么你很可能应该在其他地方寻找解决方案。

These are the low-level timeouts that are pre-configured by the test runner, you should not need to change these. If you happen to be in this section because your test are flaky, it is very likely that you should be looking for the solution elsewhere.

TimeoutDefaultDescription
Action timeoutno timeoutTimeout for each action:
Set default
config = { use: { actionTimeout: 10000 } }
Override
locator.click({ timeout: 10000 })
Navigation timeoutno timeoutTimeout for each navigation action:
Set default
config = { use: { navigationTimeout: 30000 } }
Override
page.goto('/', { timeout: 30000 })
Global timeoutno timeoutGlobal timeout for the whole test run:
Set in config
config = { globalTimeout: 60*60*1000 }
beforeAll/afterAll timeout30000 msTimeout for the hook:
Set in hook
test.setTimeout(60000)
Fixture timeoutno timeoutTimeout for an individual fixture:
Set in fixture
{ scope: 'test', timeout: 30000 }

设置单个断言的超时时间

Set timeout for a single assertion

import { test, expect } from '@playwright/test';

test('basic test', async ({ page }) => {
await expect(page.getByRole('button')).toHaveText('Sign in', { timeout: 10000 });
});

在配置中设置操作和导航超时

Set action and navigation timeouts in the config

playwright.config.ts
import { defineConfig } from '@playwright/test';

export default defineConfig({
use: {
actionTimeout: 10 * 1000,
navigationTimeout: 30 * 1000,
},
});

API 参考:testOptions.actionTimeouttestOptions.navigationTimeout

API reference: testOptions.actionTimeout and testOptions.navigationTimeout.

设置单个操作的超时时间

Set timeout for a single action

import { test, expect } from '@playwright/test';

test('basic test', async ({ page }) => {
await page.goto('https://playwright.nodejs.cn', { timeout: 30000 });
await page.getByText('Get Started').click({ timeout: 10000 });
});

夹具超时

Fixture timeout

默认情况下,fixture 与测试共享超时。然而,对于慢速比赛,尤其是 worker-scoped 的比赛,单独的暂停是很方便的。通过这种方式,你可以保持整体测试超时较小,并为慢速装置提供更多时间。

By default, fixture shares timeout with the test. However, for slow fixtures, especially worker-scoped ones, it is convenient to have a separate timeout. This way you can keep the overall test timeout small, and give the slow fixture more time.

import { test as base, expect } from '@playwright/test';

const test = base.extend<{ slowFixture: string }>({
slowFixture: [async ({}, use) => {
// ... perform a slow operation ...
await use('hello');
}, { timeout: 60000 }]
});

test('example test', async ({ slowFixture }) => {
// ...
});

API 参考:test.extend()

API reference: test.extend().