docs: update afterEach docs with an example (#9727)

Also add a test for TestInfo.status in afterEach.
This commit is contained in:
Dmitry Gozman 2021-10-22 16:32:22 -07:00 committed by GitHub
parent e2710451f3
commit 23aa0be15b
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 89 additions and 6 deletions

View file

@ -74,6 +74,40 @@ Hook function that takes one or two arguments: an object with fixtures and optio
Declares an `afterEach` hook that is executed after each test. When called in the scope of a test file, runs after each test in the file. When called inside a [`method: Test.describe`] group, runs after each test in the group. Declares an `afterEach` hook that is executed after each test. When called in the scope of a test file, runs after each test in the file. When called inside a [`method: Test.describe`] group, runs after each test in the group.
You can access all the same [Fixtures] as the test function itself, and also the [TestInfo] object that gives a lot of useful information. For example, you can check whether the test succeeded or failed.
```js js-flavor=js
// example.spec.js
const { test, expect } = require('@playwright/test');
test.afterEach(async ({ page }, testInfo) => {
console.log(`Finished ${testInfo.title} with status ${testInfo.status}`);
if (testInfo.status !== testInfo.expectedStatus)
console.log(`Did not run as expected, ended up at ${page.url()}`);
});
test('my test', async ({ page }) => {
// ...
});
```
```js js-flavor=ts
// example.spec.ts
import { test, expect } from '@playwright/test';
test.afterEach(async ({ page }, testInfo) => {
console.log(`Finished ${testInfo.title} with status ${testInfo.status}`);
if (testInfo.status !== testInfo.expectedStatus)
console.log(`Did not run as expected, ended up at ${page.url()}`);
});
test('my test', async ({ page }) => {
// ...
});
```
### param: Test.afterEach.hookFunction ### param: Test.afterEach.hookFunction
- `hookFunction` <[function]\([Fixtures], [TestInfo]\)> - `hookFunction` <[function]\([Fixtures], [TestInfo]\)>
@ -131,12 +165,14 @@ Hook function that takes one or two arguments: an object with fixtures and optio
Declares a `beforeEach` hook that is executed before each test. When called in the scope of a test file, runs before each test in the file. When called inside a [`method: Test.describe`] group, runs before each test in the group. Declares a `beforeEach` hook that is executed before each test. When called in the scope of a test file, runs before each test in the file. When called inside a [`method: Test.describe`] group, runs before each test in the group.
You can access all the same [Fixtures] as the test function itself, and also the [TestInfo] object that gives a lot of useful information. For example, you can navigate the page before starting the test.
```js js-flavor=js ```js js-flavor=js
// example.spec.js // example.spec.js
const { test, expect } = require('@playwright/test'); const { test, expect } = require('@playwright/test');
test.beforeEach(async ({ page }) => { test.beforeEach(async ({ page }, testInfo) => {
// Go to the starting url before each test. console.log(`Running ${testInfo.title}`);
await page.goto('https://my.start.url/'); await page.goto('https://my.start.url/');
}); });
@ -149,8 +185,8 @@ test('my test', async ({ page }) => {
// example.spec.ts // example.spec.ts
import { test, expect } from '@playwright/test'; import { test, expect } from '@playwright/test';
test.beforeEach(async ({ page }) => { test.beforeEach(async ({ page }, testInfo) => {
// Go to the starting url before each test. console.log(`Running ${testInfo.title}`);
await page.goto('https://my.start.url/'); await page.goto('https://my.start.url/');
}); });

View file

@ -2154,12 +2154,15 @@ export interface TestType<TestArgs extends KeyValue, WorkerArgs extends KeyValue
* [test.describe(title, callback)](https://playwright.dev/docs/api/class-test#test-describe) group, runs before each test * [test.describe(title, callback)](https://playwright.dev/docs/api/class-test#test-describe) group, runs before each test
* in the group. * in the group.
* *
* You can access all the same [Fixtures] as the test function itself, and also the [TestInfo] object that gives a lot of
* useful information. For example, you can navigate the page before starting the test.
*
* ```ts * ```ts
* // example.spec.ts * // example.spec.ts
* import { test, expect } from '@playwright/test'; * import { test, expect } from '@playwright/test';
* *
* test.beforeEach(async ({ page }) => { * test.beforeEach(async ({ page }, testInfo) => {
* // Go to the starting url before each test. * console.log(`Running ${testInfo.title}`);
* await page.goto('https://my.start.url/'); * await page.goto('https://my.start.url/');
* }); * });
* *
@ -2178,6 +2181,26 @@ export interface TestType<TestArgs extends KeyValue, WorkerArgs extends KeyValue
* test in the file. When called inside a * test in the file. When called inside a
* [test.describe(title, callback)](https://playwright.dev/docs/api/class-test#test-describe) group, runs after each test * [test.describe(title, callback)](https://playwright.dev/docs/api/class-test#test-describe) group, runs after each test
* in the group. * in the group.
*
* You can access all the same [Fixtures] as the test function itself, and also the [TestInfo] object that gives a lot of
* useful information. For example, you can check whether the test succeeded or failed.
*
* ```ts
* // example.spec.ts
* import { test, expect } from '@playwright/test';
*
* test.afterEach(async ({ page }, testInfo) => {
* console.log(`Finished ${testInfo.title} with status ${testInfo.status}`);
*
* if (testInfo.status !== testInfo.expectedStatus)
* console.log(`Did not run as expected, ended up at ${page.url()}`);
* });
*
* test('my test', async ({ page }) => {
* // ...
* });
* ```
*
* @param hookFunction Hook function that takes one or two arguments: an object with fixtures and optional [TestInfo]. * @param hookFunction Hook function that takes one or two arguments: an object with fixtures and optional [TestInfo].
*/ */
afterEach(inner: (args: TestArgs & WorkerArgs, testInfo: TestInfo) => Promise<any> | any): void; afterEach(inner: (args: TestArgs & WorkerArgs, testInfo: TestInfo) => Promise<any> | any): void;

View file

@ -493,3 +493,27 @@ test('beforeAll and afterAll timeouts at the same time should be reported', asyn
]); ]);
expect(result.output).toContain('Timeout of 1000ms exceeded in beforeAll hook.'); expect(result.output).toContain('Timeout of 1000ms exceeded in beforeAll hook.');
}); });
test('afterEach should get the test status right away', async ({ runInlineTest }) => {
const result = await runInlineTest({
'a.test.js': `
const { test } = pwt;
test.afterEach(({}, testInfo) => {
console.log('\\n%%' + testInfo.title + ': ' + testInfo.status);
});
test('failing', () => {
throw new Error('Oh my!');
});
test('timing out', async () => {
test.setTimeout(100);
await new Promise(() => {});
});
`,
});
expect(result.exitCode).toBe(1);
expect(result.failed).toBe(2);
expect(result.output.split('\n').filter(line => line.startsWith('%%'))).toEqual([
'%%failing: failed',
'%%timing out: timedOut',
]);
});