@testim/testim-cli 3.260.0 → 3.262.0

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 (32) hide show
  1. package/commons/testimServicesApi.js +10 -7
  2. package/executionQueue.js +9 -1
  3. package/npm-shrinkwrap.json +2 -2
  4. package/package.json +1 -1
  5. package/player/stepActions/RefreshStepAction.js +7 -4
  6. package/player/stepActions/baseJsStepAction.js +45 -46
  7. package/player/stepActions/dropFileStepAction.js +11 -12
  8. package/player/stepActions/evaluateExpressionStepAction.js +32 -33
  9. package/player/stepActions/extensionOnlyStepAction.js +3 -4
  10. package/player/stepActions/extractTextStepAction.js +8 -10
  11. package/player/stepActions/hoverStepAction.js +3 -3
  12. package/player/stepActions/locateStepAction.js +39 -34
  13. package/player/stepActions/mouseStepAction.js +36 -34
  14. package/player/stepActions/navigationStepAction.js +7 -8
  15. package/player/stepActions/scrollStepAction.js +22 -22
  16. package/player/stepActions/stepAction.js +21 -21
  17. package/player/stepActions/stepActionRegistrar.js +63 -58
  18. package/player/stepActions/submitStepAction.js +2 -3
  19. package/player/stepActions/textStepAction.js +14 -14
  20. package/player/stepActions/textValidationStepAction.js +50 -38
  21. package/player/stepActions/wheelStepAction.js +5 -11
  22. package/processHandler.js +2 -0
  23. package/reports/junitReporter.js +18 -1
  24. package/runOptions.d.ts +4 -0
  25. package/runOptions.js +8 -1
  26. package/runners/TestPlanRunner.js +20 -19
  27. package/runners/runnerUtils.js +1 -2
  28. package/testRunHandler.js +18 -9
  29. package/testRunStatus.js +205 -157
  30. package/workers/BaseWorker.js +11 -0
  31. package/workers/WorkerExtension.js +117 -91
  32. package/workers/WorkerSelenium.js +8 -3
@@ -183,6 +183,14 @@ function reportExecutionFinished(status, executionId, projectId, success, tmsOpt
183
183
  }), { retries: DEFAULT_REQUEST_RETRY });
184
184
  }
185
185
 
