@appium/base-driver 9.17.0 → 10.0.0-beta.1

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 (81) hide show
  1. package/build/lib/basedriver/capabilities.d.ts.map +1 -1
  2. package/build/lib/basedriver/capabilities.js +2 -4
  3. package/build/lib/basedriver/capabilities.js.map +1 -1
  4. package/build/lib/basedriver/commands/timeout.js +7 -25
  5. package/build/lib/basedriver/commands/timeout.js.map +1 -1
  6. package/build/lib/basedriver/core.d.ts +0 -8
  7. package/build/lib/basedriver/core.d.ts.map +1 -1
  8. package/build/lib/basedriver/core.js +8 -18
  9. package/build/lib/basedriver/core.js.map +1 -1
  10. package/build/lib/basedriver/driver.js +2 -2
  11. package/build/lib/basedriver/driver.js.map +1 -1
  12. package/build/lib/basedriver/helpers.d.ts +9 -1
  13. package/build/lib/basedriver/helpers.d.ts.map +1 -1
  14. package/build/lib/basedriver/helpers.js +56 -142
  15. package/build/lib/basedriver/helpers.js.map +1 -1
  16. package/build/lib/basedriver/validation.d.ts +7 -0
  17. package/build/lib/basedriver/validation.d.ts.map +1 -0
  18. package/build/lib/basedriver/validation.js +130 -0
  19. package/build/lib/basedriver/validation.js.map +1 -0
  20. package/build/lib/express/middleware.d.ts +0 -6
  21. package/build/lib/express/middleware.d.ts.map +1 -1
  22. package/build/lib/express/middleware.js +12 -64
  23. package/build/lib/express/middleware.js.map +1 -1
  24. package/build/lib/express/server.d.ts.map +1 -1
  25. package/build/lib/express/server.js +1 -2
  26. package/build/lib/express/server.js.map +1 -1
  27. package/build/lib/helpers/capabilities.d.ts +13 -6
  28. package/build/lib/helpers/capabilities.d.ts.map +1 -1
  29. package/build/lib/helpers/capabilities.js +7 -0
  30. package/build/lib/helpers/capabilities.js.map +1 -1
  31. package/build/lib/index.d.ts +1 -0
  32. package/build/lib/index.d.ts.map +1 -1
  33. package/build/lib/index.js +3 -1
  34. package/build/lib/index.js.map +1 -1
  35. package/build/lib/jsonwp-proxy/proxy.d.ts +0 -8
  36. package/build/lib/jsonwp-proxy/proxy.d.ts.map +1 -1
  37. package/build/lib/jsonwp-proxy/proxy.js +1 -29
  38. package/build/lib/jsonwp-proxy/proxy.js.map +1 -1
  39. package/build/lib/protocol/errors.d.ts +171 -277
  40. package/build/lib/protocol/errors.d.ts.map +1 -1
  41. package/build/lib/protocol/errors.js +201 -421
  42. package/build/lib/protocol/errors.js.map +1 -1
  43. package/build/lib/protocol/helpers.d.ts +6 -6
  44. package/build/lib/protocol/helpers.d.ts.map +1 -1
  45. package/build/lib/protocol/helpers.js +11 -7
  46. package/build/lib/protocol/helpers.js.map +1 -1
  47. package/build/lib/protocol/protocol.d.ts +5 -0
  48. package/build/lib/protocol/protocol.d.ts.map +1 -1
  49. package/build/lib/protocol/protocol.js +23 -23
  50. package/build/lib/protocol/protocol.js.map +1 -1
  51. package/build/lib/protocol/routes.d.ts +6 -715
  52. package/build/lib/protocol/routes.d.ts.map +1 -1
  53. package/build/lib/protocol/routes.js +16 -481
  54. package/build/lib/protocol/routes.js.map +1 -1
  55. package/build/lib/protocol/validators.d.ts +4 -7
  56. package/build/lib/protocol/validators.d.ts.map +1 -1
  57. package/build/lib/protocol/validators.js +4 -24
  58. package/build/lib/protocol/validators.js.map +1 -1
  59. package/lib/basedriver/capabilities.ts +2 -4
  60. package/lib/basedriver/commands/timeout.ts +11 -34
  61. package/lib/basedriver/core.ts +10 -19
  62. package/lib/basedriver/driver.ts +3 -3
  63. package/lib/basedriver/helpers.js +61 -167
  64. package/lib/basedriver/validation.ts +145 -0
  65. package/lib/express/middleware.js +16 -75
  66. package/lib/express/server.js +1 -3
  67. package/lib/helpers/capabilities.js +9 -4
  68. package/lib/index.js +2 -0
  69. package/lib/jsonwp-proxy/proxy.js +2 -33
  70. package/lib/protocol/{errors.js → errors.ts} +322 -436
  71. package/lib/protocol/helpers.js +12 -8
  72. package/lib/protocol/protocol.js +25 -23
  73. package/lib/protocol/routes.js +18 -491
  74. package/lib/protocol/validators.ts +19 -0
  75. package/package.json +10 -10
  76. package/build/lib/basedriver/desired-caps.d.ts +0 -5
  77. package/build/lib/basedriver/desired-caps.d.ts.map +0 -1
  78. package/build/lib/basedriver/desired-caps.js +0 -92
  79. package/build/lib/basedriver/desired-caps.js.map +0 -1
  80. package/lib/basedriver/desired-caps.js +0 -103
  81. package/lib/protocol/validators.js +0 -41
@@ -5,55 +5,48 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
6
  exports.errors = exports.ProxyRequestError = exports.BadParametersError = exports.UnableToCaptureScreen = exports.NotImplementedError = exports.NotYetImplementedError = exports.InvalidContextError = exports.NoSuchContextError = exports.MoveTargetOutOfBoundsError = exports.SessionNotCreatedError = exports.InvalidSelectorError = exports.IMEEngineActivationFailedError = exports.IMENotAvailableError = exports.InvalidCoordinatesError = exports.InvalidElementCoordinatesError = exports.ScriptTimeoutError = exports.NoSuchAlertError = exports.NoAlertOpenError = exports.UnexpectedAlertOpenError = exports.UnableToSetCookieError = exports.NoSuchCookieError = exports.InvalidCookieDomainError = exports.InvalidArgumentError = exports.NoSuchWindowError = exports.TimeoutError = exports.XPathLookupError = exports.JavaScriptError = exports.InsecureCertificateError = exports.ElementNotInteractableError = exports.ElementClickInterceptedError = exports.ElementIsNotSelectableError = exports.UnsupportedOperationError = exports.UnknownMethodError = exports.UnknownError = exports.InvalidElementStateError = exports.ElementNotVisibleError = exports.StaleElementReferenceError = exports.UnknownCommandError = exports.NoSuchFrameError = exports.NoSuchElementError = exports.NoSuchDriverError = exports.ProtocolError = void 0;
7
7
  exports.isErrorType = isErrorType;
8
- exports.isUnknownError = isUnknownError;
9
8
  exports.errorFromMJSONWPStatusCode = errorFromMJSONWPStatusCode;
10
9
  exports.errorFromW3CJsonCode = errorFromW3CJsonCode;
11
10
  exports.getResponseForW3CError = getResponseForW3CError;
12
- exports.getResponseForJsonwpError = getResponseForJsonwpError;
13
11
  const lodash_1 = __importDefault(require("lodash"));
14
12
  const support_1 = require("@appium/support");
