codeceptjs 3.5.14 → 3.6.0-beta.1.ai-healers

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (137) hide show
  1. package/README.md +2 -2
  2. package/bin/codecept.js +66 -30
  3. package/docs/advanced.md +351 -0
  4. package/docs/ai.md +365 -0
  5. package/docs/api.md +323 -0
  6. package/docs/basics.md +979 -0
  7. package/docs/bdd.md +539 -0
  8. package/docs/best.md +237 -0
  9. package/docs/books.md +37 -0
  10. package/docs/bootstrap.md +135 -0
  11. package/docs/build/AI.js +124 -0
  12. package/docs/build/ApiDataFactory.js +410 -0
  13. package/docs/build/Appium.js +2027 -0
  14. package/docs/build/Expect.js +422 -0
  15. package/docs/build/FileSystem.js +228 -0
  16. package/docs/build/GraphQL.js +229 -0
  17. package/docs/build/GraphQLDataFactory.js +309 -0
  18. package/docs/build/JSONResponse.js +338 -0
  19. package/docs/build/Mochawesome.js +71 -0
  20. package/docs/build/Nightmare.js +2152 -0
  21. package/docs/build/Playwright.js +5110 -0
  22. package/docs/build/Protractor.js +2706 -0
  23. package/docs/build/Puppeteer.js +3905 -0
  24. package/docs/build/REST.js +344 -0
  25. package/docs/build/TestCafe.js +2125 -0
  26. package/docs/build/WebDriver.js +4240 -0
  27. package/docs/changelog.md +2572 -0
  28. package/docs/commands.md +266 -0
  29. package/docs/community-helpers.md +58 -0
  30. package/docs/configuration.md +157 -0
  31. package/docs/continuous-integration.md +22 -0
  32. package/docs/custom-helpers.md +306 -0
  33. package/docs/data.md +379 -0
  34. package/docs/detox.md +235 -0
  35. package/docs/docker.md +136 -0
  36. package/docs/email.md +183 -0
  37. package/docs/examples.md +149 -0
  38. package/docs/heal.md +186 -0
  39. package/docs/helpers/ApiDataFactory.md +266 -0
  40. package/docs/helpers/Appium.md +1374 -0
  41. package/docs/helpers/Detox.md +586 -0
  42. package/docs/helpers/Expect.md +275 -0
  43. package/docs/helpers/FileSystem.md +152 -0
  44. package/docs/helpers/GraphQL.md +151 -0
  45. package/docs/helpers/GraphQLDataFactory.md +226 -0
  46. package/docs/helpers/JSONResponse.md +254 -0
  47. package/docs/helpers/Mochawesome.md +8 -0
  48. package/docs/helpers/MockRequest.md +377 -0
  49. package/docs/helpers/Nightmare.md +1305 -0
  50. package/docs/helpers/OpenAI.md +70 -0
  51. package/docs/helpers/Playwright.md +2759 -0
  52. package/docs/helpers/Polly.md +44 -0
  53. package/docs/helpers/Protractor.md +1769 -0
  54. package/docs/helpers/Puppeteer-firefox.md +86 -0
  55. package/docs/helpers/Puppeteer.md +2317 -0
  56. package/docs/helpers/REST.md +218 -0
  57. package/docs/helpers/TestCafe.md +1321 -0
  58. package/docs/helpers/WebDriver.md +2547 -0
  59. package/docs/hooks.md +340 -0
  60. package/docs/index.md +111 -0
  61. package/docs/installation.md +75 -0
  62. package/docs/internal-api.md +266 -0
  63. package/docs/locators.md +339 -0
  64. package/docs/mobile-react-native-locators.md +67 -0
  65. package/docs/mobile.md +338 -0
  66. package/docs/pageobjects.md +291 -0
  67. package/docs/parallel.md +400 -0
  68. package/docs/playwright.md +632 -0
  69. package/docs/plugins.md +1247 -0
  70. package/docs/puppeteer.md +316 -0
  71. package/docs/quickstart.md +162 -0
  72. package/docs/react.md +70 -0
  73. package/docs/reports.md +392 -0
  74. package/docs/secrets.md +36 -0
  75. package/docs/shadow.md +68 -0
  76. package/docs/shared/keys.mustache +31 -0
  77. package/docs/shared/react.mustache +1 -0
  78. package/docs/testcafe.md +174 -0
  79. package/docs/translation.md +247 -0
  80. package/docs/tutorial.md +271 -0
  81. package/docs/typescript.md +180 -0
  82. package/docs/ui.md +59 -0
  83. package/docs/videos.md +28 -0
  84. package/docs/visual.md +202 -0
  85. package/docs/vue.md +143 -0
  86. package/docs/webdriver.md +701 -0
  87. package/docs/wiki/Books-&-Posts.md +27 -0
  88. package/docs/wiki/Community-Helpers-&-Plugins.md +53 -0
  89. package/docs/wiki/Converting-Playwright-to-Istanbul-Coverage.md +61 -0
  90. package/docs/wiki/Examples.md +145 -0
  91. package/docs/wiki/Google-Summer-of-Code-(GSoC)-2020.md +68 -0
  92. package/docs/wiki/Home.md +16 -0
  93. package/docs/wiki/Migration-to-Appium-v2---CodeceptJS.md +83 -0
  94. package/docs/wiki/Release-Process.md +24 -0
  95. package/docs/wiki/Roadmap.md +23 -0
  96. package/docs/wiki/Tests.md +1393 -0
  97. package/docs/wiki/Upgrading-to-CodeceptJS-3.md +153 -0
  98. package/docs/wiki/Videos.md +19 -0
  99. package/lib/actor.js +3 -6
  100. package/lib/ai.js +152 -80
  101. package/lib/cli.js +1 -0
  102. package/lib/command/generate.js +34 -0
  103. package/lib/command/run-workers.js +3 -0
  104. package/lib/command/run.js +3 -0
  105. package/lib/container.js +2 -0
  106. package/lib/heal.js +172 -0
  107. package/lib/helper/AI.js +124 -0
  108. package/lib/helper/Appium.js +12 -36
  109. package/lib/helper/Expect.js +7 -10
  110. package/lib/helper/JSONResponse.js +8 -8
  111. package/lib/helper/Playwright.js +240 -100
  112. package/lib/helper/Puppeteer.js +9 -61
  113. package/lib/helper/REST.js +1 -4
  114. package/lib/helper/WebDriver.js +10 -324
  115. package/lib/index.js +3 -0
  116. package/lib/listener/steps.js +0 -2
  117. package/lib/locator.js +4 -13
  118. package/lib/plugin/heal.js +26 -117
  119. package/lib/recorder.js +11 -5
  120. package/lib/step.js +1 -3
  121. package/lib/store.js +2 -0
  122. package/lib/template/heal.js +39 -0
  123. package/package.json +23 -27
  124. package/typings/index.d.ts +0 -16
  125. package/typings/promiseBasedTypes.d.ts +55 -338
  126. package/typings/types.d.ts +58 -353
  127. package/docs/webapi/dontSeeTraffic.mustache +0 -13
  128. package/docs/webapi/flushNetworkTraffics.mustache +0 -5
  129. package/docs/webapi/grabRecordedNetworkTraffics.mustache +0 -10
  130. package/docs/webapi/seeTraffic.mustache +0 -36
  131. package/docs/webapi/startRecordingTraffic.mustache +0 -8
  132. package/docs/webapi/stopRecordingTraffic.mustache +0 -5
  133. package/docs/webapi/waitForCookie.mustache +0 -9
  134. package/lib/helper/MockServer.js +0 -221
  135. package/lib/helper/errors/ElementAssertion.js +0 -38
  136. package/lib/helper/networkTraffics/utils.js +0 -137
  137. /package/{lib/helper → docs/build}/OpenAI.js +0 -0