186
+ /**
187
+ * @param {string} projectId
188
+ * @param {string[]} names
189
+ * @param {string[]} planIds
190
+ * @param {string} branch
191
+ * @param {import('../runOptions').RunnerOptions['intersections']} intersections
192
+ * @returns {ReturnType<import('services/src/test-plan/service')['testPlan']['getTestPlanTestList']>}
193
+ */
186
194
  async function getTestPlanTestList(projectId, names, planIds, branch, intersections) {
187
195
  return pRetry(() => postAuth({
188
196
  url: '/testPlan/list',
@@ -206,12 +214,7 @@ async function getTestPlanTestList(projectId, names, planIds, branch, intersecti
206
214
  * testConfigIds?: string[];
207
215
  * intersections: import('../runOptions').RunnerOptions['intersections'];
208
216
  * }} param0
209
- * @returns {globalThis.Promise<{
210
- * tests: any[][];
211
- * branch?: string;
212
- * runName?: string;
213
- * runExists?: boolean;
214
- * }>}
217
+ * @returns {import('services/src/suite/service').RunListResult}
215
218
  */
216
219
  function getSuiteTestList({
217
220
  projectId, labels, testIds, testNames, testConfigNames, suiteNames, suiteIds, branch, rerunFailedByRunId, testConfigIds, intersections,
@@ -247,7 +250,7 @@ function isTestResultCompleted(resultId, projectId, testRetryKey) {
247
250
  }
248
251
 
249
252
  function getTestResults(testId, resultId, projectId, branch) {
250
- return pRetry(() => getWithAuth(`/test/v2/${testId}/result/${resultId}`, { projectId, branch }), { retries: DEFAULT_REQUEST_RETRY });
253
+ return pRetry(() => getWithAuth(`/test/v2/${testId}/result/${resultId}`, { projectId, branch }), { retries: DEFAULT_REQUEST_RETRY, factor: 1 });
251
254
  }
252
255
 
253
256
  function keepAliveGrid(projectId, slots) {
package/executionQueue.js CHANGED
@@ -1,8 +1,16 @@
1
1
  'use strict';
2
2
 
3
- const TestRun = require('./testRunHandler.js');
3
+ const TestRun = require('./testRunHandler');
4
4
 
5
5
  class ExecutionQueue {
6
+ /**
7
+ * @param {string} executionId
8
+ * @param {string} executionName
9
+ * @param {any[]} testList
10
+ * @param {import('./runOptions').RunnerOptions} options
11
+ * @param {string} branchToUse
12
+ * @param {import('./testRunStatus')} testRunStatus
13
+ */
6
14
  constructor(executionId, executionName, testList, options, branchToUse, testStatus) {
7
15
  this._waitingTests = testList.map(testInfo => new TestRun(executionId, executionName, testInfo, options, branchToUse, testStatus));
8
16
  }
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "name": "@testim/testim-cli",
3
- "version": "3.260.0",
3
+ "version": "3.262.0",
4
4
  "lockfileVersion": 2,
5
5
  "requires": true,
6
6
  "packages": {
7
7
  "": {
8
8
  "name": "@testim/testim-cli",
9
- "version": "3.260.0",
9
+ "version": "3.262.0",
10
10
  "license": "Proprietary",
11
11
  "dependencies": {
12
12
  "@applitools/eyes-sdk-core": "13.6.23",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@testim/testim-cli",
3
- "version": "3.260.0",
3
+ "version": "3.262.0",
4
4
  "description": "Command line interface for running Testing on your CI",
5
5
  "author": "Oren Rubin",
6
6
  "contributors": [{
@@ -4,10 +4,13 @@ const StepAction = require('./stepAction');
4
4
  require('bluebird');
5
5
 
6
6
  class RefreshStepAction extends StepAction {
7
- execute() {
8
- return this.driver.reloadTab()
9
- .then(() => ({ success: true }))
10
- .catch(error => ({ success: false, reason: error.message }));
7
+ async execute() {
8
+ try {
9
+ await this.driver.reloadTab();
10
+ return { success: true };
11
+ } catch (error) {
12
+ return { success: false, reason: error.message };
13
+ }
11
14
  }
12
15
  }
13
16
 
@@ -15,6 +15,7 @@ const constants = commonConstants.stepResult;
15
15
  const logger = require('../../commons/logger').getLogger('base-js-step-action');
16
16
 
17
17
  const _ = require('lodash');
18
+ const utils = require('../../utils');
18
19
 
19
20
  function constructWithArguments(constructor, args) {
20
21
  function F() {
@@ -98,46 +99,43 @@ class BaseJsStepAction extends StepAction {
98
99
  const that = this;
99
100
  const retryInterval = that.context.config.retryTimeout;
100
101
  let timeToPlayStep = that.context.data.timeToPlayStep - retryInterval;
101
- return new Promise(resolve => {
102
- function checkScriptStatus() {
103
- return that.executeGetStatus(transactionId)
104
- .catch(err => {
105
- logger.warn('failed to get js status', { err });
106
- return { value: { status: 'exception' } };
107
- })
108
- .then(selRes => {
109
- let res;
110
- try {
111
- res = JSON.parse(selRes ? selRes.value : '{}');
112
- } catch (e) {
113
- logger.warn('non object value', { selRes });
114
- res = { status: 'exception' };
115
- }
116
- const abortReason = that.stepActionUtils.abortedSteps.find(abortedStep => abortedStep.id === that.step.id);
117
- if (abortReason) {
118
- return resolve(abortReason);
119
- }
120
- if (!res) {
121
- return resolve({ success: true });
122
- }
123
- if (res.status && res.status === 'done') {
124
- return resolve(res);
125
- }
126
- if (res.status && res.status === 'failed') {
127
- return resolve({ success: false, shouldRetry: true, result: res.result });
128
- }
129
- if (timeToPlayStep - retryInterval > 0) {
130
- timeToPlayStep -= retryInterval;
131
- setTimeout(checkScriptStatus, retryInterval);
132
- } else {
133
- return resolve(Object.assign({}, res, { success: false, shouldRetry: true }));
134
- }
135
- return undefined;
136
- });
102
+ async function checkScriptStatus() {
103
+ let selRes;
104
+ try {
105
+ selRes = await that.executeGetStatus(transactionId);
106
+ } catch (err) {
107
+ logger.warn('failed to get js status', { err });
108
+ selRes = { value: { status: 'exception' } };
109
+ }
110
+ let res;
111
+ try {
112
+ res = JSON.parse(selRes ? selRes.value : '{}');
113
+ } catch (e) {
114
+ logger.warn('non object value', { selRes });
115
+ res = { status: 'exception' };
116
+ }
117
+ const abortReason = that.stepActionUtils.abortedSteps.find(abortedStep => abortedStep.id === that.step.id);
118
+ if (abortReason) {
119
+ return abortReason;
120
+ }
121
+ if (!res) {
122
+ return { success: true };
123
+ }
124
+ if (res.status && res.status === 'done') {
125
+ return res;
137
126
  }
127
+ if (res.status && res.status === 'failed') {
128
+ return { success: false, shouldRetry: true, result: res.result };
129
+ }
130
+ if (timeToPlayStep - retryInterval <= 0) {
131
+ return Object.assign(res, { success: false, shouldRetry: true });
132
+ }
133
+ timeToPlayStep -= retryInterval;
134
+ await utils.delay(retryInterval);
135
+ return checkScriptStatus();
136
+ }
138
137
 
139
- checkScriptStatus();
140
- });
138
+ return checkScriptStatus();
141
139
  }
142
140
 
143
141
  executeInAut(eventMessage) {
@@ -241,7 +239,7 @@ class BaseJsStepAction extends StepAction {
241
239
  return resp?.success ? this.codeExecDone(resp) : this.codeExecFailed(resp);
242
240
  }
243
241
 
244
- performAction() {
242
+ async performAction() {
245
243
  const step = this.step;
246
244
  const context = this.context;
247
245
 
@@ -262,14 +260,15 @@ class BaseJsStepAction extends StepAction {
262
260
  testResultId: context.testResultId,
263
261
  };
264
262
 
263
+ const browserAndOS = await this.driver.getBrowserAndOS();
264
+ Object.assign(eventMessage, { browser: browserAndOS.browser, browserMajor: browserAndOS.browserMajor });
265
+
266
+ if (!this.context.isPendingPromise) {
267
+ await this.executeInAut(eventMessage);
268
+ }
265
269
 
266
- return this.driver.getBrowserAndOS()
267
- .then(browserAndOS => {
268
- Object.assign(eventMessage, { browser: browserAndOS.browser, browserMajor: browserAndOS.browserMajor });
269
- return this.context.isPendingPromise ? undefined : this.executeInAut(eventMessage);
270
- })
271
- .then(() => this.checkStatus(eventMessage.transactionId))
272
- .then(resp => this.checkCodeResponse(resp));
270
+ const resp = await this.checkStatus(eventMessage.transactionId);
271
+ return await this.checkCodeResponse(resp);
273
272
  }
274
273
 
275
274
  handleExecutionError(err) {
@@ -8,26 +8,25 @@ const { codeSnippets, utils } = require('../../commons/getSessionPlayerRequire')
8
8
  const featureFlagService = require('../../commons/featureFlags');
9
9
 
10
10
  class DropFileStepAction extends StepAction {
11
- performAction() {
11
+ async performAction() {
12
12
  const target = this.context.data[this.step.targetId || 'targetId'];
13
13
  const overrideAzureStorageUrl = featureFlagService.flags.overrideAzureStorageUrl.isEnabled();
14
- //TODO remove if after release session player
15
- return (utils.addTokenToFileUrl ? utils.addTokenToFileUrl(
14
+ const fileUrls = await utils.addTokenToFileUrl(
16
15
  this.context.project.id,
17
16
  this.step.fileUrls,
18
17
  this.stepActionUtils.testimServicesApi,
19
18
  overrideAzureStorageUrl,
20
19
  logger,
21
- ) : Promise.resolve(this.step.fileUrls)).then((fileUrls) => {
22
- const dropFileCode = `
23
- var getLocatedElement = ${codeSnippets.getLocatedElementCode};
24
- var createDropEvent = ${(codeSnippets.createDropEvent ? codeSnippets.createDropEvent : createDropEventLegacy).toString()};
25
- var downloadFileAndFireDropEvent = ${downloadFileAndFireDropEvent.toString()};
26
- return downloadFileAndFireDropEvent.apply(null, arguments)
27
- `;
20
+ );
28
21
 
29
- return this.driver.executeJSWithArray(dropFileCode, [target.locatedElement, fileUrls]).then(() => {});
30
- });
22
+ const dropFileCode = `
23
+ var getLocatedElement = ${codeSnippets.getLocatedElementCode};
24
+ var createDropEvent = ${(codeSnippets.createDropEvent ? codeSnippets.createDropEvent : createDropEventLegacy).toString()};
25
+ var downloadFileAndFireDropEvent = ${downloadFileAndFireDropEvent.toString()};
26
+ return downloadFileAndFireDropEvent.apply(null, arguments)
27
+ `;
28
+
29
+ return await this.driver.executeJSWithArray(dropFileCode, [target.locatedElement, fileUrls]);
31
30
  }
32
31
  }
33
32
 
@@ -1,6 +1,5 @@
1
1
  'use strict';
2
2
 
3
- const Promise = require('bluebird');
4
3
  const sessionPlayer = require('../../commons/getSessionPlayerRequire');
5
4
  const StepAction = require('./stepAction');
6
5
 
@@ -10,44 +9,44 @@ const logger = require('../../commons/logger').getLogger('evaluate-expression-st
10
9
  const _ = require('lodash');
11
10
 
12
11
  class EvaluateExpressionStepAction extends StepAction {
13
- execute() {
12
+ async execute() {
14
13
  const step = this.step;
15
14
  const context = this.context;
16
15
  const exportsGlobal = this.exportsGlobal;
17
16
  const exportsTest = this.exportsTest;
18
17
 
19
- return new Promise((resolve, reject) => {
20
- try {
21
- logger.info('runner running incoming params evaluation');
22
- let incomingParams = context.incomingParams || {};
23
- if (_.isEmpty(incomingParams)) {
24
- incomingParams = stepParamBuilder.getStepInputs(step, context, exportsGlobal, exportsTest);
25
- }
26
-
27
- const params = ['context', ...incomingParams.as.functionParameters];
28
- const args = [context, ...incomingParams.as.functionArguments];
29
- const expressionToEvaluate = step.subType === 'text' ? `'${step.expression.replace(/'/g, "\\\'")}'` : step.expression;
30
- const code = (`return ${expressionToEvaluate}`).replace(/\n/g, '\\n');
31
- const textEvaluateFunction = Function.apply(Function, params.concat([code]));
32
- const evaluatedText = textEvaluateFunction.apply(null, args);
33
-
34
- context.data[step.targetName] = evaluatedText;
35
- context.data[step.targetId] = evaluatedText;
36
- if (context.internalParams) {
37
- context.internalParams.add(step.targetId);
38
- }
39
-
40
- const result = {
41
- success: true,
42
- evaluatedText,
43
- data: context.data,
44
- };
45
-
46
- resolve(result);
47
- } catch (e) {
48
- reject({ errorType: constants.EVALUATE_EXPRESSION_EXCEPTION, resultInfo: { exception: e.toString() }, success: false });
18
+ try {
19
+ logger.info('runner running incoming params evaluation');
20
+ let incomingParams = context.incomingParams || {};
21
+ if (_.isEmpty(incomingParams)) {
22
+ incomingParams = stepParamBuilder.getStepInputs(step, context, exportsGlobal, exportsTest);
49
23
  }
50
- });
24
+
25
+ const params = ['context', ...incomingParams.as.functionParameters];
26
+ const args = [context, ...incomingParams.as.functionArguments];
27
+ const expressionToEvaluate = step.subType === 'text' ? `'${step.expression.replace(/'/g, "\\\'")}'` : step.expression;
28
+ const code = `return ${expressionToEvaluate}`.replace(/\n/g, '\\n');
29
+ const textEvaluateFunction = Function.apply(Function, params.concat([code]));
30
+ const evaluatedText = textEvaluateFunction.apply(null, args);
31
+
32
+ context.data[step.targetName] = evaluatedText;
33
+ context.data[step.targetId] = evaluatedText;
34
+ if (context.internalParams) {
35
+ context.internalParams.add(step.targetId);
36
+ }
37
+
38
+ const result = {
39
+ success: true,
40
+ evaluatedText,
41
+ data: context.data,
42
+ };
43
+
44
+ return result;
45
+ } catch (e) {
46
+ // TODO: Fix throwing non-error
47
+ // eslint-disable-next-line no-throw-literal
48
+ throw { errorType: constants.EVALUATE_EXPRESSION_EXCEPTION, resultInfo: { exception: e.toString() }, success: false };
49
+ }
51
50
  }
52
51
  }
53
52
 
@@ -1,12 +1,11 @@
1
1
  const StepAction = require('./stepAction');
2
- const Promise = require('bluebird');
3
2
 
4
3
  class ExtensionOnlyStepAction extends StepAction {
5
- performAction() {
6
- return Promise.resolve({
4
+ async performAction() {
5
+ return {
7
6
  success: 'skipped',
8
7
  reason: 'This step can run only on Chrome',
9
- });
8
+ };
10
9
  }
11
10
  }
12
11
 
@@ -3,18 +3,16 @@
3
3
  const StepAction = require('./stepAction');
4
4
 
5
5
  class ExtractTextStepAction extends StepAction {
6
- performAction() {
6
+ async performAction() {
7
7
  const paramName = this.step.extractTextParamName;
8
8
 
9
- return this.stepActionUtils.extractTargetText(this.getTarget())
10
- .then(extractedText => {
11
- this.context.data.exports = this.context.data.exports || {};
12
- this.context.data.exports[paramName] = extractedText;
13
- return {
14
- success: true,
15
- data: this.context.data,
16
- };
17
- });
9
+ const extractedText = await this.stepActionUtils.extractTargetText(this.getTarget());
10
+ this.context.data.exports = this.context.data.exports || {};
11
+ this.context.data.exports[paramName] = extractedText;
12
+ return {
13
+ success: true,
14
+ data: this.context.data,
15
+ };
18
16
  }
19
17
  }
20
18
 
@@ -21,7 +21,7 @@ class HoverStepAction extends StepAction {
21
21
  this.getTarget().rect;
22
22
  }
23
23
 
24
- performAction() {
24
+ async performAction() {
25
25
  const target = this.getTarget();
26
26
  const { seleniumElement, rectWithoutFrameOffset, rect } = target;
27
27
 
@@ -49,8 +49,8 @@ class HoverStepAction extends StepAction {
49
49
  clickOffset: { x: Math.floor(clickOffsetX), y: Math.floor(clickOffsetY) },
50
50
  };
51
51
 
52
- return this.driver.hover(seleniumElement, offsets)
53
- .then(() => ({ success: true }));
52
+ await this.driver.hover(seleniumElement, offsets);
53
+ return { success: true };
54
54
  }
55
55
  }
56
56
 
@@ -1,3 +1,5 @@
1
+ // @ts-check
2
+
1
3
  'use strict';
2
4
 
3
5
  const StepAction = require('./stepAction');
@@ -14,15 +16,16 @@ const {
14
16
 
15
17
  const DEFAULT_VISIBILITY_RESULT = { opacity: 1, clientRects: {} };
16
18
 
19
+ /**
20
+ * @param {import('../webdriver')} driver
21
+ */
17
22
  function createUtils(driver) {
18
23
  return {
19
24
  getFrameIdByTestimFrameId() { },
20
25
 
21
- setElementResultDataOnContext(target) {
22
- return driver.getElement(target.locatedElement)
23
- .then(seleniumResponse => {
24
- target.seleniumElement = seleniumResponse.value;
25
- });
26
+ async setElementResultDataOnContext(target) {
27
+ const seleniumResponse = await driver.getElement(target.locatedElement);
28
+ target.seleniumElement = seleniumResponse.value;
26
29
  },
27
30
 
28
31
  getElementRectangle(target) {
@@ -76,14 +79,18 @@ function createUtils(driver) {
76
79
  },
77
80
 
78
81
  /** @type {typeof import('clickim/src/background/stepActions/locateStepAction').LocateStepAction['isVisible']} */
79
- isVisible(target, targetElement, rect, locateStep, frameHandler, allOffsets, dom) {
80
- const skipVisibilityCheck =
81
- featureFlags.flags.disableEdgeVisibilityChecks.isEnabled() && driver.isEdge();
82
+ async isVisible(target, targetElement, rect, locateStep, frameHandler, allOffsets, dom) {
83
+ const skipVisibilityCheck = featureFlags.flags.disableEdgeVisibilityChecks.isEnabled() && driver.isEdge();
82
84
 
83
85
  if (skipVisibilityCheck) {
84
86
  logger.info('bypassed visibility check because of feature flag');
85
87
  target.visibilityCheckSkipped = skipVisibilityCheck;
86
- return driver.isVisible(target.seleniumElement).catch(() => { }).then(() => true);
88
+ try {
89
+ await driver.isVisible(target.seleniumElement);
90
+ } catch {
91
+ /* ignored */
92
+ }
93
+ return true;
87
94
  }
88
95
 
89
96
  const useNativeVisibilityCheck = this.shouldUseNativeVisibilityCheck(locateStep, driver, visibilityUtils, positionUtils);
@@ -91,35 +98,33 @@ function createUtils(driver) {
91
98
  return driver.isVisible(target.seleniumElement);
92
99
  }
93
100
 
94
- const handler = res => {
95
- if (!targetElement || locatorBuilderUtils.isEmptyResult(targetElement)) {
96
- return Promise.resolve({ visible: false, invisibleReason: 'element not found' });
97
- }
98
- const middlePosition = positionUtils.calculateElementMiddlePoint(rect);
99
- const points = [middlePosition, positionUtils.calculateClickPoint(locateStep.clickOffset, rect)].filter(Boolean);
100
- const code = codeSnippets.getVisibilityCode.getCompoundVisibilityInfoCode(target.locatedElement, points, false, locateStep);
101
- return driver.execute(`return ${code}`)
102
- .catch(err => {
103
- logger.error('failed to execute getVisibilityCode', { err });
104
- throw err;
105
- })
106
- .then((response = {}) => {
107
- const { value: result } = response;
108
- const elementVisibilityInfo = result.elementVisibilityInfo || DEFAULT_VISIBILITY_RESULT;
109
- const [middleElementFromPoint, clickElementFromPoint] = result.elementsFromPointResults || [null, null];
110
-
111
- return visibilityUtils.checkElementVisibility(elementVisibilityInfo, locateStep, clickElementFromPoint, middleElementFromPoint, dom, targetElement);
112
- });
113
- };
114
-
115
101
  if (!target.seleniumElement) {
116
- return Promise.resolve({ visible: false, invisibleReason: 'element not found' });
102
+ return { visible: false, invisibleReason: 'element not found' };
117
103
  }
118
104
 
119
105
  // this is here for the side effects.
120
- return driver.isVisible(target.seleniumElement)
121
- .catch(() => { })
122
- .then(handler);
106
+ try {
107
+ await driver.isVisible(target.seleniumElement);
108
+ } catch {
109
+ /* ignored */
110
+ }
111
+ if (!targetElement || locatorBuilderUtils.isEmptyResult(targetElement)) {
112
+ return { visible: false, invisibleReason: 'element not found' };
113
+ }
114
+ const middlePosition = positionUtils.calculateElementMiddlePoint(rect);
115
+ const points = [middlePosition, positionUtils.calculateClickPoint(locateStep.clickOffset, rect)].filter(Boolean);
116
+ const code = codeSnippets.getVisibilityCode.getCompoundVisibilityInfoCode(target.locatedElement, points, false, locateStep);
117
+ let response;
118
+ try {
119
+ response = await driver.execute(`return ${code}`);
120
+ } catch (err) {
121
+ logger.error('failed to execute getVisibilityCode', { err });
122
+ throw err;
123
+ }
124
+ const { value } = response || {};
125
+ const elementVisibilityInfo = value.elementVisibilityInfo || DEFAULT_VISIBILITY_RESULT;
126
+ const [middleElementFromPoint, clickElementFromPoint] = value.elementsFromPointResults || [null, null];
127
+ return visibilityUtils.checkElementVisibility(elementVisibilityInfo, locateStep, clickElementFromPoint, middleElementFromPoint, dom, targetElement);
123
128
  },
124
129
 
125
130
  scrollToElement(frameHandler, locatedElement) {
@@ -1,3 +1,5 @@
1
+ // @ts-check
2
+
1
3
  const StepAction = require('./stepAction');
2
4
  const html5dndAction = require('./scripts/html5dragAction');
3
5
  const html5dndActionV2 = require('./scripts/html5dragActionV2');
@@ -22,7 +24,7 @@ class MouseStepAction extends StepAction {
22
24
  };
23
25
  }
24
26
 
25
- clickJs() {
27
+ async clickJs() {
26
28
  const step = this.step;
27
29
  const context = this.context;
28
30
  const target = context.data[step.targetId || 'targetId'];
@@ -30,7 +32,7 @@ class MouseStepAction extends StepAction {
30
32
  const events = step.events;
31
33
 
32
34
  if (!events?.length) {
33
- return Promise.resolve();
35
+ return undefined;
34
36
  }
35
37
 
36
38
  const eventMessage = {
@@ -55,18 +57,19 @@ class MouseStepAction extends StepAction {
55
57
  // values between 0 and -1 -_-.
56
58
  const eventParam = this.driver.isEdge() ? JSON.stringify(eventMessage) : eventMessage;
57
59
 
58
- return this.driver.executeCodeAsync(doClickCode, timeout, eventParam)
59
- .then(result => {
60
- if (result.value?.success) {
61
- return { success: true };
62
- }
63
- return { success: false };
64
- })
65
- .catch(err => ({
60
+ try {
61
+ const result = await this.driver.executeCodeAsync(doClickCode, timeout, eventParam);
62
+ if (result.value?.success) {
63
+ return { success: true };
64
+ }
65
+ return { success: false };
66
+ } catch (err) {
67
+ return {
66
68
  success: false,
67
69
  reason: err.message,
68
70
  exception: err,
69
- }));
71
+ };
72
+ }
70
73
  }
71
74
 
72
75
  isWithinBounds(start, end, point) {
@@ -126,14 +129,14 @@ class MouseStepAction extends StepAction {
126
129
  this.addOffsetToEvents(this.getEventSequenceOffset());
127
130
  }
128
131
 
129
- dragPathJs() {
132
+ async dragPathJs() {
130
133
  const step = this.step;
131
134
  const context = this.context;
132
135
  const target = context.data[step.targetId || 'targetId'];
133
136
  const timeout = context.data.timeToPlayStep + 3000;
134
137
 
135
138
  if (!this.step.events || !this.step.events.length) {
136
- return Promise.resolve();
139
+ return undefined;
137
140
  }
138
141
 
139
142
  this.fixAbsoluteDragEventSequence();
@@ -158,18 +161,19 @@ class MouseStepAction extends StepAction {
158
161
  return doDragPath.apply(null, arguments);
159
162
  `;
160
163
 
161
- return this.driver.executeCodeAsync(doDragPathCode, timeout, eventMessage)
162
- .then(result => {
163
- if (result.value?.success) {
164
- return { success: true };
165
- }
166
- return { success: false };
167
- })
168
- .catch(err => ({
164
+ try {
165
+ const result = await this.driver.executeCodeAsync(doDragPathCode, timeout, eventMessage);
166
+ if (result.value?.success) {
167
+ return { success: true };
168
+ }
169
+ return { success: false };
170
+ } catch (err) {
171
+ return {
169
172
  success: false,
170
173
  reason: err.message,
171
174
  exception: err,
172
- }));
175
+ };
176
+ }
173
177
  }
174
178
 
175
179
  chooseAndRunAction() {
@@ -295,18 +299,16 @@ class MouseStepAction extends StepAction {
295
299
  return this.driver.leftClick(seleniumElement, offsets);
296
300
  }
297
301
 
298
- performAction() {
299
- return this.chooseAndRunAction()
300
- .then(res => {
301
- if (!res.status && res.value && res.value.keep) {
302
- res = res.value;
303
- }
304
- if (res.keep) {
305
- delete res.keep;
306
- return res;
307
- }
308
- return undefined;
309
- });
302
+ async performAction() {
303
+ let res = await this.chooseAndRunAction();
304
+ if (!res.status && res.value && res.value.keep) {
305
+ res = res.value;
306
+ }
307
+ if (res.keep) {
308
+ delete res.keep;
309
+ return res;
310
+ }
311
+ return undefined;
310
312
  }
311
313
 
312
314
  addDragendIfNeeded(events) {