15
13
  const http_status_codes_1 = require("http-status-codes");
16
14
  const mjsonwpLog = support_1.logger.getLogger('MJSONWP');
17
15
  const w3cLog = support_1.logger.getLogger('W3C');
18
- const W3C_UNKNOWN_ERROR = 'unknown error';
19
16
  class BaseError extends Error {
20
- constructor(message = '') {
17
+ constructor(message = '', cause) {
21
18
  super(message);
22
- /** @type {[string, () => any][]} */
23
- const propsMap = [
24
- ['message', () => message],
25
- ['name', () => this.constructor.name],
26
- ['stack', () => (new Error(message)).stack],
27
- ];
19
+ this.cause = cause;
20
+ this.message = message;
21
+ this.name = this.constructor.name;
22
+ this._formatStack();
23
+ }
24
+ _formatStack() {
28
25
  // eslint-disable-next-line no-prototype-builtins
29
- const shouldSkipStack = Error.hasOwnProperty('captureStackTrace');
30
- for (const [propName, valueGetter] of propsMap) {
31
- if (propName === 'stack' && shouldSkipStack) {
32
- continue;
33
- }
34
- Object.defineProperty(this, propName, {
35
- configurable: true,
36
- enumerable: false,
37
- value: valueGetter(),
38
- writable: true,
39
- });
40
- }
41
- if (shouldSkipStack) {
26
+ if (Error.hasOwnProperty('captureStackTrace') && lodash_1.default.isEmpty(this.stack)) {
42
27
  Error.captureStackTrace(this, this.constructor);
43
28
  }
29
+ if (!lodash_1.default.isString(this.cause?.stack)) {
30
+ return;
31
+ }
32
+ if (lodash_1.default.isEmpty(this.stack)) {
33
+ this.stack = this.cause.stack;
34
+ return;
35
+ }
36
+ const stackLines = this.stack?.split('\n') ?? [];
37
+ stackLines.push('The above error is caused by');
38
+ stackLines.push(...this.cause.stack.split('\n'));
39
+ this.stack = stackLines.join('\n');
44
40
  }
45
41
  }
46
42
  // base error class for all of our errors
47
43
  class ProtocolError extends BaseError {
48
- constructor(msg, jsonwpCode, w3cStatus, error) {
49
- super(msg);
50
- this.jsonwpCode = jsonwpCode;
51
- this.error = error || W3C_UNKNOWN_ERROR;
52
- if (this.jsonwpCode === null) {
53
- this.jsonwpCode = 13;
54
- }
55
- this.w3cStatus = w3cStatus || http_status_codes_1.StatusCodes.BAD_REQUEST;
56
- this._stacktrace = null;
44
+ constructor(msg, jsonwpCode, w3cStatus, w3cErrorSignature, cause) {
45
+ super(msg, cause);
46
+ this.jsonwpCode = jsonwpCode ?? UnknownError.code();
47
+ this.error = w3cErrorSignature ?? UnknownError.error();
48
+ this.w3cStatus = w3cStatus ?? UnknownError.w3cStatus();
49
+ this._stacktrace = undefined;
57
50
  }
58
51
  get stacktrace() {
59
52
  return this._stacktrace || this.stack;
@@ -63,14 +56,14 @@ class ProtocolError extends BaseError {
63
56
  }
64
57
  /**
65
58
  * Get the Bidi protocol version of an error
66
- * @param {string|number} id - the id used in the request for which this error forms the response
59
+ * @param id - the id used in the request for which this error forms the response
67
60
  * @see https://w3c.github.io/webdriver-bidi/#protocol-definition
68
- * @returns {import('@appium/types').ErrorBiDiCommandResponse} The object conforming to the shape of a BiDi error response
61
+ * @returns The object conforming to the shape of a BiDi error response
69
62
  */
70
63
  bidiErrObject(id) {
71
64
  // if we don't have an id, the client didn't send one, so we have nothing to send back.
72
65
  // send back zero rather than making something up
73
- const intId = /** @type {number} */ (lodash_1.default.isInteger(id) ? id : (parseInt(`${id}`, 10) || 0));
66
+ const intId = (lodash_1.default.isInteger(id) ? id : (parseInt(`${id}`, 10) || 0));
74
67
  return {
75
68
  id: intId,
76
69
  type: 'error',
@@ -95,11 +88,8 @@ class NoSuchDriverError extends ProtocolError {
95
88
  static error() {
96
89
  return 'invalid session id';
97
90
  }
98
- /**
99
- * @param {string} [message] error message
100
- */
101
- constructor(message) {
102
- super(message || 'A session is either terminated or not started', NoSuchDriverError.code(), NoSuchDriverError.w3cStatus(), NoSuchDriverError.error());
91
+ constructor(message = '', cause) {
92
+ super(message || 'A session is either terminated or not started', NoSuchDriverError.code(), NoSuchDriverError.w3cStatus(), NoSuchDriverError.error(), cause);
103
93
  }
104
94
  }
105
95
  exports.NoSuchDriverError = NoSuchDriverError;
@@ -113,12 +103,9 @@ class NoSuchElementError extends ProtocolError {
113
103
  static error() {
114
104
  return 'no such element';
115
105
  }
116
- /**
117
- * @param {string} [message] error message
118
- */
119
- constructor(message) {
106
+ constructor(message = '', cause) {
120
107
  super(message ||
121
- 'An element could not be located on the page using the given ' + 'search parameters.', NoSuchElementError.code(), NoSuchElementError.w3cStatus(), NoSuchElementError.error());
108
+ 'An element could not be located on the page using the given ' + 'search parameters.', NoSuchElementError.code(), NoSuchElementError.w3cStatus(), NoSuchElementError.error(), cause);
122
109
  }
123
110
  }
124
111
  exports.NoSuchElementError = NoSuchElementError;
@@ -132,14 +119,10 @@ class NoSuchFrameError extends ProtocolError {
132
119
  static w3cStatus() {
133
120
  return http_status_codes_1.StatusCodes.NOT_FOUND;
134
121
  }
135
- /**
136
- *
137
- * @param {string} [message]
138
- */
139
- constructor(message) {
122
+ constructor(message = '', cause) {
140
123
  super(message ||
141
124
  'A request to switch to a frame could not be satisfied because ' +
142
- 'the frame could not be found.', NoSuchFrameError.code(), NoSuchFrameError.w3cStatus(), NoSuchFrameError.error());
125
+ 'the frame could not be found.', NoSuchFrameError.code(), NoSuchFrameError.w3cStatus(), NoSuchFrameError.error(), cause);
143
126
  }
144
127
  }
145
128
  exports.NoSuchFrameError = NoSuchFrameError;
@@ -153,15 +136,11 @@ class UnknownCommandError extends ProtocolError {
153
136
  static error() {
154
137
  return 'unknown command';
155
138
  }
156
- /**
157
- *
158
- * @param {string} [message]
159
- */
160
- constructor(message) {
139
+ constructor(message = '', cause) {
161
140
  super(message ||
162
141
  'The requested resource could not be found, or a request was ' +
163
142
  'received using an HTTP method that is not supported by the mapped ' +
164
- 'resource.', UnknownCommandError.code(), UnknownCommandError.w3cStatus(), UnknownCommandError.error());
143
+ 'resource.', UnknownCommandError.code(), UnknownCommandError.w3cStatus(), UnknownCommandError.error(), cause);
165
144
  }
166
145
  }
167
146
  exports.UnknownCommandError = UnknownCommandError;
@@ -175,14 +154,10 @@ class StaleElementReferenceError extends ProtocolError {
175
154
  static error() {
176
155
  return 'stale element reference';
177
156
  }
178
- /**
179
- *
180
- * @param {string} [message]
181
- */
182
- constructor(message) {
157
+ constructor(message = '', cause) {
183
158
  super(message ||
184
159
  'An element command failed because the referenced element is no ' +
185
- 'longer attached to the DOM.', StaleElementReferenceError.code(), StaleElementReferenceError.w3cStatus(), StaleElementReferenceError.error());
160
+ 'longer attached to the DOM.', StaleElementReferenceError.code(), StaleElementReferenceError.w3cStatus(), StaleElementReferenceError.error(), cause);
186
161
  }
187
162
  }
188
163
  exports.StaleElementReferenceError = StaleElementReferenceError;
@@ -196,13 +171,10 @@ class ElementNotVisibleError extends ProtocolError {
196
171
  static error() {
197
172
  return 'element not visible';
198
173
  }
199
- /**
200
- * @param {string} [message] error message
201
- */
202
- constructor(message) {
174
+ constructor(message = '', cause) {
203
175
  super(message ||
204
176
  'An element command could not be completed because the element is ' +
205
- 'not visible on the page.', ElementNotVisibleError.code(), ElementNotVisibleError.w3cStatus(), ElementNotVisibleError.error());
177
+ 'not visible on the page.', ElementNotVisibleError.code(), ElementNotVisibleError.w3cStatus(), ElementNotVisibleError.error(), cause);
206
178
  }
207
179
  }
208
180
  exports.ElementNotVisibleError = ElementNotVisibleError;
@@ -216,14 +188,10 @@ class InvalidElementStateError extends ProtocolError {
216
188
  static error() {
217
189
  return 'invalid element state';
218
190
  }
219
- /**
220
- *
221
- * @param {string} [message]
222
- */
223
- constructor(message) {
191
+ constructor(message = '', cause) {
224
192
  super(message ||
225
193
  'An element command could not be completed because the element is ' +
226
- 'in an invalid state (e.g. attempting to click a disabled element).', InvalidElementStateError.code(), InvalidElementStateError.w3cStatus(), InvalidElementStateError.error());
194
+ 'in an invalid state (e.g. attempting to click a disabled element).', InvalidElementStateError.code(), InvalidElementStateError.w3cStatus(), InvalidElementStateError.error(), cause);
227
195
  }
228
196
  }
229
197
  exports.InvalidElementStateError = InvalidElementStateError;
@@ -235,15 +203,10 @@ class UnknownError extends ProtocolError {
235
203
  return http_status_codes_1.StatusCodes.INTERNAL_SERVER_ERROR;
236
204
  }
237
205
  static error() {
238
- return W3C_UNKNOWN_ERROR;
206
+ return 'unknown error';
239
207
  }
240
- constructor(errorOrMessage) {
241
- const origMessage = lodash_1.default.isString((errorOrMessage || {}).message)
242
- ? errorOrMessage.message
243
- : errorOrMessage;
244
- const message = 'An unknown server-side error occurred while processing the command.' +
245
- (origMessage ? ` Original error: ${origMessage}` : '');
246
- super(message, UnknownError.code(), UnknownError.w3cStatus(), UnknownError.error());
208
+ constructor(message = '', cause) {
209
+ super(message || 'An unknown server-side error occurred while processing the command.', UnknownError.code(), UnknownError.w3cStatus(), UnknownError.error(), cause);
247
210
  }
248
211
  }
249
212
  exports.UnknownError = UnknownError;
@@ -257,12 +220,9 @@ class UnknownMethodError extends ProtocolError {
257
220
  static error() {
258
221
  return 'unknown method';
259
222
  }
260
- /**
261
- * @param {string} [message] error message
262
- */
263
- constructor(message) {
223
+ constructor(message = '', cause) {
264
224
  super(message ||
265
- 'The requested command matched a known URL but did not match an method for that URL', UnknownMethodError.code(), UnknownMethodError.w3cStatus(), UnknownMethodError.error());
225
+ 'The requested command matched a known URL but did not match an method for that URL', UnknownMethodError.code(), UnknownMethodError.w3cStatus(), UnknownMethodError.error(), cause);
266
226
  }
267
227
  }
268
228
  exports.UnknownMethodError = UnknownMethodError;
@@ -276,11 +236,8 @@ class UnsupportedOperationError extends ProtocolError {
276
236
  static error() {
277
237
  return 'unsupported operation';
278
238
  }
279
- /**
280
- * @param {string} [message] error message
281
- */
282
- constructor(message) {
283
- super(message || 'A server-side error occurred. Command cannot be supported.', UnsupportedOperationError.code(), UnsupportedOperationError.w3cStatus(), UnsupportedOperationError.error());
239
+ constructor(message = '', cause) {
240
+ super(message || 'A server-side error occurred. Command cannot be supported.', UnsupportedOperationError.code(), UnsupportedOperationError.w3cStatus(), UnsupportedOperationError.error(), cause);
284
241
  }
285
242
  }
286
243
  exports.UnsupportedOperationError = UnsupportedOperationError;
@@ -294,11 +251,8 @@ class ElementIsNotSelectableError extends ProtocolError {
294
251
  static w3cStatus() {
295
252
  return http_status_codes_1.StatusCodes.BAD_REQUEST;
296
253
  }
297
- /**
298
- * @param {string} [message] error message
299
- */
300
- constructor(message) {
301
- super(message || 'An attempt was made to select an element that cannot be selected.', ElementIsNotSelectableError.code(), ElementIsNotSelectableError.w3cStatus(), ElementIsNotSelectableError.error());
254
+ constructor(message = '', cause) {
255
+ super(message || 'An attempt was made to select an element that cannot be selected.', ElementIsNotSelectableError.code(), ElementIsNotSelectableError.w3cStatus(), ElementIsNotSelectableError.error(), cause);
302
256
  }
303
257
  }
304
258
  exports.ElementIsNotSelectableError = ElementIsNotSelectableError;
@@ -312,13 +266,10 @@ class ElementClickInterceptedError extends ProtocolError {
312
266
  static w3cStatus() {
313
267
  return http_status_codes_1.StatusCodes.BAD_REQUEST;
314
268
  }
315
- /**
316
- * @param {string} [message] error message
317
- */
318
- constructor(message) {
269
+ constructor(message = '', cause) {
319
270
  super(message ||
320
271
  'The Element Click command could not be completed because the element receiving ' +
321
- 'the events is obscuring the element that was requested clicked', ElementClickInterceptedError.code(), ElementClickInterceptedError.w3cStatus(), ElementClickInterceptedError.error());
272
+ 'the events is obscuring the element that was requested clicked', ElementClickInterceptedError.code(), ElementClickInterceptedError.w3cStatus(), ElementClickInterceptedError.error(), cause);
322
273
  }
323
274
  }
324
275
  exports.ElementClickInterceptedError = ElementClickInterceptedError;
@@ -332,12 +283,9 @@ class ElementNotInteractableError extends ProtocolError {
332
283
  static w3cStatus() {
333
284
  return http_status_codes_1.StatusCodes.BAD_REQUEST;
334
285
  }
335
- /**
336
- * @param {string} [message] error message
337
- */
338
- constructor(message) {
286
+ constructor(message = '', cause) {
339
287
  super(message ||
340
- 'A command could not be completed because the element is not pointer- or keyboard interactable', ElementNotInteractableError.code(), ElementNotInteractableError.w3cStatus(), ElementNotInteractableError.error());
288
+ 'A command could not be completed because the element is not pointer- or keyboard interactable', ElementNotInteractableError.code(), ElementNotInteractableError.w3cStatus(), ElementNotInteractableError.error(), cause);
341
289
  }
342
290
  }
343
291
  exports.ElementNotInteractableError = ElementNotInteractableError;
@@ -345,12 +293,12 @@ class InsecureCertificateError extends ProtocolError {
345
293
  static error() {
346
294
  return 'insecure certificate';
347
295
  }
348
- /**
349
- * @param {string} [message] error message
350
- */
351
- constructor(message) {
296
+ static w3cStatus() {
297
+ return http_status_codes_1.StatusCodes.BAD_REQUEST;
298
+ }
299
+ constructor(message = '', cause) {
352
300
  super(message ||
353
- 'Navigation caused the user agent to hit a certificate warning, which is usually the result of an expired or invalid TLS certificate', ElementIsNotSelectableError.code(), null, InsecureCertificateError.error());
301
+ 'Navigation caused the user agent to hit a certificate warning, which is usually the result of an expired or invalid TLS certificate', UnknownError.code(), InsecureCertificateError.w3cStatus(), InsecureCertificateError.error(), cause);
354
302
  }
355
303
  }
356
304
  exports.InsecureCertificateError = InsecureCertificateError;
@@ -364,11 +312,8 @@ class JavaScriptError extends ProtocolError {
364
312
  static error() {
365
313
  return 'javascript error';
366
314
  }
367
- /**
368
- * @param {string} [message] error message
369
- */
370
- constructor(message) {
371
- super(message || 'An error occurred while executing user supplied JavaScript.', JavaScriptError.code(), JavaScriptError.w3cStatus(), JavaScriptError.error());
315
+ constructor(message = '', cause) {
316
+ super(message || 'An error occurred while executing user supplied JavaScript.', JavaScriptError.code(), JavaScriptError.w3cStatus(), JavaScriptError.error(), cause);
372
317
  }
373
318
  }
374
319
  exports.JavaScriptError = JavaScriptError;
@@ -382,11 +327,8 @@ class XPathLookupError extends ProtocolError {
382
327
  static error() {
383
328
  return 'invalid selector';
384
329
  }
385
- /**
386
- * @param {string} [message] error message
387
- */
388
- constructor(message) {
389
- super(message || 'An error occurred while searching for an element by XPath.', XPathLookupError.code(), XPathLookupError.w3cStatus(), XPathLookupError.error());
330
+ constructor(message = '', cause) {
331
+ super(message || 'An error occurred while searching for an element by XPath.', XPathLookupError.code(), XPathLookupError.w3cStatus(), XPathLookupError.error(), cause);
390
332
  }
391
333
  }
392
334
  exports.XPathLookupError = XPathLookupError;
@@ -400,11 +342,8 @@ class TimeoutError extends ProtocolError {
400
342
  static error() {
401
343
  return 'timeout';
402
344
  }
403
- /**
404
- * @param {string} [message] error message
405
- */
406
- constructor(message) {
407
- super(message || 'An operation did not complete before its timeout expired.', TimeoutError.code(), TimeoutError.w3cStatus(), TimeoutError.error());
345
+ constructor(message = '', cause) {
346
+ super(message || 'An operation did not complete before its timeout expired.', TimeoutError.code(), TimeoutError.w3cStatus(), TimeoutError.error(), cause);
408
347
  }
409
348
  }
410
349
  exports.TimeoutError = TimeoutError;
@@ -418,13 +357,10 @@ class NoSuchWindowError extends ProtocolError {
418
357
  static w3cStatus() {
419
358
  return http_status_codes_1.StatusCodes.NOT_FOUND;
420
359
  }
421
- /**
422
- * @param {string} [message] error message
423
- */
424
- constructor(message) {
360
+ constructor(message = '', cause) {
425
361
  super(message ||
426
362
  'A request to switch to a different window could not be satisfied ' +
427
- 'because the window could not be found.', NoSuchWindowError.code(), NoSuchWindowError.w3cStatus(), NoSuchWindowError.error());
363
+ 'because the window could not be found.', NoSuchWindowError.code(), NoSuchWindowError.w3cStatus(), NoSuchWindowError.error(), cause);
428
364
  }
429
365
  }
430
366
  exports.NoSuchWindowError = NoSuchWindowError;
@@ -438,11 +374,8 @@ class InvalidArgumentError extends ProtocolError {
438
374
  static w3cStatus() {
439
375
  return http_status_codes_1.StatusCodes.BAD_REQUEST;
440
376
  }
441
- /**
442
- * @param {string} [err] error message
443
- */
444
- constructor(err) {
445
- super(err || 'The arguments passed to the command are either invalid or malformed', InvalidArgumentError.code(), InvalidArgumentError.w3cStatus(), InvalidArgumentError.error());
377
+ constructor(message = '', cause) {
378
+ super(message || 'The arguments passed to the command are either invalid or malformed', InvalidArgumentError.code(), InvalidArgumentError.w3cStatus(), InvalidArgumentError.error(), cause);
446
379
  }
447
380
  }
448
381
  exports.InvalidArgumentError = InvalidArgumentError;
@@ -456,13 +389,10 @@ class InvalidCookieDomainError extends ProtocolError {
456
389
  static w3cStatus() {
457
390
  return http_status_codes_1.StatusCodes.BAD_REQUEST;
458
391
  }
459
- /**
460
- * @param {string} [err] error message
461
- */
462
- constructor(err) {
463
- super(err ||
392
+ constructor(message = '', cause) {
393
+ super(message ||
464
394
  'An illegal attempt was made to set a cookie under a different ' +
465
- 'domain than the current page.', InvalidCookieDomainError.code(), InvalidCookieDomainError.w3cStatus(), InvalidCookieDomainError.error());
395
+ 'domain than the current page.', InvalidCookieDomainError.code(), InvalidCookieDomainError.w3cStatus(), InvalidCookieDomainError.error(), cause);
466
396
  }
467
397
  }
468
398
  exports.InvalidCookieDomainError = InvalidCookieDomainError;
@@ -476,12 +406,9 @@ class NoSuchCookieError extends ProtocolError {
476
406
  static error() {
477
407
  return 'no such cookie';
478
408
  }
479
- /**
480
- * @param {string} [err] error message
481
- */
482
- constructor(err) {
483
- super(err ||
484
- 'No cookie matching the given path name was found amongst the associated cookies of the current browsing context’s active document', NoSuchCookieError.code(), NoSuchCookieError.w3cStatus(), NoSuchCookieError.error());
409
+ constructor(message = '', cause) {
410
+ super(message ||
411
+ 'No cookie matching the given path name was found amongst the associated cookies of the current browsing context’s active document', NoSuchCookieError.code(), NoSuchCookieError.w3cStatus(), NoSuchCookieError.error(), cause);
485
412
  }
486
413
  }
487
414
  exports.NoSuchCookieError = NoSuchCookieError;
@@ -495,11 +422,8 @@ class UnableToSetCookieError extends ProtocolError {
495
422
  static error() {
496
423
  return 'unable to set cookie';
497
424
  }
498
- /**
499
- * @param {string} [err] error message
500
- */
501
- constructor(err) {
502
- super(err || "A request to set a cookie's value could not be satisfied.", UnableToSetCookieError.code(), UnableToSetCookieError.w3cStatus(), UnableToSetCookieError.error());
425
+ constructor(message = '', cause) {
426
+ super(message || "A request to set a cookie's value could not be satisfied.", UnableToSetCookieError.code(), UnableToSetCookieError.w3cStatus(), UnableToSetCookieError.error(), cause);
503
427
  }
504
428
  }
505
429
  exports.UnableToSetCookieError = UnableToSetCookieError;
@@ -513,11 +437,8 @@ class UnexpectedAlertOpenError extends ProtocolError {
513
437
  static error() {
514
438
  return 'unexpected alert open';
515
439
  }
516
- /**
517
- * @param {string} [message] error message
518
- */
519
- constructor(message) {
520
- super(message || 'A modal dialog was open, blocking this operation', UnexpectedAlertOpenError.code(), UnexpectedAlertOpenError.w3cStatus(), UnexpectedAlertOpenError.error());
440
+ constructor(message = '', cause) {
441
+ super(message || 'A modal dialog was open, blocking this operation', UnexpectedAlertOpenError.code(), UnexpectedAlertOpenError.w3cStatus(), UnexpectedAlertOpenError.error(), cause);
521
442
  }
522
443
  }
523
444
  exports.UnexpectedAlertOpenError = UnexpectedAlertOpenError;
@@ -531,12 +452,8 @@ class NoAlertOpenError extends ProtocolError {
531
452
  static error() {
532
453
  return 'no such alert';
533
454
  }
534
- /**
535
- *
536
- * @param {string} [message]
537
- */
538
- constructor(message) {
539
- super(message || 'An attempt was made to operate on a modal dialog when one ' + 'was not open.', NoAlertOpenError.code(), NoAlertOpenError.w3cStatus(), NoAlertOpenError.error());
455
+ constructor(message = '', cause) {
456
+ super(message || 'An attempt was made to operate on a modal dialog when one was not open.', NoAlertOpenError.code(), NoAlertOpenError.w3cStatus(), NoAlertOpenError.error(), cause);
540
457
  }
541
458
  }
542
459
  exports.NoAlertOpenError = NoAlertOpenError;
@@ -553,11 +470,8 @@ class ScriptTimeoutError extends ProtocolError {
553
470
  static error() {
554
471
  return 'script timeout';
555
472
  }
556
- /**
557
- * @param {string} [err] error message
558
- */
559
- constructor(err) {
560
- super(err || 'A script did not complete before its timeout expired.', ScriptTimeoutError.code(), ScriptTimeoutError.w3cStatus(), ScriptTimeoutError.error());
473
+ constructor(message = '', cause) {
474
+ super(message || 'A script did not complete before its timeout expired.', ScriptTimeoutError.code(), ScriptTimeoutError.w3cStatus(), ScriptTimeoutError.error(), cause);
561
475
  }
562
476
  }
563
477
  exports.ScriptTimeoutError = ScriptTimeoutError;
@@ -571,11 +485,8 @@ class InvalidElementCoordinatesError extends ProtocolError {
571
485
  static error() {
572
486
  return 'invalid coordinates';
573
487
  }
574
- /**
575
- * @param {string} [err] error message
576
- */
577
- constructor(err) {
578
- super(err || 'The coordinates provided to an interactions operation are invalid.', InvalidElementCoordinatesError.code(), InvalidElementCoordinatesError.w3cStatus(), InvalidElementCoordinatesError.error());
488
+ constructor(message = '', cause) {
489
+ super(message || 'The coordinates provided to an interactions operation are invalid.', InvalidElementCoordinatesError.code(), InvalidElementCoordinatesError.w3cStatus(), InvalidElementCoordinatesError.error(), cause);
579
490
  }
580
491
  }
581
492
  exports.InvalidElementCoordinatesError = InvalidElementCoordinatesError;
@@ -592,11 +503,8 @@ class IMENotAvailableError extends ProtocolError {
592
503
  static error() {
593
504
  return 'unsupported operation';
594
505
  }
595
- /**
596
- * @param {string} [message] error message
597
- */
598
- constructor(message) {
599
- super(message || 'IME was not available.', IMENotAvailableError.code(), IMENotAvailableError.w3cStatus(), IMENotAvailableError.error());
506
+ constructor(message = '', cause) {
507
+ super(message || 'IME was not available.', IMENotAvailableError.code(), IMENotAvailableError.w3cStatus(), IMENotAvailableError.error(), cause);
600
508
  }
601
509
  }
602
510
  exports.IMENotAvailableError = IMENotAvailableError;
@@ -610,11 +518,8 @@ class IMEEngineActivationFailedError extends ProtocolError {
610
518
  static error() {
611
519
  return 'unsupported operation';
612
520
  }
613
- /**
614
- * @param {string} [err] error message
615
- */
616
- constructor(err) {
617
- super(err || 'An IME engine could not be started.', IMEEngineActivationFailedError.code(), IMEEngineActivationFailedError.w3cStatus(), IMEEngineActivationFailedError.error());
521
+ constructor(message = '', cause) {
522
+ super(message || 'An IME engine could not be started.', IMEEngineActivationFailedError.code(), IMEEngineActivationFailedError.w3cStatus(), IMEEngineActivationFailedError.error(), cause);
618
523
  }
619
524
  }
620
525
  exports.IMEEngineActivationFailedError = IMEEngineActivationFailedError;
@@ -628,11 +533,8 @@ class InvalidSelectorError extends ProtocolError {
628
533
  static error() {
629
534
  return 'invalid selector';
630
535
  }
631
- /**
632
- * @param {string} [err] error message
633
- */
634
- constructor(err) {
635
- super(err || 'Argument was an invalid selector (e.g. XPath/CSS).', InvalidSelectorError.code(), InvalidSelectorError.w3cStatus(), InvalidSelectorError.error());
536
+ constructor(message = '', cause) {
537
+ super(message || 'Argument was an invalid selector (e.g. XPath/CSS).', InvalidSelectorError.code(), InvalidSelectorError.w3cStatus(), InvalidSelectorError.error(), cause);
636
538
  }
637
539
  }
638
540
  exports.InvalidSelectorError = InvalidSelectorError;
@@ -646,12 +548,8 @@ class SessionNotCreatedError extends ProtocolError {
646
548
  static error() {
647
549
  return 'session not created';
648
550
  }
649
- constructor(details) {
650
- let message = 'A new session could not be created.';
651
- if (details) {
652
- message += ` Details: ${details}`;
653
- }
654
- super(message, SessionNotCreatedError.code(), SessionNotCreatedError.w3cStatus(), SessionNotCreatedError.error());
551
+ constructor(message = '', cause) {
552
+ super(`A new session could not be created.${message ? (' Details: ' + message) : ''}`, SessionNotCreatedError.code(), SessionNotCreatedError.w3cStatus(), SessionNotCreatedError.error(), cause);
655
553
  }
656
554
  }
657
555
  exports.SessionNotCreatedError = SessionNotCreatedError;
@@ -665,11 +563,8 @@ class MoveTargetOutOfBoundsError extends ProtocolError {
665
563
  static error() {
666
564
  return 'move target out of bounds';
667
565
  }
668
- /**
669
- * @param {string} [err] error message
670
- */
671
- constructor(err) {
672
- super(err || 'Target provided for a move action is out of bounds.', MoveTargetOutOfBoundsError.code(), MoveTargetOutOfBoundsError.w3cStatus(), MoveTargetOutOfBoundsError.error());
566
+ constructor(message = '', cause) {
567
+ super(message || 'Target provided for a move action is out of bounds.', MoveTargetOutOfBoundsError.code(), MoveTargetOutOfBoundsError.w3cStatus(), MoveTargetOutOfBoundsError.error(), cause);
673
568
  }
674
569
  }
675
570
  exports.MoveTargetOutOfBoundsError = MoveTargetOutOfBoundsError;
@@ -677,12 +572,8 @@ class NoSuchContextError extends ProtocolError {
677
572
  static code() {
678
573
  return 35;
679
574
  }
680
- /**
681
- *
682
- * @param {string} [message]
683
- */
684
- constructor(message) {
685
- super(message || 'No such context found.', NoSuchContextError.code());
575
+ constructor(message = '', cause) {
576
+ super(message || 'No such context found.', NoSuchContextError.code(), UnknownError.w3cStatus(), UnknownError.error(), cause);
686
577
  }
687
578
  }
688
579
  exports.NoSuchContextError = NoSuchContextError;
@@ -690,31 +581,21 @@ class InvalidContextError extends ProtocolError {
690
581
  static code() {
691
582
  return 36;
692
583
  }
693
- /**
694
- *
695
- * @param {string} [message]
696
- */
697
- constructor(message) {
698
- super(message || 'That command could not be executed in the current context.', InvalidContextError.code());
584
+ constructor(message = '', cause) {
585
+ super(message || 'That command could not be executed in the current context.', InvalidContextError.code(), UnknownError.w3cStatus(), UnknownError.error(), cause);
699
586
  }
700
587
  }
701
588
  exports.InvalidContextError = InvalidContextError;
702
- // These are aliases for UnknownMethodError
589
+ // Aliases to UnknownMethodError
703
590
  class NotYetImplementedError extends UnknownMethodError {
704
- /**
705
- * @param {string} [err] error message
706
- */
707
- constructor(err) {
708
- super(err || 'Method has not yet been implemented');
591
+ constructor(message = '', cause) {
592
+ super(message || 'Method has not yet been implemented', cause);
709
593
  }
710
594
  }
711
595
  exports.NotYetImplementedError = NotYetImplementedError;
712
596
  class NotImplementedError extends UnknownMethodError {
713
- /**
714
- * @param {string} [err] error message
715
- */
716
- constructor(err) {
717
- super(err || 'Method is not implemented');
597
+ constructor(message = '', cause) {
598
+ super(message || 'Method is not implemented', cause);
718
599
  }
719
600
  }
720
601
  exports.NotImplementedError = NotImplementedError;
@@ -728,45 +609,43 @@ class UnableToCaptureScreen extends ProtocolError {
728
609
  static error() {
729
610
  return 'unable to capture screen';
730
611
  }
731
- /**
732
- * @param {string} [err] error message
733
- */
734
- constructor(err) {
735
- super(err || 'A screen capture was made impossible', UnableToCaptureScreen.code(), UnableToCaptureScreen.w3cStatus(), UnableToCaptureScreen.error());
612
+ constructor(message = '', cause) {
613
+ super(message || 'A screen capture was made impossible', UnableToCaptureScreen.code(), UnableToCaptureScreen.w3cStatus(), UnableToCaptureScreen.error(), cause);
736
614
  }
737
615
  }
738
616
  exports.UnableToCaptureScreen = UnableToCaptureScreen;
739
- function generateBadParametersMessage(requiredParams, actualParams) {
740
- const toArray = (/** @type {any} */ x) => (lodash_1.default.isArray(x) ? x : []);
741
- const requiredParamNames = toArray(requiredParams?.required);
742
- const actualParamNames = toArray(actualParams);
617
+ function generateBadParametersMessage(paramRequirements, paramNames) {
618
+ const toArray = function (x) {
619
+ if (lodash_1.default.isUndefined(x)) {
620
+ return [];
621
+ }
622
+ if (lodash_1.default.isArray(x)) {
623
+ return x;
624
+ }
625
+ return [x];
626
+ };
627
+ const requiredParamNames = toArray(paramRequirements.required);
628
+ const actualParamNames = toArray(paramNames);
743
629
  const missingRequiredParamNames = lodash_1.default.difference(requiredParamNames, actualParamNames);
744
- /** @type {string[]} */
745
630
  const resultLines = [];
746
631
  resultLines.push(lodash_1.default.isEmpty(missingRequiredParamNames)
747
632
  ? // This should not happen
748
633
  'Some of the provided parameters are not known'
749
- : `The following required parameter${missingRequiredParamNames.length === 1 ? ' is ' : 's are '}` + `missing: ${JSON.stringify(missingRequiredParamNames)}`);
634
+ : `The following required parameter${missingRequiredParamNames.length === 1 ? ' is' : 's are'} missing: ${JSON.stringify(missingRequiredParamNames)}`);
750
635
  if (!lodash_1.default.isEmpty(requiredParamNames)) {
751
636
  resultLines.push(`Known required parameters are: ${JSON.stringify(requiredParamNames)}`);
752
637
  }
753
- const optionalParamNames = lodash_1.default.difference(toArray(requiredParams?.optional), ['sessionId', 'id']);
638
+ const optionalParamNames = lodash_1.default.difference(toArray(paramRequirements.optional), ['sessionId', 'id']);
754
639
  if (!lodash_1.default.isEmpty(optionalParamNames)) {
755
640
  resultLines.push(`Known optional parameters are: ${JSON.stringify(optionalParamNames)}`);
756
641
  }
757
- resultLines.push(`You have provided${lodash_1.default.isEmpty(actualParamNames) ? ' none' : ': ' + JSON.stringify(actualParams)}`);
642
+ resultLines.push(`You have provided${lodash_1.default.isEmpty(actualParamNames) ? ' none' : ': ' + JSON.stringify(paramNames)}`);
758
643
  return resultLines.join('\n');
759
644
  }
760
645
  // Equivalent to W3C InvalidArgumentError
761
- class BadParametersError extends BaseError {
762
- static error() {
763
- return 'invalid argument';
764
- }
765
- constructor(requiredParams, actualParams, errMessage) {
766
- super(errMessage
767
- ? `Parameters were incorrect. You sent ${JSON.stringify(actualParams)}, ${errMessage}`
768
- : generateBadParametersMessage(requiredParams, actualParams));
769
- this.w3cStatus = http_status_codes_1.StatusCodes.BAD_REQUEST;
646
+ class BadParametersError extends InvalidArgumentError {
647
+ constructor(paramReqs, paramNames) {
648
+ super(generateBadParametersMessage(paramReqs, paramNames));
770
649
  }
771
650
  }
772
651
  exports.BadParametersError = BadParametersError;
@@ -777,49 +656,50 @@ exports.BadParametersError = BadParametersError;
777
656
  * for proxy failure to generate the client response.
778
657
  */
779
658
  class ProxyRequestError extends BaseError {
780
- constructor(err, responseError, httpStatus) {
781
- let responseErrorObj = support_1.util.safeJsonParse(responseError);
782
- if (!lodash_1.default.isPlainObject(responseErrorObj)) {
783
- responseErrorObj = {};
784
- }
785
- let origMessage = lodash_1.default.isString(responseError) ? responseError : '';
786
- if (!lodash_1.default.isEmpty(responseErrorObj)) {
787
- if (lodash_1.default.isString(responseErrorObj.value)) {
788
- origMessage = responseErrorObj.value;
789
- }
790
- else if (lodash_1.default.isPlainObject(responseErrorObj.value) &&
791
- lodash_1.default.isString(responseErrorObj.value.message)) {
792
- origMessage = responseErrorObj.value.message;
793
- }
794
- }
795
- super(lodash_1.default.isEmpty(err) ? `Proxy request unsuccessful. ${origMessage}` : err);
796
- this.w3cStatus = http_status_codes_1.StatusCodes.BAD_REQUEST;
659
+ constructor(message, httpResponseData, httpStatus, cause) {
660
+ const [responseErrorObj, originalMessage] = ProxyRequestError._parseHttpResponse(httpResponseData);
661
+ super(lodash_1.default.isEmpty(message)
662
+ ? `Proxy request unsuccessful.${originalMessage ? (' ' + originalMessage) : ''}`
663
+ : message, cause);
797
664
  // If the response error is an object and value is an object, it's a W3C error (for JSONWP value is a string)
798
665
  if (lodash_1.default.isPlainObject(responseErrorObj.value) && lodash_1.default.has(responseErrorObj.value, 'error')) {
799
- this.w3c = responseErrorObj.value;
800
- this.w3cStatus = httpStatus || http_status_codes_1.StatusCodes.BAD_REQUEST;
666
+ this._w3cError = responseErrorObj.value;
667
+ this._w3cErrorStatus = httpStatus;
801
668
  }
802
- else {
803
- this.jsonwp = responseErrorObj;
669
+ else if (lodash_1.default.has(responseErrorObj, 'status')) {
670
+ this._jwpError = responseErrorObj;
804
671
  }
805
672
  }
806
673
  getActualError() {
807
- // If it's MJSONWP error, returns actual error cause for request failure based on `jsonwp.status`
808
- if (support_1.util.hasValue(this.jsonwp?.status) && support_1.util.hasValue(this.jsonwp?.value)) {
809
- return errorFromMJSONWPStatusCode(this.jsonwp.status, this.jsonwp.value);
674
+ if (support_1.util.hasValue(this._jwpError?.status) && support_1.util.hasValue(this._jwpError?.value)) {
675
+ // If it's MJSONWP error, returns actual error cause for request failure based on `jsonwp.status`
676
+ return errorFromMJSONWPStatusCode(this._jwpError.status, this._jwpError.value);
677
+ }
678
+ if (support_1.util.hasValue(this._w3cError) && lodash_1.default.isNumber(this._w3cErrorStatus) && this._w3cErrorStatus >= 300) {
679
+ return errorFromW3CJsonCode(this._w3cError.error, this._w3cError.message || this.message, this._w3cError.stacktrace || this.stack);
680
+ }
681
+ return new UnknownError(this.message, this.cause);
682
+ }
683
+ static _parseHttpResponse(data) {
684
+ let responseErrorObj = support_1.util.safeJsonParse(data);
685
+ if (!lodash_1.default.isPlainObject(responseErrorObj)) {
686
+ responseErrorObj = {};
687
+ }
688
+ let errorMessage = lodash_1.default.isString(data) ? data : '';
689
+ if (lodash_1.default.isString(responseErrorObj.value)) {
690
+ errorMessage = responseErrorObj.value;
810
691
  }
811
- else if (support_1.util.hasValue(this.w3c) && lodash_1.default.isNumber(this.w3cStatus) && this.w3cStatus >= 300) {
812
- return errorFromW3CJsonCode(this.w3c.error, this.w3c.message || this.message, this.w3c.stacktrace);
692
+ else if (lodash_1.default.isString(responseErrorObj.value?.message)) {
693
+ errorMessage = responseErrorObj.value.message;
813
694
  }
814
- return new UnknownError(this.message);
695
+ return [responseErrorObj, errorMessage];
815
696
  }
816
697
  }
817
698
  exports.ProxyRequestError = ProxyRequestError;
818
699
  // map of error class name to error class
819
- const errors = {
700
+ exports.errors = {
820
701
  NotYetImplementedError,
821
702
  NotImplementedError,
822
- BadParametersError,
823
703
  InvalidArgumentError,
824
704
  NoSuchDriverError,
825
705
  NoSuchElementError,
@@ -858,178 +738,78 @@ const errors = {
858
738
  UnsupportedOperationError,
859
739
  ProxyRequestError,
860
740
  };
861
- exports.errors = errors;
862
- // map of error code to error class
863
- const jsonwpErrorCodeMap = {};
864
- for (let ErrorClass of lodash_1.default.values(errors)) {
741
+ const jsonwpErrorCodeMap = lodash_1.default.values(exports.errors)
742
+ .reduce((acc, ErrorClass) => {
865
743
  if ('code' in ErrorClass) {
866
- jsonwpErrorCodeMap[ErrorClass.code()] = ErrorClass;
744
+ acc[ErrorClass.code()] = ErrorClass;
867
745
  }
868
- }
869
- const w3cErrorCodeMap = {};
870
- for (let ErrorClass of lodash_1.default.values(errors)) {
746
+ return acc;
747
+ }, {});
748
+ const w3cErrorCodeMap = lodash_1.default.values(exports.errors)
749
+ .reduce((acc, ErrorClass) => {
871
750
  if ('error' in ErrorClass) {
872
- w3cErrorCodeMap[ErrorClass.error()] = ErrorClass;
751
+ acc[ErrorClass.error()] = ErrorClass;
873
752
  }
874
- }
875
- function isUnknownError(err) {
876
- return (!err.constructor.name ||
877
- !lodash_1.default.values(errors).find(function equalNames(error) {
878
- return error.name === err.constructor.name;
879
- }));
880
- }
753
+ return acc;
754
+ }, {});
881
755
  /**
882
756
  * Type guard to check if an Error is of a specific type
883
- * @template {Error} T
884
- * @param {any} err
885
- * @param {import('@appium/types').Class<T>} type
886
- * @returns {err is T}
887
757
  */
888
758
  function isErrorType(err, type) {
889
- // `name` property is the constructor name
890
- if (type.name === ProtocolError.name) {
891
- // `jsonwpCode` is `0` on success
892
- return !!err.jsonwpCode;
893
- }
894
- else if (type.name === ProxyRequestError.name) {
895
- // `status` is `0` on success
896
- if (err.jsonwp) {
897
- return !!err.jsonwp.status;
898
- }
899
- if (lodash_1.default.isPlainObject(err.w3c)) {
900
- return lodash_1.default.isNumber(err.w3cStatus) && err.w3cStatus >= 300;
901
- }
902
- return false;
903
- }
904
- return err.constructor.name === type.name;
759
+ return err.constructor?.name === type.name;
905
760
  }
906
761
  /**
907
762
  * Retrieve an error derived from MJSONWP status
908
- * @param {number} code JSONWP status code
909
- * @param {string|Object} value The error message, or an object with a `message` property
910
- * @return {ProtocolError} The error that is associated with provided JSONWP status code
763
+ * @param code JSONWP status code
764
+ * @param value The error message, or an object with a `message` property
765
+ * @return The error that is associated with provided JSONWP status code
911
766
  */
912
767
  function errorFromMJSONWPStatusCode(code, value = '') {
768
+ const ErrorClass = jsonwpErrorCodeMap[code] ?? UnknownError;
769
+ mjsonwpLog.debug(`Matched JSONWP error code ${code} to ${ErrorClass.name}`);
913
770
  // if `value` is an object, pull message from it, otherwise use the plain
914
771
  // value, or default to an empty string, if null
915
772
  const message = (value || {}).message || value || '';
916
- if (code !== UnknownError.code() && jsonwpErrorCodeMap[code]) {
917
- mjsonwpLog.debug(`Matched JSONWP error code ${code} to ${jsonwpErrorCodeMap[code].name}`);
918
- return new jsonwpErrorCodeMap[code](message);
919
- }
920
- mjsonwpLog.debug(`Matched JSONWP error code ${code} to UnknownError`);
921
- return new UnknownError(message);
773
+ return new ErrorClass(message);
922
774
  }
923
775
  /**
924
776
  * Retrieve an error derived from W3C JSON Code
925
- * @param {string} code W3C error string (see https://www.w3.org/TR/webdriver/#handling-errors `JSON Error Code` column)
926
- * @param {string} message the error message
927
- * @param {?string} stacktrace an optional error stacktrace
928
- * @return {ProtocolError} The error that is associated with the W3C error string
777
+ * @param signature W3C error string (see https://www.w3.org/TR/webdriver/#handling-errors `JSON Error Code` column)
778
+ * @param message the error message
779
+ * @param stacktrace an optional error stacktrace
780
+ * @return The error that is associated with the W3C error string
929
781
  */
930
- function errorFromW3CJsonCode(code, message, stacktrace = null) {
931
- if (code && w3cErrorCodeMap[code.toLowerCase()]) {
932
- w3cLog.debug(`Matched W3C error code '${code}' to ${w3cErrorCodeMap[code.toLowerCase()].name}`);
933
- const resultError = new w3cErrorCodeMap[code.toLowerCase()](message);
934
- resultError.stacktrace = stacktrace;
935
- return resultError;
936
- }
937
- w3cLog.debug(`Matched W3C error code '${code}' to UnknownError`);
938
- const resultError = new UnknownError(message);
782
+ function errorFromW3CJsonCode(signature, message, stacktrace) {
783
+ const ErrorClass = w3cErrorCodeMap[lodash_1.default.toLower(signature)] ?? UnknownError;
784
+ w3cLog.debug(`Matched W3C error code '${signature}' to ${ErrorClass.name}`);
785
+ const resultError = new ErrorClass(message);
939
786
  resultError.stacktrace = stacktrace;
940
787
  return resultError;
941
788
  }
942
- /**
943
- *
944
- * @param {any} err
945
- * @returns {err is ProtocolError}
946
- */
947
- function isProtocolError(err) {
948
- return 'w3cStatus' in err;
949
- }
950
789
  /**
951
790
  * Convert an Appium error to proper W3C HTTP response
952
- * @param {ProtocolError|MJSONWPError} err The error that needs to be translated
791
+ *
792
+ * @param err The error that needs to be translated
953
793
  */
954
794
  function getResponseForW3CError(err) {
955
- let httpStatus;
956
- // W3C defined error message (https://www.w3.org/TR/webdriver/#dfn-error-code)
957
- let w3cErrorString;
958
- if (!isProtocolError(err)) {
959
- err = support_1.util.hasValue(err.status)
960
- ? // If it's a JSONWP error, find corresponding error
961
- errorFromMJSONWPStatusCode(err.status, err.value)
962
- : new errors.UnknownError(err.message);
963
- }
964
- if (isErrorType(err, errors.BadParametersError)) {
965
- // respond with a 400 if we have bad parameters
966
- w3cLog.debug(`Bad parameters: ${err}`);
967
- w3cErrorString = BadParametersError.error();
968
- }
969
- else {
970
- // @ts-expect-error unclear what the problem is here
971
- w3cErrorString = err.error;
972
- }
973
- httpStatus = err.w3cStatus;
974
- if (!w3cErrorString) {
975
- w3cErrorString = UnknownError.error();
976
- }
977
- let httpResBody = {
978
- value: {
979
- error: w3cErrorString,
980
- message: err.message,
981
- stacktrace: err.stacktrace || err.stack,
982
- },
983
- };
984
- return [httpStatus, httpResBody];
985
- }
986
- /**
987
- * Convert an Appium error to a proper JSONWP response
988
- * @param {ProtocolError} err The error to be converted
989
- */
990
- function getResponseForJsonwpError(err) {
991
- if (isUnknownError(err)) {
992
- err = new errors.UnknownError(err);
993
- }
994
- // MJSONWP errors are usually 500 status code so set it to that by default
995
- let httpStatus = http_status_codes_1.StatusCodes.INTERNAL_SERVER_ERROR;
996
- /** @type {HttpResultBody} */
997
- let httpResBody = {
998
- status: err.jsonwpCode,
999
- value: {
1000
- message: err.message,
1001
- },
1002
- };
1003
- if (isErrorType(err, errors.BadParametersError)) {
1004
- // respond with a 400 if we have bad parameters
1005
- mjsonwpLog.debug(`Bad parameters: ${err}`);
1006
- httpStatus = http_status_codes_1.StatusCodes.BAD_REQUEST;
1007
- httpResBody = err.message;
1008
- }
1009
- else if (isErrorType(err, errors.NotYetImplementedError) ||
1010
- isErrorType(err, errors.NotImplementedError)) {
1011
- // respond with a 501 if the method is not implemented
1012
- httpStatus = http_status_codes_1.StatusCodes.NOT_IMPLEMENTED;
1013
- }
1014
- else if (isErrorType(err, errors.NoSuchDriverError)) {
1015
- // respond with a 404 if there is no driver for the session
1016
- httpStatus = http_status_codes_1.StatusCodes.NOT_FOUND;
1017
- }
1018
- return [httpStatus, httpResBody];
795
+ const protocolErrorToResponse = (e) => [
796
+ e.w3cStatus,
797
+ {
798
+ value: {
799
+ error: e.error,
800
+ message: e.message,
801
+ stacktrace: e.stacktrace || e.stack,
802
+ }
803
+ }
804
+ ];
805
+ // err is ProtocolError
806
+ if (['error', 'w3cStatus'].every((prop) => lodash_1.default.has(err, prop))) {
807
+ return protocolErrorToResponse(err);
808
+ }
809
+ // err is ProxyRequestError
810
+ if (lodash_1.default.has(err, 'getActualError') && lodash_1.default.isFunction(err.getActualError)) {
811
+ return protocolErrorToResponse(err.getActualError());
812
+ }
813
+ return protocolErrorToResponse(new UnknownError(err.message, err));
1019
814
  }
1020
- /**
1021
- * @typedef { string | {value: HttpResultBodyValue, status?: number } } HttpResultBody
1022
- */
1023
- /**
1024
- * @typedef HttpResultBodyValue
1025
- * @property {string} [message]
1026
- * @property {string|Error} [error]
1027
- * @property {string} [stacktrace]
1028
- */
1029
- /**
1030
- * @typedef MJSONWPError
1031
- * @property {number} status
1032
- * @property {string|object} value
1033
- * @property {string} message
1034
- */
1035
815
  //# sourceMappingURL=errors.js.map