@@ -1,221 +0,0 @@
1
- const { mock, settings } = require('pactum');
2
-
3
- /**
4
- * ## Configuration
5
- *
6
- * This helper should be configured in codecept.conf.(js|ts)
7
- *
8
- * @typedef MockServerConfig
9
- * @type {object}
10
- * @prop {number} [port=9393] - Mock server port
11
- * @prop {string} [host="0.0.0.0"] - Mock server host
12
- * @prop {object} [httpsOpts] - key & cert values are the paths to .key and .crt files
13
- */
14
- let config = {
15
- port: 9393,
16
- host: '0.0.0.0',
17
- httpsOpts: {
18
- key: '',
19
- cert: '',
20
- },
21
- };
22
-
23
- /**
24
- * MockServer
25
- *
26
- * The MockServer Helper in CodeceptJS empowers you to mock any server or service via HTTP or HTTPS, making it an excellent tool for simulating REST endpoints and other HTTP-based APIs.
27
- *
28
- * <!-- configuration -->
29
- *
30
- * #### Examples
31
- *
32
- * You can seamlessly integrate MockServer with other helpers like REST or Playwright. Here's a configuration example inside the `codecept.conf.js` file:
33
- *
34
- * ```javascript
35
- * {
36
- * helpers: {
37
- * REST: {...},
38
- * MockServer: {
39
- * // default mock server config
40
- * port: 9393,
41
- * host: '0.0.0.0',
42
- * httpsOpts: {
43
- * key: '',
44
- * cert: '',
45
- * },
46
- * },
47
- * }
48
- * }
49
- * ```
50
- *
51
- * #### Adding Interactions
52
- *
53
- * Interactions add behavior to the mock server. Use the `I.addInteractionToMockServer()` method to include interactions. It takes an interaction object as an argument, containing request and response details.
54
- *
55
- * ```javascript
56
- * I.addInteractionToMockServer({
57
- * request: {
58
- * method: 'GET',
59
- * path: '/api/hello'
60
- * },
61
- * response: {
62
- * status: 200,
63
- * body: {
64
- * 'say': 'hello to mock server'
65
- * }
66
- * }
67
- * });
68
- * ```
69
- *
70
- * #### Request Matching
71
- *
72
- * When a real request is sent to the mock server, it matches the received request with the interactions. If a match is found, it returns the specified response; otherwise, a 404 status code is returned.
73
- *
74
- * - Strong match on HTTP Method, Path, Query Params & JSON body.
75
- * - Loose match on Headers.
76
- *
77
- * ##### Strong Match on Query Params
78
- *
79
- * You can send different responses based on query parameters:
80
- *
81
- * ```javascript
82
- * I.addInteractionToMockServer({
83
- * request: {
84
- * method: 'GET',
85
- * path: '/api/users',
86
- * queryParams: {
87
- * id: 1
88
- * }
89
- * },
90
- * response: {
91
- * status: 200,
92
- * body: 'user 1'
93
- * }
94
- * });
95
- *
96
- * I.addInteractionToMockServer({
97
- * request: {
98
- * method: 'GET',
99
- * path: '/api/users',
100
- * queryParams: {
101
- * id: 2
102
- * }
103
- * },
104
- * response: {
105
- * status: 200,
106
- * body: 'user 2'
107
- * }
108
- * });
109
- * ```
110
- *
111
- * - GET to `/api/users?id=1` will return 'user 1'.
112
- * - GET to `/api/users?id=2` will return 'user 2'.
113
- * - For all other requests, it returns a 404 status code.
114
- *
115
- * ##### Loose Match on Body
116
- *
117
- * When `strict` is set to false, it performs a loose match on query params and response body:
118
- *
119
- * ```javascript
120
- * I.addInteractionToMockServer({
121
- * strict: false,
122
- * request: {
123
- * method: 'POST',
124
- * path: '/api/users',
125
- * body: {
126
- * name: 'john'
127
- * }
128
- * },
129
- * response: {
130
- * status: 200
131
- * }
132
- * });
133
- * ```
134
- *
135
- * - POST to `/api/users` with the body containing `name` as 'john' will return a 200 status code.
136
- * - POST to `/api/users` without the `name` property in the body will return a 404 status code.
137
- *
138
- * Happy testing with MockServer in CodeceptJS! 🚀
139
- *
140
- * ## Methods
141
- */
142
- class MockServer {
143
- constructor(passedConfig) {
144
- settings.setLogLevel('SILENT');
145
- config = { ...passedConfig };
146
- if (global.debugMode) {
147
- settings.setLogLevel('VERBOSE');
148
- }
149
- }
150
-
151
- /**
152
- * Start the mock server
153
- * @param {number} [port] start the mock server with given port
154
- *
155
- * @returns void
156
- */
157
- async startMockServer(port) {
158
- const _config = { ...config };
159
- if (port) _config.port = port;
160
- await mock.setDefaults(_config);
161
- await mock.start();
162
- }
163
-
164
- /**
165
- * Stop the mock server
166
- *
167
- * @returns void
168
- *
169
- */
170
- async stopMockServer() {
171
- await mock.stop();
172
- }
173
-
174
- /**
175
- * An interaction adds behavior to the mock server
176
- *
177
- *
178
- * ```js
179
- * I.addInteractionToMockServer({
180
- * request: {
181
- * method: 'GET',
182
- * path: '/api/hello'
183
- * },
184
- * response: {
185
- * status: 200,
186
- * body: {
187
- * 'say': 'hello to mock server'
188
- * }
189
- * }
190
- * });
191
- * ```
192
- * ```js
193
- * // with query params
194
- * I.addInteractionToMockServer({
195
- * request: {
196
- * method: 'GET',
197
- * path: '/api/hello',
198
- * queryParams: {
199
- * id: 2
200
- * }
201
- * },
202
- * response: {
203
- * status: 200,
204
- * body: {
205
- * 'say': 'hello to mock server'
206
- * }
207
- * }
208
- * });
209
- * ```
210
- *
211
- * @param {CodeceptJS.MockInteraction|object} interaction add behavior to the mock server
212
- *
213
- * @returns void
214
- *
215
- */
216
- async addInteractionToMockServer(interaction) {
217
- await mock.addInteraction(interaction);
218
- }
219
- }
220
-
221
- module.exports = MockServer;
@@ -1,38 +0,0 @@
1
- const Locator = require('../../locator');
2
-
3
- const prefixMessage = 'Element';
4
-
5
- function seeElementError(locator) {
6
- if (typeof locator === 'object') {
7
- locator = JSON.stringify(locator);
8
- }
9
- throw new Error(`${prefixMessage} "${(new Locator(locator))}" is still visible on page.`);
10
- }
11
-
12
- function seeElementInDOMError(locator) {
13
- if (typeof locator === 'object') {
14
- locator = JSON.stringify(locator);
15
- }
16
- throw new Error(`${prefixMessage} "${(new Locator(locator))}" is still seen in DOM.`);
17
- }
18
-
19
- function dontSeeElementError(locator) {
20
- if (typeof locator === 'object') {
21
- locator = JSON.stringify(locator);
22
- }
23
- throw new Error(`${prefixMessage} "${(new Locator(locator))}" is not visible on page.`);
24
- }
25
-
26
- function dontSeeElementInDOMError(locator) {
27
- if (typeof locator === 'object') {
28
- locator = JSON.stringify(locator);
29
- }
30
- throw new Error(`${prefixMessage} "${(new Locator(locator))}" is not seen in DOM.`);
31
- }
32
-
33
- module.exports = {
34
- seeElementError,
35
- dontSeeElementError,
36
- seeElementInDOMError,
37
- dontSeeElementInDOMError,
38
- };
@@ -1,137 +0,0 @@
1
- const createAdvancedTestResults = (url, dataToCheck, requests) => {
2
- // Creates advanced test results for a network traffic check.
3
- // Advanced test results only applies when expected parameters are set
4
- if (!dataToCheck) return '';
5
-
6
- let urlFound = false;
7
- let advancedResults;
8
- requests.forEach((request) => {
9
- // url not found in this request. continue with next request
10
- if (urlFound || !request.url.match(new RegExp(url))) return;
11
- urlFound = true;
12
-
13
- // Url found. Now we create advanced test report for that URL and show which parameters failed
14
- if (!request.requestPostData) {
15
- advancedResults = allParameterValuePairsMatchExtreme(extractQueryObjects(request.url), dataToCheck);
16
- } else if (request.requestPostData) {
17
- advancedResults = allRequestPostDataValuePairsMatchExtreme(request.requestPostData, dataToCheck);
18
- }
19
- });
20
- return advancedResults;
21
- };
22
-
23
- const extractQueryObjects = (queryString) => {
24
- // Converts a string of GET parameters into an array of parameter objects. Each parameter object contains the properties "name" and "value".
25
- if (queryString.indexOf('?') === -1) {
26
- return [];
27
- }
28
- const queryObjects = [];
29
-
30
- const queryPart = queryString.split('?')[1];
31
-
32
- const queryParameters = queryPart.split('&');
33
-
34
- queryParameters.forEach((queryParameter) => {
35
- const keyValue = queryParameter.split('=');
36
- const queryObject = {};
37
- // eslint-disable-next-line prefer-destructuring
38
- queryObject.name = keyValue[0];
39
- queryObject.value = decodeURIComponent(keyValue[1]);
40
- queryObjects.push(queryObject);
41
- });
42
-
43
- return queryObjects;
44
- };
45
-
46
- const allParameterValuePairsMatchExtreme = (queryStringObject, advancedExpectedParameterValuePairs) => {
47
- // More advanced check if all request parameters match with the expectations
48
- let littleReport = '\nQuery parameters:\n';
49
- let success = true;
50
-
51
- for (const expectedKey in advancedExpectedParameterValuePairs) {
52
- if (!Object.prototype.hasOwnProperty.call(advancedExpectedParameterValuePairs, expectedKey)) {
53
- continue;
54
- }
55
- let parameterFound = false;
56
- const expectedValue = advancedExpectedParameterValuePairs[expectedKey];
57
-
58
- for (const queryParameter of queryStringObject) {
59
- if (queryParameter.name === expectedKey) {
60
- parameterFound = true;
61
- if (expectedValue === undefined) {
62
- littleReport += ` ${expectedKey.padStart(10, ' ')}\n`;
63
- } else if (typeof expectedValue === 'object' && expectedValue.base64) {
64
- const decodedActualValue = Buffer.from(queryParameter.value, 'base64').toString('utf8');
65
- if (decodedActualValue === expectedValue.base64) {
66
- littleReport += ` ${expectedKey.padStart(10, ' ')} = base64(${expectedValue.base64})\n`;
67
- } else {
68
- littleReport += ` ✖ ${expectedKey.padStart(10, ' ')} = base64(${expectedValue.base64}) -> actual value: "base64(${decodedActualValue})"\n`;
69
- success = false;
70
- }
71
- } else if (queryParameter.value === expectedValue) {
72
- littleReport += ` ${expectedKey.padStart(10, ' ')} = ${expectedValue}\n`;
73
- } else {
74
- littleReport += ` ✖ ${expectedKey.padStart(10, ' ')} = ${expectedValue} -> actual value: "${queryParameter.value}"\n`;
75
- success = false;
76
- }
77
- }
78
- }
79
-
80
- if (parameterFound === false) {
81
- littleReport += ` ✖ ${expectedKey.padStart(10, ' ')}${expectedValue ? ` = ${JSON.stringify(expectedValue)}` : ''} -> parameter not found in request\n`;
82
- success = false;
83
- }
84
- }
85
-
86
- return success ? true : littleReport;
87
- };
88
-
89
- const allRequestPostDataValuePairsMatchExtreme = (RequestPostDataObject, advancedExpectedRequestPostValuePairs) => {
90
- // More advanced check if all request post data match with the expectations
91
- let littleReport = '\nRequest Post Data:\n';
92
- let success = true;
93
-
94
- for (const expectedKey in advancedExpectedRequestPostValuePairs) {
95
- if (!Object.prototype.hasOwnProperty.call(advancedExpectedRequestPostValuePairs, expectedKey)) {
96
- continue;
97
- }
98
- let keyFound = false;
99
- const expectedValue = advancedExpectedRequestPostValuePairs[expectedKey];
100
-
101
- for (const [key, value] of Object.entries(RequestPostDataObject)) {
102
- if (key === expectedKey) {
103
- keyFound = true;
104
- if (expectedValue === undefined) {
105
- littleReport += ` ${expectedKey.padStart(10, ' ')}\n`;
106
- } else if (typeof expectedValue === 'object' && expectedValue.base64) {
107
- const decodedActualValue = Buffer.from(value, 'base64').toString('utf8');
108
- if (decodedActualValue === expectedValue.base64) {
109
- littleReport += ` ${expectedKey.padStart(10, ' ')} = base64(${expectedValue.base64})\n`;
110
- } else {
111
- littleReport += ` ✖ ${expectedKey.padStart(10, ' ')} = base64(${expectedValue.base64}) -> actual value: "base64(${decodedActualValue})"\n`;
112
- success = false;
113
- }
114
- } else if (value === expectedValue) {
115
- littleReport += ` ${expectedKey.padStart(10, ' ')} = ${expectedValue}\n`;
116
- } else {
117
- littleReport += ` ✖ ${expectedKey.padStart(10, ' ')} = ${expectedValue} -> actual value: "${value}"\n`;
118
- success = false;
119
- }
120
- }
121
- }
122
-
123
- if (keyFound === false) {
124
- littleReport += ` ✖ ${expectedKey.padStart(10, ' ')}${expectedValue ? ` = ${JSON.stringify(expectedValue)}` : ''} -> key not found in request\n`;
125
- success = false;
126
- }
127
- }
128
-
129
- return success ? true : littleReport;
130
- };
131
-
132
- module.exports = {
133
- createAdvancedTestResults,
134
- extractQueryObjects,
135
- allParameterValuePairsMatchExtreme,
136
- allRequestPostDataValuePairsMatchExtreme,
137
- };
File without changes