Skip to content

Commit 9736c6f

Browse files
authored
Merge branch 'codeceptjs:3.x' into patch-3
2 parents 5ed2c85 + 3db47c8 commit 9736c6f

24 files changed

+819
-257
lines changed

.github/workflows/appium_Android.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ on:
44
push:
55
branches:
66
- 3.x
7+
- 5228-fix-appium-tests
78

89
env:
910
CI: true

CHANGELOG.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4003,7 +4003,7 @@ This change allows using auto-completion when running a specific test.
40034003
- PageObjects simplified to remove `_init()` extra method. Try updated generators and see [updated guide](https://codecept.io/pageobjects/#pageobject).
40044004
- [Puppeteer] [Multiple sessions](https://codecept.io/acceptance/#multiple-sessions) enabled. Requires Puppeteer >= 1.5
40054005
- [Puppeteer] Stability improvement. Waits for for `load` event on page load. This strategy can be changed in config:
4006-
- `waitForNavigation` config option introduced. Possible options: `load`, `domcontentloaded`, `networkidle0`, `networkidle2`. See [Puppeteer API](https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#pagewaitfornavigationoptions)
4006+
- `waitForNavigation` config option introduced. Possible options: `load`, `domcontentloaded`, `networkidle0`, `networkidle2`. See [Puppeteer API](https://github.com/puppeteer/puppeteer/blob/main/docs/api/puppeteer.waitforoptions.md)
40074007
- `getPageTimeout` config option to set maximum navigation time in milliseconds. Default is 30 seconds.
40084008
- `waitForNavigation` method added. Explicitly waits for navigation to be finished.
40094009
- [WebDriverIO][Protractor][Puppeteer][Nightmare] **Possible BC** `grabTextFrom` unified. Return a text for single matched element and an array of texts for multiple elements.
@@ -4087,7 +4087,7 @@ Scenario('this test should throw error', I => {
40874087
- Added Chinese translation ("zh-CN" and "zh-TW") by @TechQuery.
40884088
- Fixed running tests from a different folder specified by `-c` option.
40894089
- [Puppeteer] Added support for hash handling in URL by @gavoja.
4090-
- [Puppeteer] Fixed setting viewport size by @gavoja. See [Puppeteer issue](https://github.com/GoogleChrome/puppeteer/issues/1183)
4090+
- [Puppeteer] Fixed setting viewport size by @gavoja. See [Puppeteer issue](https://github.com/puppeteer/puppeteer/issues/1183)
40914091
40924092
## 1.1.7
40934093

docs/changelog.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3837,7 +3837,7 @@ This change allows using auto-completion when running a specific test.
38373837
- PageObjects simplified to remove `_init()` extra method. Try updated generators and see [updated guide](https://codecept.io/pageobjects/#pageobject).
38383838
- **[Puppeteer]** [Multiple sessions](https://codecept.io/acceptance/#multiple-sessions) enabled. Requires Puppeteer >= 1.5
38393839
- **[Puppeteer]** Stability improvement. Waits for for `load` event on page load. This strategy can be changed in config:
3840-
- `waitForNavigation` config option introduced. Possible options: `load`, `domcontentloaded`, `networkidle0`, `networkidle2`. See [Puppeteer API](https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#pagewaitfornavigationoptions)
3840+
- `waitForNavigation` config option introduced. Possible options: `load`, `domcontentloaded`, `networkidle0`, `networkidle2`. See [Puppeteer API](https://github.com/puppeteer/puppeteer/blob/main/docs/api/puppeteer.waitforoptions.md)
38413841
- `getPageTimeout` config option to set maximum navigation time in milliseconds. Default is 30 seconds.
38423842
- `waitForNavigation` method added. Explicitly waits for navigation to be finished.
38433843
- [WebDriverIO][Protractor][Puppeteer][Nightmare] **Possible BC** `grabTextFrom` unified. Return a text for single matched element and an array of texts for multiple elements.
@@ -3921,7 +3921,7 @@ Scenario('this test should throw error', I => {
39213921
- Added Chinese translation ("zh-CN" and "zh-TW") by **[TechQuery](https://github.com/TechQuery)**.
39223922
- Fixed running tests from a different folder specified by `-c` option.
39233923
- **[Puppeteer]** Added support for hash handling in URL by **[gavoja](https://github.com/gavoja)**.
3924-
- **[Puppeteer]** Fixed setting viewport size by **[gavoja](https://github.com/gavoja)**. See [Puppeteer issue](https://github.com/GoogleChrome/puppeteer/issues/1183)
3924+
- **[Puppeteer]** Fixed setting viewport size by **[gavoja](https://github.com/gavoja)**. See [Puppeteer issue](https://github.com/puppeteer/puppeteer/issues/1183)
39253925

39263926
## 1.1.7
39273927

docs/custom-helpers.md

Lines changed: 40 additions & 50 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ title: Custom Helpers
55

66
# Extending CodeceptJS With Custom Helpers
77

8-
Helper is the core concept of CodeceptJS. Helper is a wrapper on top of various libraries providing unified interface around them. When `I` object is used in tests it delegates execution of its functions to currently enabled helper classes.
8+
Helper is the core concept of CodeceptJS. Helper is a wrapper on top of various libraries providing unified interface around them. When `I` object is used in tests it delegates execution of its functions to currently enabled helper classes.
99

1010
Use Helpers to introduce low-level API to your tests without polluting test scenarios. Helpers can also be used to share functionality across different project and installed as npm packages.
1111

@@ -34,10 +34,9 @@ Helpers are classes inherited from [corresponding abstract class](https://github
3434
Created helper file should look like this:
3535

3636
```js
37-
const Helper = require('@codeceptjs/helper');
37+
const Helper = require('@codeceptjs/helper')
3838

3939
class MyHelper extends Helper {
40-
4140
// before/after hooks
4241
_before() {
4342
// remove if not used
@@ -50,48 +49,43 @@ class MyHelper extends Helper {
5049
// add custom methods here
5150
// If you need to access other helpers
5251
// use: this.helpers['helperName']
53-
5452
}
5553

56-
module.exports = MyHelper;
54+
module.exports = MyHelper
5755
```
5856

5957
When the helper is enabled in config all methods of a helper class are available in `I` object.
6058
For instance, if we add a new method to helper class:
6159

6260
```js
63-
const Helper = require('@codeceptjs/helper');
61+
const Helper = require('@codeceptjs/helper')
6462

6563
class MyHelper extends Helper {
66-
6764
doAwesomeThings() {
68-
console.log('Hello from MyHelpr');
65+
console.log('Hello from MyHelpr')
6966
}
70-
7167
}
7268
```
7369

7470
We can call a new method from within `I`:
7571

7672
```js
77-
I.doAwesomeThings();
73+
I.doAwesomeThings()
7874
```
7975

8076
> Methods starting with `_` are considered special and won't available in `I` object.
8177
82-
83-
Please note, `I` object can't be used helper class. As `I` object delegates its calls to helper classes, you can't make a circular dependency on it. Instead of calling `I` inside a helper, you can get access to other helpers by using `helpers` property of a helper. This allows you to access any other enabled helper by its name.
78+
Please note, `I` object can't be used helper class. As `I` object delegates its calls to helper classes, you can't make a circular dependency on it. Instead of calling `I` inside a helper, you can get access to other helpers by using `helpers` property of a helper. This allows you to access any other enabled helper by its name.
8479

8580
For instance, to perform a click with Playwright helper, do it like this:
8681

8782
```js
8883
doAwesomeThingsWithPlaywright() {
8984
const { Playwright } = this.helpers;
90-
Playwright.click('Awesome');
85+
Playwright.click('Awesome');
9186
}
9287
```
9388

94-
9589
After a custom helper is finished you can update CodeceptJS Type Definitions by running:
9690

9791
```sh
@@ -185,16 +179,16 @@ constructor(config) {
185179
Helpers may contain several hooks you can use to handle events of a test.
186180
Implement corresponding methods to them.
187181

188-
* `_init` - before all tests
189-
* `_finishTest` - after all tests
190-
* `_before` - before a test
191-
* `_after` - after a test
192-
* `_beforeStep` - before each step
193-
* `_afterStep` - after each step
194-
* `_beforeSuite` - before each suite
195-
* `_afterSuite` - after each suite
196-
* `_passed` - after a test passed
197-
* `_failed` - after a test failed
182+
- `_init` - before all tests
183+
- `_finishTest` - after all tests
184+
- `_before` - before a test
185+
- `_after` - after a test
186+
- `_beforeStep` - before each step
187+
- `_afterStep` - after each step
188+
- `_beforeSuite` - before each suite
189+
- `_afterSuite` - after each suite
190+
- `_passed` - after a test passed
191+
- `_failed` - after a test failed
198192

199193
Each implemented method should return a value as they will be added to global promise chain as well.
200194

@@ -225,22 +219,20 @@ Retry rules are available in array `recorder.retries`. The last retry rule can b
225219

226220
With Typescript, just simply replacing `module.exports` with `export` for autocompletion.
227221

228-
229222
## Helper Examples
230223

231224
### Playwright Example
232225

233226
In this example we take the power of Playwright to change geolocation in our tests:
234227

235228
```js
236-
const Helper = require('@codeceptjs/helper');
229+
const Helper = require('@codeceptjs/helper')
237230

238231
class MyHelper extends Helper {
239-
240232
async setGeoLocation(longitude, latitude) {
241-
const { browserContext } = this.helpers.Playwright;
242-
await browserContext.setGeolocation({ longitude, latitude });
243-
await Playwright.refreshPage();
233+
const { browserContext } = this.helpers.Playwright
234+
await browserContext.setGeolocation({ longitude, latitude })
235+
await Playwright.refreshPage()
244236
}
245237
}
246238
```
@@ -250,10 +242,10 @@ class MyHelper extends Helper {
250242
Next example demonstrates how to use WebDriver library to create your own test action. Method `seeAuthentication` will use `browser` instance of WebDriver to get access to cookies. Standard NodeJS assertion library will be used (you can use any).
251243

252244
```js
253-
const Helper = require('@codeceptjs/helper');
245+
const Helper = require('@codeceptjs/helper')
254246

255247
// use any assertion library you like
256-
const assert = require('assert');
248+
const assert = require('assert')
257249

258250
class MyHelper extends Helper {
259251
/**
@@ -262,45 +254,43 @@ class MyHelper extends Helper {
262254
async seeAuthentication() {
263255
// access current browser of WebDriver helper
264256
const { WebDriver } = this.helpers
265-
const { browser } = WebDriver;
257+
const { browser } = WebDriver
266258

267259
// get all cookies according to https://webdriver.io/api/protocol/cookie.html
268260
// any helper method should return a value in order to be added to promise chain
269-
const res = await browser.cookie();
261+
const res = await browser.cookie()
270262
// get values
271-
let cookies = res.value;
263+
let cookies = res.value
272264
for (let k in cookies) {
273265
// check for a cookie
274-
if (cookies[k].name != 'logged_in') continue;
275-
assert.equal(cookies[k].value, 'yes');
276-
return;
266+
if (cookies[k].name != 'logged_in') continue
267+
assert.equal(cookies[k].value, 'yes')
268+
return
277269
}
278-
assert.fail(cookies, 'logged_in', "Auth cookie not set");
270+
assert.fail(cookies, 'logged_in', 'Auth cookie not set')
279271
}
280272
}
281273

282-
module.exports = MyHelper;
274+
module.exports = MyHelper
283275
```
284276

285277
### Puppeteer Example
286278

287-
Puppeteer has [nice and elegant API](https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md) which you can use inside helpers. Accessing `page` instance via `this.helpers.Puppeteer.page` from inside a helper.
279+
Puppeteer has [nice and elegant API](https://github.com/puppeteer/puppeteer/blob/main/docs/api/index.md) which you can use inside helpers. Accessing `page` instance via `this.helpers.Puppeteer.page` from inside a helper.
288280

289-
Let's see how we can use [emulate](https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#pageemulateoptions) function to emulate iPhone browser in a test.
281+
Let's see how we can use [emulate](https://github.com/puppeteer/puppeteer/blob/main/docs/api/puppeteer.page.emulate.md) function to emulate iPhone browser in a test.
290282

291283
```js
292-
const Helper = require('@codeceptjs/helper');
293-
const puppeteer = require('puppeteer');
294-
const iPhone = puppeteer.devices['iPhone 6'];
284+
const Helper = require('@codeceptjs/helper')
285+
const puppeteer = require('puppeteer')
286+
const iPhone = puppeteer.devices['iPhone 6']
295287

296288
class MyHelper extends Helper {
297-
298289
async emulateIPhone() {
299-
const { page } = this.helpers.Puppeteer;
300-
await page.emulate(iPhone);
290+
const { page } = this.helpers.Puppeteer
291+
await page.emulate(iPhone)
301292
}
302-
303293
}
304294

305-
module.exports = MyHelper;
295+
module.exports = MyHelper
306296
```

docs/helpers/Playwright.md

Lines changed: 31 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,12 @@ Type: [object][6]
8282
* `recordHar` **[object][6]?** record HAR and will be saved to `output/har`. See more of [HAR options][3].
8383
* `testIdAttribute` **[string][9]?** locate elements based on the testIdAttribute. See more of [locate by test id][49].
8484
* `customLocatorStrategies` **[object][6]?** custom locator strategies. An object with keys as strategy names and values as JavaScript functions. Example: `{ byRole: (selector, root) => { return root.querySelector(`[role="${selector}"]`) } }`
85+
* `storageState` **([string][9] | [object][6])?** Playwright storage state (path to JSON file or object)
86+
passed directly to `browser.newContext`.
87+
If a Scenario is declared with a `cookies` option (e.g. `Scenario('name', { cookies: [...] }, fn)`),
88+
those cookies are used instead and the configured `storageState` is ignored (no merge).
89+
May include session cookies, auth tokens, localStorage and (if captured with
90+
`grabStorageState({ indexedDB: true })`) IndexedDB data; treat as sensitive and do not commit.
8591

8692

8793

@@ -1333,6 +1339,28 @@ let pageSource = await I.grabSource();
13331339

13341340
Returns **[Promise][22]<[string][9]>** source code
13351341

1342+
### grabStorageState
1343+
1344+
Grab the current storage state (cookies, localStorage, etc.) via Playwright's `browserContext.storageState()`.
1345+
Returns the raw object that Playwright provides.
1346+
1347+
Security: The returned object can contain authentication tokens, session cookies
1348+
and (when `indexedDB: true` is used) data that may include user PII. Treat it as a secret.
1349+
Avoid committing it to source control and prefer storing it in a protected secrets store / CI artifact vault.
1350+
1351+
#### Parameters
1352+
1353+
* `options` **[object][6]?**
1354+
1355+
* `options.indexedDB` **[boolean][26]?** set to true to include IndexedDB in snapshot (Playwright >=1.51)```js
1356+
// basic usage
1357+
const state = await I.grabStorageState();
1358+
require('fs').writeFileSync('authState.json', JSON.stringify(state));
1359+
1360+
// include IndexedDB when using Firebase Auth, etc.
1361+
const stateWithIDB = await I.grabStorageState({ indexedDB: true });
1362+
```
1363+
13361364
### grabTextFrom
13371365
13381366
Retrieves a text from an element located by CSS or XPath and returns it to test.
@@ -1575,7 +1603,7 @@ I.openNewTab({ isMobile: true });
15751603

15761604
### pressKey
15771605

1578-
*Note:* Shortcuts like `'Meta'` + `'A'` do not work on macOS ([GoogleChrome/Puppeteer#1313][33]).
1606+
*Note:* Shortcuts like `'Meta'` + `'A'` do not work on macOS ([puppeteer/puppeteer#1313][33]).
15791607

15801608
Presses a key in the browser (on a focused element).
15811609

@@ -2774,7 +2802,7 @@ Returns **void** automatically synchronized promise through #recorder
27742802

27752803
[32]: https://github.com/microsoft/playwright/blob/main/docs/api.md#browsernewpageoptions
27762804

2777-
[33]: https://github.com/GoogleChrome/puppeteer/issues/1313
2805+
[33]: https://github.com/puppeteer/puppeteer/issues/1313
27782806

27792807
[34]: #fillfield
27802808

@@ -2790,7 +2818,7 @@ Returns **void** automatically synchronized promise through #recorder
27902818

27912819
[40]: https://github.com/microsoft/playwright/blob/main/docs/src/api/class-browser.md
27922820

2793-
[41]: https://playwright.dev/docs/api/class-page?_highlight=waitfornavi#pagewaitfornavigationoptions
2821+
[41]: https://playwright.dev/docs/api/class-page#page-wait-for-navigation
27942822

27952823
[42]: https://playwright.dev/docs/api/class-page#page-wait-for-url
27962824

docs/helpers/Puppeteer.md

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -49,15 +49,15 @@ Type: [object][4]
4949
* `keepBrowserState` **[boolean][23]?** keep browser state between tests when `restart` is set to false.
5050
* `keepCookies` **[boolean][23]?** keep cookies between tests when `restart` is set to false.
5151
* `waitForAction` **[number][11]?** how long to wait after click, doubleClick or PressKey actions in ms. Default: 100.
52-
* `waitForNavigation` **[string][6]?** when to consider navigation succeeded. Possible options: `load`, `domcontentloaded`, `networkidle0`, `networkidle2`. See [Puppeteer API][26]. Array values are accepted as well.
52+
* `waitForNavigation` **([string][6] | [Array][16]<[string][6]>)?** when to consider navigation succeeded. Possible options: `load`, `domcontentloaded`, `networkidle0`, `networkidle2`. See [Puppeteer API][28]. Array values are accepted as well.
5353
* `pressKeyDelay` **[number][11]?** delay between key presses in ms. Used when calling Puppeteers page.type(...) in fillField/appendField
5454
* `getPageTimeout` **[number][11]?** config option to set maximum navigation time in milliseconds. If the timeout is set to 0, then timeout will be disabled.
5555
* `waitForTimeout` **[number][11]?** default wait* timeout in ms.
5656
* `windowSize` **[string][6]?** default window size. Set a dimension in format WIDTHxHEIGHT like `640x480`.
5757
* `userAgent` **[string][6]?** user-agent string.
5858
* `manualStart` **[boolean][23]?** do not start browser before a test, start it manually inside a helper with `this.helpers["Puppeteer"]._startBrowser()`.
5959
* `browser` **[string][6]?** can be changed to `firefox` when using [puppeteer-firefox][2].
60-
* `chrome` **[object][4]?** pass additional [Puppeteer run options][28].
60+
* `chrome` **[object][4]?** pass additional [Puppeteer run options][29].
6161
* `highlightElement` **[boolean][23]?** highlight the interacting elements. Default: false. Note: only activate under verbose mode (--verbose).
6262

6363
## findElement
@@ -1412,7 +1412,7 @@ I.openNewTab();
14121412
14131413
### pressKey
14141414
1415-
*Note:* Shortcuts like `'Meta'` + `'A'` do not work on macOS ([GoogleChrome/puppeteer#1313][20]).
1415+
*Note:* Shortcuts like `'Meta'` + `'A'` do not work on macOS ([puppeteer/puppeteer#1313][20]).
14161416
14171417
Presses a key in the browser (on a focused element).
14181418
@@ -2501,7 +2501,7 @@ I.waitUrlEquals('http://127.0.0.1:8000/info');
25012501
25022502
Returns **void** automatically synchronized promise through #recorder
25032503
2504-
[1]: https://github.com/GoogleChrome/puppeteer
2504+
[1]: https://github.com/puppeteer/puppeteer
25052505
25062506
[2]: https://codecept.io/helpers/Puppeteer-firefox
25072507
@@ -2539,7 +2539,7 @@ Returns **void** automatically synchronized promise through #recorder
25392539
25402540
[19]: https://pptr.dev/guides/network-interception
25412541
2542-
[20]: https://github.com/GoogleChrome/puppeteer/issues/1313
2542+
[20]: https://github.com/puppeteer/puppeteer/issues/1313
25432543
25442544
[21]: #fillfield
25452545
@@ -2551,8 +2551,10 @@ Returns **void** automatically synchronized promise through #recorder
25512551
25522552
[25]: https://github.com/puppeteer/puppeteer/blob/master/docs/api.md#class-browser
25532553
2554-
[26]: https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#pagewaitfornavigationoptions
2554+
[26]: https://github.com/puppeteer/puppeteer/blob/main/docs/api/puppeteer.page.waitfornavigation.md
25552555
25562556
[27]: https://pptr.dev/api/puppeteer.tracing
25572557
2558-
[28]: https://github.com/GoogleChrome/puppeteer/blob/master/docs/api.md#puppeteerlaunchoptions
2558+
[28]: https://github.com/puppeteer/puppeteer/blob/main/docs/api/puppeteer.waitforoptions.md
2559+
2560+
[29]: https://github.com/puppeteer/puppeteer/blob/main/docs/api/puppeteer.launchoptions.md

0 commit comments

Comments
 (0)