mirror of
https://github.com/appium/appium.git
synced 2026-11-03 07:34:36 +08:00
Compare commits
71
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
74292e2292 | ||
|
|
8ccaf09877 | ||
|
|
d3d77a38df | ||
|
|
0149490522 | ||
|
|
16015de1b5 | ||
|
|
b7999aed03 | ||
|
|
1fa8c54765 | ||
|
|
8565209fda | ||
|
|
f8819836b5 | ||
|
|
ac912606e7 | ||
|
|
dcac55711c | ||
|
|
821ed01ae2 | ||
|
|
62fe09d563 | ||
|
|
8894b9adf7 | ||
|
|
44e423110a | ||
|
|
41a18f3b68 | ||
|
|
c2f3a618e4 | ||
|
|
5ce3b0c1aa | ||
|
|
177dff4f0e | ||
|
|
e7665d1cd9 | ||
|
|
34b636082f | ||
|
|
06607da92e | ||
|
|
9d6bbdb13e | ||
|
|
234ad59798 | ||
|
|
fe1b926886 | ||
|
|
5281f5a01a | ||
|
|
86f843b9e1 | ||
|
|
5226fa897b | ||
|
|
19928e9b90 | ||
|
|
e43c7a4dce | ||
|
|
82e40c1400 | ||
|
|
f3d959ef91 | ||
|
|
e8a838417a | ||
|
|
9773a23b26 | ||
|
|
cc10b65ee5 | ||
|
|
530045ec53 | ||
|
|
8e0fa2c1b3 | ||
|
|
d0d7548576 | ||
|
|
c7198b13e4 | ||
|
|
4279cc6cee | ||
|
|
a746eefbbb | ||
|
|
b6de85359d | ||
|
|
f2c8b69608 | ||
|
|
87fc50c2af | ||
|
|
f25079354b | ||
|
|
189bce88a0 | ||
|
|
15234bc055 | ||
|
|
073447ae4a | ||
|
|
dd070dc51d | ||
|
|
2882e71631 | ||
|
|
c106326169 | ||
|
|
5203480df6 | ||
|
|
52ae52a90a | ||
|
|
d5e5186cb7 | ||
|
|
541246184d | ||
|
|
faf9623a65 | ||
|
|
bc388db111 | ||
|
|
bdea13130c | ||
|
|
cc23c22b60 | ||
|
|
f675abc27b | ||
|
|
6fa0ed57ff | ||
|
|
57bbb7f46d | ||
|
|
d2b24daba0 | ||
|
|
14d27fe2a4 | ||
|
|
19845531f5 | ||
|
|
3cc878d835 | ||
|
|
4345a40a15 | ||
|
|
89e5f7e8db | ||
|
|
9469aaef0e | ||
|
|
2b12d5974a | ||
|
|
45cc948671 |
@@ -63,5 +63,6 @@ appium.zip
|
||||
**/build-fixtures/**
|
||||
*.tsbuildinfo
|
||||
packages/*/LICENSE
|
||||
\!packages/*/LICENSE
|
||||
local_appium_home
|
||||
*.tgz
|
||||
|
||||
+1
-1
@@ -3,7 +3,7 @@
|
||||
'use strict';
|
||||
|
||||
module.exports = {
|
||||
require: [require.resolve('./test/setup.js')],
|
||||
require: ['ts-node/register'],
|
||||
// forbids use of .only() in CI
|
||||
forbidOnly: Boolean(process.env.CI),
|
||||
color: true,
|
||||
|
||||
Generated
+2988
-6722
File diff suppressed because it is too large
Load Diff
+17
-20
@@ -65,7 +65,7 @@
|
||||
"sync-pkgs:license": "sync-monorepo-packages --force --no-package-json --packages=\"!packages/logger\" LICENSE",
|
||||
"test": "run-s test:quick",
|
||||
"test:ci": "run-s test:smoke test:unit test:types test:e2e",
|
||||
"test:e2e": "lerna run --concurrency=2 test:e2e",
|
||||
"test:e2e": "lerna run test:e2e",
|
||||
"test:quick": "run-s lint test:unit test:types",
|
||||
"test:slow": "run-s test:quick test:smoke test:e2e",
|
||||
"test:smoke": "smoker --all test:smoke",
|
||||
@@ -86,8 +86,8 @@
|
||||
"@types/chai": "4.3.16",
|
||||
"@types/chai-as-promised": "7.1.8",
|
||||
"@types/diff": "5.2.1",
|
||||
"@types/mocha": "10.0.6",
|
||||
"@types/node": "20.14.2",
|
||||
"@types/mocha": "10.0.7",
|
||||
"@types/node": "20.14.10",
|
||||
"@types/semver": "7.5.8",
|
||||
"@types/sinon": "17.0.3",
|
||||
"@types/sinon-chai": "3.2.12",
|
||||
@@ -95,12 +95,11 @@
|
||||
"@types/teen_process": "2.0.4",
|
||||
"@types/ws": "8.5.10",
|
||||
"@types/yargs": "17.0.32",
|
||||
"@typescript-eslint/eslint-plugin": "7.13.0",
|
||||
"@typescript-eslint/parser": "7.13.0",
|
||||
"@typescript-eslint/eslint-plugin": "7.16.0",
|
||||
"@typescript-eslint/parser": "7.16.0",
|
||||
"asyncbox": "3.0.0",
|
||||
"chai": "4.4.1",
|
||||
"chai-as-promised": "7.1.2",
|
||||
"chai-webdriverio-async": "3.0.0",
|
||||
"chai": "5.1.1",
|
||||
"chai-as-promised": "8.0.0",
|
||||
"conventional-changelog-conventionalcommits": "7.0.2",
|
||||
"cpy-cli": "5.0.0",
|
||||
"eslint": "8.57.0",
|
||||
@@ -109,33 +108,31 @@
|
||||
"eslint-import-resolver-typescript": "3.6.1",
|
||||
"eslint-plugin-import": "2.29.1",
|
||||
"eslint-plugin-mocha": "10.4.3",
|
||||
"eslint-plugin-promise": "6.2.0",
|
||||
"eslint-plugin-promise": "6.4.0",
|
||||
"fancy-log": "2.0.0",
|
||||
"finalhandler": "1.2.0",
|
||||
"get-port": "5.1.1",
|
||||
"json-schema-to-typescript": "14.0.5",
|
||||
"lerna": "8.1.3",
|
||||
"json-schema-to-typescript": "14.1.0",
|
||||
"lerna": "8.1.6",
|
||||
"log-symbols": "4.1.0",
|
||||
"midnight-smoker": "8.0.0",
|
||||
"mjpeg-consumer": "2.0.0",
|
||||
"mjpeg-server": "0.3.1",
|
||||
"mocha": "10.4.0",
|
||||
"mocha-chai-jest-snapshot": "1.1.4",
|
||||
"npm-run-all2": "6.2.0",
|
||||
"mocha": "10.6.0",
|
||||
"npm-run-all2": "6.2.2",
|
||||
"prettier": "3.3.2",
|
||||
"rewiremock": "3.14.5",
|
||||
"rimraf": "5.0.7",
|
||||
"rimraf": "5.0.9",
|
||||
"serve-static": "1.15.0",
|
||||
"sinon": "18.0.0",
|
||||
"sinon-chai": "3.7.0",
|
||||
"sync-monorepo-packages": "1.0.2",
|
||||
"through2": "4.0.2",
|
||||
"ts-node": "10.9.2",
|
||||
"tsd": "0.31.0",
|
||||
"typescript": "5.4.5",
|
||||
"tsd": "0.31.1",
|
||||
"typescript": "5.5.3",
|
||||
"validate.js": "0.13.1",
|
||||
"webdriverio": "8.38.2",
|
||||
"ws": "8.17.0",
|
||||
"webdriverio": "8.39.1",
|
||||
"ws": "8.18.0",
|
||||
"yaml-js": "0.3.1"
|
||||
},
|
||||
"engines": {
|
||||
|
||||
@@ -3,6 +3,65 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
## [2.11.2](https://github.com/appium/appium/compare/appium@2.11.1...appium@2.11.2) (2024-07-10)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **appium:** update dependency ws to v8.18.0 ([44e4231](https://github.com/appium/appium/commit/44e423110ad6c8bd7d846cc334fafe931fea43f9))
|
||||
* **execute-driver-plugin:** update dependency webdriverio to v8.39.1 ([c2f3a61](https://github.com/appium/appium/commit/c2f3a618e413c7f21057ba6d9002dc1fe4507e6f))
|
||||
* **support:** update dependency teen_process to v2.1.10 ([86f843b](https://github.com/appium/appium/commit/86f843b9e1fc56576d7a08bf95838a58971e98b3))
|
||||
* **support:** update dependency teen_process to v2.1.7 ([5226fa8](https://github.com/appium/appium/commit/5226fa897b90e9fec9be3e79a7d48fc7b4e0016d))
|
||||
* **support:** update dependency teen_process to v2.2.0 ([06607da](https://github.com/appium/appium/commit/06607da92e93d015747fd6d6d5bdabe1b3ac58d2))
|
||||
* **types:** update dependency type-fest to v4.21.0 ([#20335](https://github.com/appium/appium/issues/20335)) ([8894b9a](https://github.com/appium/appium/commit/8894b9adf709646108cc8d6426bbb690550609f2))
|
||||
|
||||
|
||||
|
||||
## [2.11.1](https://github.com/appium/appium/compare/appium@2.11.0...appium@2.11.1) (2024-06-28)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **images-plugin:** update dependency lru-cache to v10.3.0 ([#20306](https://github.com/appium/appium/issues/20306)) ([e43c7a4](https://github.com/appium/appium/commit/e43c7a4dce1f50fbd4d028cbeac5677422210b20))
|
||||
|
||||
|
||||
|
||||
## [2.11.0](https://github.com/appium/appium/compare/appium@2.10.3...appium@2.11.0) (2024-06-27)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* **appium:** Improve context logging ([#20250](https://github.com/appium/appium/issues/20250)) ([f675abc](https://github.com/appium/appium/commit/f675abc27b3e6beac2431cc71afb5fc2c2f70534))
|
||||
* **appium:** show extension update info message for newer major versions ([#20283](https://github.com/appium/appium/issues/20283)) ([f2c8b69](https://github.com/appium/appium/commit/f2c8b696085ba862553476f23509cac0674a447c))
|
||||
* **appium:** show spinner during extension uninstall ([#20282](https://github.com/appium/appium/issues/20282)) ([f250793](https://github.com/appium/appium/commit/f25079354bfd646810813ae47244a1e2e962dbfb))
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **appium:** update dependency ws to v8.17.1 ([d2b24da](https://github.com/appium/appium/commit/d2b24daba056373160d680ec5f017b28e9cbde1a))
|
||||
* **execute-driver-plugin:** update dependency webdriverio to v8.39.0 ([faf9623](https://github.com/appium/appium/commit/faf9623a65868a6330d062076074da7c1c3acb2a))
|
||||
* **support:** update dependency teen_process to v2.1.5 ([bc388db](https://github.com/appium/appium/commit/bc388db1116f411f4b241105f5feae30418c9a27))
|
||||
* **support:** update dependency teen_process to v2.1.6 ([5412461](https://github.com/appium/appium/commit/541246184dc7521c825ec1902775e681ea6f0db3))
|
||||
* **types:** update dependency type-fest to v4.20.1 ([#20255](https://github.com/appium/appium/issues/20255)) ([1984553](https://github.com/appium/appium/commit/19845531f558e2b16dfae807c768e1b9f2cab25d))
|
||||
|
||||
|
||||
|
||||
## [2.10.3](https://github.com/appium/appium/compare/appium@2.10.2...appium@2.10.3) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package appium
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [2.10.2](https://github.com/appium/appium/compare/appium@2.10.1...appium@2.10.2) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package appium
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [2.10.1](https://github.com/appium/appium/compare/appium@2.10.0...appium@2.10.1) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package appium
|
||||
|
||||
@@ -43,6 +43,7 @@ These drivers are not maintained by the Appium team and can be used to target ad
|
||||
|[Tizen](https://github.com/Samsung/appium-tizen-driver)|`--source=npm appium-tizen-driver`|Android|Native|Community / Samsung|
|
||||
|[TizenTV](https://github.com/headspinio/appium-tizen-tv-driver)|`--source=npm appium-tizen-tv-driver`|Samsung TV|Web|HeadSpin|
|
||||
|[Youi](https://github.com/YOU-i-Labs/appium-youiengine-driver)|`--source=npm appium-youiengine-driver`|iOS, Android, macOS, Linux, tvOS|Native|Community / You.i|
|
||||
|[Flutter Integration](https://github.com/AppiumTestDistribution/appium-flutter-integration-driver)|`--source=npm appium-flutter-integration-driver`|Android, iOS|Native|Community / AppiumTestDistribution|
|
||||
|
||||
!!! note
|
||||
|
||||
|
||||
@@ -47,7 +47,7 @@ another project called WebDriver) developed a relatively stable API for browser
|
||||
|
||||
Over the years, Selenium worked with various web browser vendors and the [W3C](https://w3c.org)
|
||||
standards group to turn its API into an official web browser standard, called the [WebDriver
|
||||
specification](https://w3c.github.io/webdriver/webdriver-spec.html). All the main browsers now
|
||||
specification](https://w3c.github.io/webdriver/). All the main browsers now
|
||||
implement automation capabilities inline with the WebDriver spec, without the Selenium team having
|
||||
to maintain any software that performs actual automation; standards for the win!
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@ title: Intro to Appium Clients
|
||||
---
|
||||
|
||||
For all the reasons discussed in the [main Overview](./appium.md), Appium is based on the [W3C
|
||||
WebDriver specification](https://w3c.github.io/webdriver/webdriver-spec.html). This means that
|
||||
WebDriver specification](https://w3c.github.io/webdriver/). This means that
|
||||
Appium implements a client-server architecture. The server (consisting of Appium itself along with
|
||||
any drivers or plugins you are using for automation) is connected to the devices under test, and
|
||||
is actually responsible for making automation happen on those devices. The client (driven by *you*,
|
||||
|
||||
@@ -37,7 +37,7 @@ their WebDriver protocol equivalents.
|
||||
|
||||
So let's say I wanted to do something with this empty driver; first I have to decide which
|
||||
WebDriver command I want to implement. For our example, let's take the [Navigate
|
||||
To](https://www.w3.org/TR/webdriver1/#navigate-to) WebDriver command. Leave aside for the moment
|
||||
To](https://w3c.github.io/webdriver/#navigate-to) WebDriver command. Leave aside for the moment
|
||||
what I want to have the driver *do* when this command is executed. To tell Appium the driver can
|
||||
handle the command, all we have to do is define a method like this in our driver class:[^1]
|
||||
|
||||
@@ -96,7 +96,7 @@ a driver becomes the task of mapping the WebDriver protocol to this underlying A
|
||||
a set of different underlying APIs--for example, the UiAutomator2 driver relies not only on the
|
||||
[UiAutomator2](https://developer.android.com/training/testing/other-components/ui-automator)
|
||||
technology from Google, but also functions only available through
|
||||
[ADB](https://developer.android.com/studio/command-line/adb), as well as functions only available
|
||||
[ADB](https://developer.android.com/tools/adb), as well as functions only available
|
||||
via the Android SDK inside a helper app). Tying it all together into a single, usable, WebDriver
|
||||
interface is the incredibly useful (but incredibly challenging) art of driver development!
|
||||
|
||||
|
||||
@@ -578,7 +578,9 @@ class ExtensionCliCommand {
|
||||
return this.config.installedExtensions;
|
||||
}
|
||||
const pkgName = extRecord.pkgName;
|
||||
await npm.uninstallPackage(this.config.appiumHome, pkgName);
|
||||
await spinWith(this.isJsonOutput, `Uninstalling ${this.type} '${installSpec}'`, async () => {
|
||||
await npm.uninstallPackage(this.config.appiumHome, pkgName);
|
||||
});
|
||||
await this.config.removeExtension(installSpec);
|
||||
this.log.ok(`Successfully uninstalled ${this.type} '${installSpec}'`.green);
|
||||
return this.config.installedExtensions;
|
||||
@@ -639,9 +641,16 @@ class ExtensionCliCommand {
|
||||
const updateVer = unsafe && update.unsafeUpdate ? update.unsafeUpdate : update.safeUpdate;
|
||||
await spinWith(
|
||||
this.isJsonOutput,
|
||||
`Updating driver '${e}' from ${update.current} to ${updateVer}`,
|
||||
`Updating ${this.type} '${e}' from ${update.current} to ${updateVer}`,
|
||||
async () => await this.updateExtension(e, updateVer)
|
||||
);
|
||||
// if we're doing a safe update, but an unsafe update is also available, let the user know
|
||||
if (!unsafe && update.unsafeUpdate) {
|
||||
const newMajorUpdateMsg = `A newer major version ${update.unsafeUpdate} ` +
|
||||
`is available for ${this.type} '${e}', which could include breaking changes. ` +
|
||||
`If you want to apply this update, re-run with --unsafe`;
|
||||
this.log.info(newMajorUpdateMsg.yellow);
|
||||
}
|
||||
updates[e] = {from: update.current, to: updateVer};
|
||||
} catch (err) {
|
||||
errors[e] = err;
|
||||
|
||||
@@ -142,7 +142,7 @@ function createConsoleTransport(args, logLvl) {
|
||||
format: format.combine(
|
||||
formatTimestamp(args),
|
||||
isLogColorEnabled(args) ? colorizeFormat : stripColorFormat,
|
||||
format.printf(formatLogLine(args, true))
|
||||
formatLog(args, true),
|
||||
),
|
||||
});
|
||||
}
|
||||
@@ -166,7 +166,7 @@ function createFileTransport(args, logLvl) {
|
||||
format: format.combine(
|
||||
stripColorFormat,
|
||||
formatTimestamp(args),
|
||||
format.printf(formatLogLine(args, false))
|
||||
formatLog(args, false),
|
||||
),
|
||||
});
|
||||
}
|
||||
@@ -199,7 +199,7 @@ function createHttpTransport(args, logLvl) {
|
||||
level: logLvl,
|
||||
format: format.combine(
|
||||
stripColorFormat,
|
||||
format.printf(formatLogLine(args, false))
|
||||
formatLog(args, false),
|
||||
),
|
||||
});
|
||||
}
|
||||
@@ -288,22 +288,35 @@ function colorizePrefix(text) {
|
||||
/**
|
||||
* @param {ParsedArgs} args
|
||||
* @param {boolean} targetConsole
|
||||
* @returns {(info: import('logform').TransformableInfo) => string}
|
||||
* @returns {import('logform').Format}
|
||||
*/
|
||||
function formatLogLine(args, targetConsole) {
|
||||
return (info) => {
|
||||
if (['json', 'pretty_json'].includes(args.logFormat)) {
|
||||
let infoCopy = {...info};
|
||||
if (targetConsole && !args.logTimestamp) {
|
||||
delete infoCopy.timestamp;
|
||||
}
|
||||
return JSON.stringify(infoCopy, null, args.logFormat === 'pretty_json' ? 2 : undefined);
|
||||
}
|
||||
function formatLog(args, targetConsole) {
|
||||
if (['json', 'pretty_json'].includes(args.logFormat)) {
|
||||
return format.combine(
|
||||
format((info) => {
|
||||
const infoCopy = {...info};
|
||||
const contextInfo = globalLog.asyncStorage.getStore() ?? {};
|
||||
|
||||
if (targetConsole && !args.logTimestamp) {
|
||||
delete infoCopy.timestamp;
|
||||
}
|
||||
|
||||
if (!_.isEmpty(contextInfo)) {
|
||||
infoCopy.context = {...contextInfo};
|
||||
}
|
||||
|
||||
return infoCopy;
|
||||
})(),
|
||||
format.json({space: args.logFormat === 'pretty_json' ? 2 : undefined}),
|
||||
);
|
||||
}
|
||||
|
||||
return format.printf((info) => {
|
||||
if (targetConsole) {
|
||||
return `${args.logTimestamp ? `${info.timestamp} - ` : ''}${info.message}`;
|
||||
}
|
||||
return `${info.timestamp} ${info.message}`;
|
||||
};
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -249,15 +249,19 @@ async function init(args) {
|
||||
const {issues, rules} = await logger.unwrap().loadSecureValuesPreprocessingRules(
|
||||
serverArgs.logFilters,
|
||||
);
|
||||
const argToLog = _.truncate(JSON.stringify(serverArgs.logFilters), {
|
||||
length: 150
|
||||
});
|
||||
if (!_.isEmpty(issues)) {
|
||||
throw new Error(
|
||||
`The log filtering rules config '${serverArgs.logFilters}' has issues: ` +
|
||||
`The log filtering rules config ${argToLog} has issues: ` +
|
||||
JSON.stringify(issues, null, 2),
|
||||
);
|
||||
}
|
||||
if (_.isEmpty(rules)) {
|
||||
logger.warn(
|
||||
`Found no log filtering rules in '${serverArgs.logFilters}'. Is that expected?`,
|
||||
`Found no log filtering rules in the ${argToLog} config. ` +
|
||||
`Is that expected?`,
|
||||
);
|
||||
} else {
|
||||
// Filtering aims to "hide" these values from the log,
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "appium",
|
||||
"version": "2.10.1",
|
||||
"version": "2.11.2",
|
||||
"description": "Automation for Apps.",
|
||||
"keywords": [
|
||||
"automation",
|
||||
@@ -54,18 +54,18 @@
|
||||
"postinstall": "node ./scripts/autoinstall-extensions.js",
|
||||
"publish:docs": "cross-env APPIUM_DOCS_PUBLISH=1 npm run build:docs",
|
||||
"test": "npm run test:unit",
|
||||
"test:e2e": "mocha -p --timeout 1m --slow 30s \"./test/e2e/**/*.spec.js\"",
|
||||
"test:e2e": "mocha --timeout 1m --slow 30s \"./test/e2e/**/*.spec.js\"",
|
||||
"test:smoke": "cross-env APPIUM_HOME=./local_appium_home node ./index.js driver install uiautomator2 && cross-env APPIUM_HOME=./local_appium_home node ./index.js driver list",
|
||||
"test:unit": "mocha \"./test/unit/**/*.spec.js\""
|
||||
},
|
||||
"dependencies": {
|
||||
"@appium/base-driver": "^9.10.1",
|
||||
"@appium/base-plugin": "^2.2.37",
|
||||
"@appium/docutils": "^1.0.13",
|
||||
"@appium/logger": "^1.4.1",
|
||||
"@appium/schema": "^0.6.0",
|
||||
"@appium/support": "^5.0.1",
|
||||
"@appium/types": "^0.20.1",
|
||||
"@appium/base-driver": "^9.11.2",
|
||||
"@appium/base-plugin": "^2.2.42",
|
||||
"@appium/docutils": "^1.0.18",
|
||||
"@appium/logger": "^1.6.0",
|
||||
"@appium/schema": "^0.6.1",
|
||||
"@appium/support": "^5.1.2",
|
||||
"@appium/types": "^0.21.1",
|
||||
"@sidvind/better-ajv-errors": "2.1.3",
|
||||
"@types/argparse": "2.0.16",
|
||||
"@types/bluebird": "3.5.42",
|
||||
@@ -83,17 +83,17 @@
|
||||
"cross-env": "7.0.3",
|
||||
"lilconfig": "3.1.2",
|
||||
"lodash": "4.17.21",
|
||||
"lru-cache": "10.2.2",
|
||||
"lru-cache": "10.3.0",
|
||||
"ora": "5.4.1",
|
||||
"package-changed": "3.0.0",
|
||||
"resolve-from": "5.0.0",
|
||||
"semver": "7.6.2",
|
||||
"source-map-support": "0.5.21",
|
||||
"teen_process": "2.1.4",
|
||||
"type-fest": "4.20.0",
|
||||
"teen_process": "2.2.0",
|
||||
"type-fest": "4.21.0",
|
||||
"winston": "3.13.0",
|
||||
"wrap-ansi": "7.0.0",
|
||||
"ws": "8.17.0",
|
||||
"ws": "8.18.0",
|
||||
"yaml": "2.4.5"
|
||||
},
|
||||
"engines": {
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
{
|
||||
"devDependencies": {
|
||||
"webdriverio": "8.38.2"
|
||||
"webdriverio": "8.39.1"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -10,15 +10,20 @@ import {
|
||||
runAppiumRaw,
|
||||
} from './e2e-helpers';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('argument parsing', function () {
|
||||
/**
|
||||
* @type {string}
|
||||
*/
|
||||
let appiumHome;
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
|
||||
appiumHome = await tempDir.openDir();
|
||||
});
|
||||
|
||||
|
||||
@@ -16,8 +16,6 @@ import {
|
||||
import {FAKE_DRIVER_DIR, resolveFixture} from '../helpers';
|
||||
import {installLocalExtension, runAppiumJson, runAppiumRaw} from './e2e-helpers';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
const TEST_DRIVER_DIR = path.dirname(resolveFixture('test-driver/package.json'));
|
||||
|
||||
const TEST_DRIVER_INVALID_PEERS_DIR = path.dirname(
|
||||
@@ -56,6 +54,7 @@ describe('Driver CLI', function () {
|
||||
* @type {(args: string[]) => Promise<ExtRecord<DriverType>>}
|
||||
*/
|
||||
let runDoctor;
|
||||
let expect;
|
||||
|
||||
async function resetAppiumHome() {
|
||||
await fs.rimraf(appiumHome);
|
||||
@@ -63,6 +62,12 @@ describe('Driver CLI', function () {
|
||||
}
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
|
||||
appiumHome = await tempDir.openDir();
|
||||
const run = runAppiumJson(appiumHome);
|
||||
runInstall = async (args) =>
|
||||
|
||||
@@ -5,8 +5,6 @@ import {EXT_SUBCOMMAND_RUN as RUN, PLUGIN_TYPE} from '../../lib/constants';
|
||||
import {FAKE_PLUGIN_DIR} from '../helpers';
|
||||
import {installLocalExtension, runAppiumJson} from './e2e-helpers';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('Plugin CLI', function () {
|
||||
/**
|
||||
* @type {string}
|
||||
@@ -17,8 +15,15 @@ describe('Plugin CLI', function () {
|
||||
* @type {(args: string[]) => Promise<{ output: string, error?: string }>}
|
||||
*/
|
||||
let runRun;
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
|
||||
appiumHome = await tempDir.openDir();
|
||||
const run = runAppiumJson(appiumHome);
|
||||
runRun = async (args) =>
|
||||
|
||||
@@ -22,6 +22,13 @@ describe('config file behavior', function () {
|
||||
const EXT_PROPS_FILEPATH = resolveConfigFixture('appium-config-ext-good.json');
|
||||
const LOG_FILTERS_FILEPATH = resolveConfigFixture('appium-config-log-filters.json');
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
finalizeSchema();
|
||||
});
|
||||
|
||||
@@ -6,6 +6,7 @@ import * as teenProcess from 'teen_process';
|
||||
|
||||
describe('Config', function () {
|
||||
let sandbox;
|
||||
let should;
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
@@ -15,6 +16,13 @@ describe('Config', function () {
|
||||
sandbox.restore();
|
||||
});
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
});
|
||||
|
||||
describe('getGitRev', function () {
|
||||
it('should get a reasonable git revision', async function () {
|
||||
let rev = await getGitRev();
|
||||
|
||||
@@ -23,8 +23,6 @@ import {
|
||||
W3C_PREFIXED_CAPS,
|
||||
} from '../helpers';
|
||||
|
||||
const should = chai.should();
|
||||
|
||||
/** @type {string} */
|
||||
let testServerBaseUrl;
|
||||
|
||||
@@ -87,8 +85,14 @@ describe('FakeDriver via HTTP', function () {
|
||||
|
||||
/** @type {import('sinon').SinonSandbox} */
|
||||
let sandbox;
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
|
||||
sandbox = createSandbox();
|
||||
appiumHome = await tempDir.openDir();
|
||||
wdOpts.port = port = await getTestPort();
|
||||
@@ -637,8 +641,14 @@ describe('Bidi over SSL', function () {
|
||||
let certPath = 'certificate.cert';
|
||||
let keyPath = 'certificate.key';
|
||||
const capabilities = {...caps, webSocketUrl: true};
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
|
||||
try {
|
||||
await generateCertificate(certPath, keyPath);
|
||||
} catch (e) {
|
||||
|
||||
@@ -14,7 +14,6 @@ import {FAKE_DRIVER_DIR, resolveFixture} from '../helpers';
|
||||
import {installLocalExtension, runAppiumJson} from './e2e-helpers';
|
||||
|
||||
const {MANIFEST_RELATIVE_PATH} = env;
|
||||
const {expect} = chai;
|
||||
const testDriverPath = path.dirname(resolveFixture('test-driver/package.json'));
|
||||
|
||||
describe('when Appium is a dependency of the current project', function () {
|
||||
@@ -26,8 +25,15 @@ describe('when Appium is a dependency of the current project', function () {
|
||||
let appiumHomePkgPath;
|
||||
/** @type {string} */
|
||||
let appiumHome;
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
|
||||
appiumHome = await tempDir.openDir();
|
||||
});
|
||||
|
||||
|
||||
@@ -10,8 +10,6 @@ import {
|
||||
import {FAKE_DRIVER_DIR, resolveFixture} from '../helpers';
|
||||
import {installLocalExtension, runAppiumJson} from './e2e-helpers';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('manifest handling', function () {
|
||||
/**
|
||||
* @type {string}
|
||||
@@ -27,6 +25,7 @@ describe('manifest handling', function () {
|
||||
* @type {(args?: string[]) => Promise<ExtensionListData>}
|
||||
*/
|
||||
let runList;
|
||||
let expect;
|
||||
|
||||
async function resetAppiumHome() {
|
||||
await fs.rimraf(appiumHome);
|
||||
@@ -34,6 +33,12 @@ describe('manifest handling', function () {
|
||||
}
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
|
||||
appiumHome = await tempDir.openDir();
|
||||
manifestPath = path.join(appiumHome, CACHE_DIR_RELATIVE_PATH, 'extensions.yaml');
|
||||
const run = runAppiumJson(appiumHome);
|
||||
|
||||
@@ -21,8 +21,6 @@ import {
|
||||
const FAKE_ARGS = {sillyWebServerPort: 1234, host: 'hey'};
|
||||
const FAKE_PLUGIN_ARGS = {fake: FAKE_ARGS};
|
||||
|
||||
const should = chai.should();
|
||||
|
||||
/** @type {import('webdriverio').RemoteOptions} */
|
||||
const wdOpts = {
|
||||
hostname: TEST_HOST,
|
||||
@@ -41,8 +39,14 @@ describe('FakePlugin w/ FakeDriver via HTTP', function () {
|
||||
let port;
|
||||
/** @type {string} */
|
||||
let testServerBaseSessionUrl;
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
|
||||
resetSchema();
|
||||
appiumHome = await tempDir.openDir();
|
||||
wdOpts.port = port = await getTestPort();
|
||||
|
||||
@@ -5,15 +5,20 @@ import {DRIVER_TYPE} from '../../lib/constants';
|
||||
import {resolveFixture} from '../helpers';
|
||||
import {installLocalExtension, runAppium} from './e2e-helpers';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('CLI behavior controlled by schema', function () {
|
||||
/**
|
||||
* @type {string}
|
||||
*/
|
||||
let appiumHome;
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
|
||||
appiumHome = await tempDir.openDir();
|
||||
});
|
||||
|
||||
|
||||
@@ -14,8 +14,6 @@ import BasePlugin from '@appium/base-plugin';
|
||||
|
||||
const SESSION_ID = '1';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('AppiumDriver', function () {
|
||||
/** @type {import('sinon').SinonSandbox} */
|
||||
let sandbox;
|
||||
@@ -25,6 +23,15 @@ describe('AppiumDriver', function () {
|
||||
|
||||
/** @type {MockConfig} */
|
||||
let MockConfig;
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
@@ -64,10 +71,10 @@ describe('AppiumDriver', function () {
|
||||
// triggers the `log` getter to set `_log`
|
||||
ad.log;
|
||||
// now we can stub `_log`, since it exists
|
||||
sandbox.stub(ad._log, 'debug');
|
||||
const debugStrub = sandbox.stub(ad._log, 'debug');
|
||||
// finally, wait for `updateBuildInfo()` to finish up
|
||||
await promise;
|
||||
ad._log.debug.should.have.been.calledOnce;
|
||||
debugStrub.calledOnce.should.be.true;
|
||||
});
|
||||
});
|
||||
|
||||
@@ -403,7 +410,7 @@ describe('AppiumDriver', function () {
|
||||
[ArgsPlugin, 'args'],
|
||||
]);
|
||||
for (const plugin of appium.createPluginInstances()) {
|
||||
chai.expect(plugin.cliArgs).to.eql({});
|
||||
expect(plugin.cliArgs).to.eql({});
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
@@ -17,6 +17,11 @@ describe('DriverCommand', function () {
|
||||
|
||||
let sandbox;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
beforeEach(async function () {
|
||||
sandbox = createSandbox();
|
||||
appiumHome = await tempDir.openDir();
|
||||
|
||||
@@ -2,8 +2,6 @@ import {createSandbox} from 'sinon';
|
||||
import {finalizeSchema, resetSchema, SchemaFinalizationError} from '../../../lib/schema/schema';
|
||||
import {rewiremock} from '../../helpers';
|
||||
|
||||
const expect = chai.expect;
|
||||
|
||||
describe('cli/schema-args', function () {
|
||||
/** @type {import('appium/lib/schema/cli-args').toParserArgs} */
|
||||
let toParserArgs;
|
||||
@@ -12,6 +10,15 @@ describe('cli/schema-args', function () {
|
||||
* @type {sinon.SinonSandbox}
|
||||
*/
|
||||
let sandbox;
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
|
||||
@@ -2,10 +2,17 @@ import {createSandbox} from 'sinon';
|
||||
import {system} from '@appium/support';
|
||||
import {getPresetDrivers} from '../../../lib/cli/setup-command';
|
||||
|
||||
const expect = chai.expect;
|
||||
|
||||
describe('SetupCommand', function () {
|
||||
let sandbox;
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
|
||||
@@ -6,8 +6,6 @@ import YAML from 'yaml';
|
||||
import * as schema from '../../lib/schema/schema';
|
||||
import {resolveFixture, rewiremock} from '../helpers';
|
||||
|
||||
const expect = chai.expect;
|
||||
|
||||
describe('config-file', function () {
|
||||
const GOOD_YAML_CONFIG_FILEPATH = resolveFixture('config', 'appium-config-good.yaml');
|
||||
const GOOD_JSON_CONFIG_FILEPATH = resolveFixture('config', 'appium-config-good.json');
|
||||
@@ -47,8 +45,15 @@ describe('config-file', function () {
|
||||
let lc;
|
||||
|
||||
let mocks;
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
|
||||
before(function () {
|
||||
// generally called via the CLI parser, this needs to be done manually in tests.
|
||||
// we don't need to do this before _each_ test, because we're not changing the schema.
|
||||
// if we did change the schema, this would need to be in `beforeEach()` and `afterEach()`
|
||||
@@ -120,19 +125,22 @@ describe('config-file', function () {
|
||||
it('should support yaml', async function () {
|
||||
const {config} = await readConfigFile(GOOD_YAML_CONFIG_FILEPATH);
|
||||
expect(config).to.eql(normalizeConfig(GOOD_JSON_CONFIG));
|
||||
expect(schema.validate).to.have.been.calledOnce;
|
||||
// @ts-ignore
|
||||
schema.validate.calledOnce.should.be.true;
|
||||
});
|
||||
|
||||
it('should support json', async function () {
|
||||
const {config} = await readConfigFile(GOOD_JSON_CONFIG_FILEPATH);
|
||||
expect(config).to.eql(normalizeConfig(GOOD_JSON_CONFIG));
|
||||
expect(schema.validate).to.have.been.calledOnce;
|
||||
// @ts-ignore
|
||||
schema.validate.calledOnce.should.be.true;
|
||||
});
|
||||
|
||||
it('should support js', async function () {
|
||||
const {config} = await readConfigFile(GOOD_JS_CONFIG_FILEPATH);
|
||||
expect(config).to.eql(normalizeConfig(GOOD_JSON_CONFIG));
|
||||
expect(schema.validate).to.have.been.calledOnce;
|
||||
// @ts-ignore
|
||||
schema.validate.calledOnce.should.be.true;
|
||||
});
|
||||
|
||||
describe('when no filepath provided', function () {
|
||||
@@ -141,12 +149,13 @@ describe('config-file', function () {
|
||||
});
|
||||
|
||||
it('should search for a config file', function () {
|
||||
expect(lc.search).to.have.been.calledOnce;
|
||||
expect(schema.validate).to.have.been.calledOnce;
|
||||
lc.search.calledOnce.should.be.true;
|
||||
// @ts-ignore
|
||||
schema.validate.calledOnce.should.be.true;
|
||||
});
|
||||
|
||||
it('should not try to load a config file directly', function () {
|
||||
expect(lc.load).to.not.have.been.called;
|
||||
lc.load.called.should.be.false;
|
||||
});
|
||||
|
||||
describe('when no config file is found', function () {
|
||||
@@ -160,7 +169,8 @@ describe('config-file', function () {
|
||||
|
||||
it('should resolve with an empty object', function () {
|
||||
expect(result).to.be.an('object').that.is.empty;
|
||||
expect(schema.validate).not.to.have.been.called;
|
||||
// @ts-ignore
|
||||
schema.validate.calledOnce.should.be.false;
|
||||
});
|
||||
});
|
||||
|
||||
@@ -183,7 +193,8 @@ describe('config-file', function () {
|
||||
|
||||
describe('when the config file is not empty', function () {
|
||||
it('should validate the config against a schema', function () {
|
||||
expect(schema.validate).to.have.been.calledOnceWith(GOOD_JSON_CONFIG);
|
||||
// @ts-ignore
|
||||
schema.validate.calledOnceWith(GOOD_JSON_CONFIG).should.be.true;
|
||||
});
|
||||
|
||||
describe('when the config file is valid', function () {
|
||||
@@ -226,11 +237,11 @@ describe('config-file', function () {
|
||||
});
|
||||
|
||||
it('should not attempt to find a config file', function () {
|
||||
expect(lc.search).to.not.have.been.called;
|
||||
lc.search.called.should.be.false;
|
||||
});
|
||||
|
||||
it('should try to load a config file directly', function () {
|
||||
expect(lc.load).to.have.been.calledOnce;
|
||||
lc.load.calledOnce.should.be.true;
|
||||
});
|
||||
|
||||
describe('when no config file exists at path', function () {
|
||||
@@ -285,7 +296,8 @@ describe('config-file', function () {
|
||||
|
||||
describe('when the config file is not empty', function () {
|
||||
it('should validate the config against a schema', function () {
|
||||
expect(schema.validate).to.have.been.calledOnceWith(GOOD_JSON_CONFIG);
|
||||
// @ts-ignore
|
||||
schema.validate.calledOnceWith(GOOD_JSON_CONFIG).should.be.true;
|
||||
});
|
||||
|
||||
describe('when the config file is valid', function () {
|
||||
@@ -340,12 +352,12 @@ describe('config-file', function () {
|
||||
it('should call `betterAjvErrors()` with option `json: opts.json`', function () {
|
||||
// @ts-expect-error
|
||||
formatErrors([{}], {}, {json: '{"foo": "bar"}'});
|
||||
expect(mocks['@sidvind/better-ajv-errors']).to.have.been.calledWith(
|
||||
mocks['@sidvind/better-ajv-errors'].calledWith(
|
||||
schema.getSchema(),
|
||||
{},
|
||||
[{}],
|
||||
{format: 'cli', json: '{"foo": "bar"}'}
|
||||
);
|
||||
).should.be.true;
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -23,6 +23,13 @@ describe('Config', function () {
|
||||
/** @type {sinon.SinonSandbox} */
|
||||
let sandbox;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
});
|
||||
@@ -45,7 +52,7 @@ describe('Config', function () {
|
||||
it('should log build info to console', async function () {
|
||||
const config = getBuildInfo();
|
||||
await showBuildInfo();
|
||||
log.should.have.been.calledOnce;
|
||||
log.calledOnce.should.be.true;
|
||||
log.firstCall.args.should.contain(JSON.stringify(config));
|
||||
});
|
||||
});
|
||||
@@ -64,7 +71,7 @@ describe('Config', function () {
|
||||
{port: 1234},
|
||||
{allowCors: false}
|
||||
);
|
||||
log.should.have.been.calledWith('Appium Configuration\n');
|
||||
log.calledWith('Appium Configuration\n').should.be.true;
|
||||
});
|
||||
|
||||
it('should skip empty objects', function () {
|
||||
@@ -75,7 +82,7 @@ describe('Config', function () {
|
||||
{spam: 'food'},
|
||||
{}
|
||||
);
|
||||
dir.should.have.been.calledWith({foo: 'bar', sheep: 0, ducks: false});
|
||||
dir.calledWith({foo: 'bar', sheep: 0, ducks: false}).should.be.true;
|
||||
});
|
||||
});
|
||||
|
||||
@@ -88,7 +95,7 @@ describe('Config', function () {
|
||||
{spam: 'food'},
|
||||
{}
|
||||
);
|
||||
log.should.have.been.calledWith('\n(no configuration file loaded)');
|
||||
log.calledWith('\n(no configuration file loaded)').should.be.true;
|
||||
});
|
||||
});
|
||||
|
||||
@@ -96,7 +103,7 @@ describe('Config', function () {
|
||||
it('should not dump CLI args', function () {
|
||||
// @ts-expect-error
|
||||
showConfig({}, {}, {}, {});
|
||||
log.should.have.been.calledWith('\n(no CLI parameters provided)');
|
||||
log.calledWith('\n(no CLI parameters provided)').should.be.true;
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -6,8 +6,6 @@ import {resetSchema} from '../../../lib/schema';
|
||||
import {resolveFixture, rewiremock} from '../../helpers';
|
||||
import {initMocks} from './mocks';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('DriverConfig', function () {
|
||||
/** @type {string} */
|
||||
let yamlFixture;
|
||||
@@ -31,7 +29,15 @@ describe('DriverConfig', function () {
|
||||
*/
|
||||
let DriverConfig;
|
||||
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
|
||||
yamlFixture = await fs.readFile(resolveFixture('manifest', 'v3.yaml'), 'utf8');
|
||||
});
|
||||
|
||||
@@ -338,7 +344,7 @@ describe('DriverConfig', function () {
|
||||
driverConfig.readExtensionSchema(extName, extData);
|
||||
|
||||
// we don't have access to the schema registration cache directly, so this is as close as we can get.
|
||||
expect(MockResolveFrom).to.have.been.calledOnce;
|
||||
MockResolveFrom.calledOnce.should.be.true;
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -5,8 +5,6 @@ import sinon from 'sinon';
|
||||
import {FAKE_DRIVER_DIR} from '../../helpers';
|
||||
import {Manifest} from '../../../lib/extension/manifest';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
/**
|
||||
* Relative path from actual `package.json` of `FakeDriver` for the `fake-stdin` script
|
||||
*/
|
||||
@@ -20,6 +18,16 @@ describe('ExtensionCommand', function () {
|
||||
/** @type {sinon.SinonSandbox} */
|
||||
let sandbox;
|
||||
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = sinon.createSandbox();
|
||||
const driverConfig = DriverConfig.create(sandbox.createStubInstance(Manifest));
|
||||
|
||||
@@ -4,8 +4,6 @@ import {version as APPIUM_VER} from '../../../package.json';
|
||||
import {FAKE_DRIVER_DIR, PROJECT_ROOT, rewiremock} from '../../helpers';
|
||||
import {initMocks} from './mocks';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('ExtensionConfig', function () {
|
||||
/** @type {import('sinon').SinonSandbox} */
|
||||
let sandbox;
|
||||
@@ -19,6 +17,16 @@ describe('ExtensionConfig', function () {
|
||||
/** @type {import('./mocks').MockAppiumSupport} */
|
||||
let MockAppiumSupport;
|
||||
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
let overrides;
|
||||
({MockAppiumSupport, overrides, sandbox} = initMocks());
|
||||
@@ -270,9 +278,9 @@ describe('ExtensionConfig', function () {
|
||||
|
||||
it('should display a warning count of 1', async function () {
|
||||
await config._validate({foo: {}});
|
||||
expect(MockAppiumSupport.logger.__logger.warn).to.be.calledWith(
|
||||
MockAppiumSupport.logger.__logger.warn.calledWith(
|
||||
'Appium encountered 1 warning while validating drivers found in manifest /some/path/extensions.yaml'
|
||||
);
|
||||
).should.be.true;
|
||||
});
|
||||
});
|
||||
|
||||
@@ -284,9 +292,9 @@ describe('ExtensionConfig', function () {
|
||||
|
||||
it('should display an error count of 1', async function () {
|
||||
await config._validate({foo: {}});
|
||||
expect(MockAppiumSupport.logger.__logger.error).to.be.calledWith(
|
||||
MockAppiumSupport.logger.__logger.error.calledWith(
|
||||
'Appium encountered 1 error while validating drivers found in manifest /some/path/extensions.yaml'
|
||||
);
|
||||
).should.be.true;
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -2,9 +2,17 @@ import {Manifest} from '../../../lib/extension/manifest';
|
||||
import {migrate} from '../../../lib/extension/manifest-migrations';
|
||||
import {DRIVER_TYPE} from '../../../lib/constants';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('manifest-migrations', function () {
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
describe('when no installPath property present in manifest', function () {
|
||||
it('should trigger refresh', async function () {
|
||||
const manifest = Manifest.getInstance(process.cwd());
|
||||
|
||||
@@ -7,8 +7,6 @@ import {initMocks} from './mocks';
|
||||
import {version as APPIUM_VER} from '../../../package.json';
|
||||
import EventEmitter from 'events';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('Manifest', function () {
|
||||
/**
|
||||
* @type {sinon.SinonSandbox}
|
||||
@@ -27,7 +25,15 @@ describe('Manifest', function () {
|
||||
/** @type {import('./mocks').MockGlob} */
|
||||
let MockGlob;
|
||||
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
|
||||
yamlFixture = await fs.readFile(resolveFixture('manifest', 'v3.yaml'), 'utf8');
|
||||
});
|
||||
|
||||
@@ -143,7 +149,7 @@ describe('Manifest', function () {
|
||||
});
|
||||
|
||||
it('should create a new file', function () {
|
||||
expect(MockAppiumSupport.fs.writeFile).to.be.calledOnce;
|
||||
MockAppiumSupport.fs.writeFile.calledOnce.should.be.true;
|
||||
});
|
||||
});
|
||||
|
||||
@@ -179,10 +185,10 @@ describe('Manifest', function () {
|
||||
await B.all([manifest.read(), manifest.read()]);
|
||||
});
|
||||
it('should not read the file twice', function () {
|
||||
expect(MockAppiumSupport.fs.readFile).to.have.been.calledOnceWith(
|
||||
MockAppiumSupport.fs.readFile.calledOnceWith(
|
||||
'/some/path/extensions.yaml',
|
||||
'utf8'
|
||||
);
|
||||
).should.be.true;
|
||||
});
|
||||
});
|
||||
|
||||
@@ -193,15 +199,16 @@ describe('Manifest', function () {
|
||||
});
|
||||
|
||||
it('should attempt to read the file at `filepath`', function () {
|
||||
expect(MockAppiumSupport.fs.readFile).to.have.been.calledOnceWith(
|
||||
MockAppiumSupport.fs.readFile.calledOnceWith(
|
||||
'/some/path/extensions.yaml',
|
||||
'utf8'
|
||||
);
|
||||
).should.be.true;
|
||||
});
|
||||
|
||||
describe('when the data has not changed', function () {
|
||||
it('should not write the data', function () {
|
||||
expect(manifest.write).not.to.be.called;
|
||||
// @ts-ignore
|
||||
manifest.write.called.should.be.false;
|
||||
});
|
||||
});
|
||||
|
||||
@@ -218,12 +225,13 @@ describe('Manifest', function () {
|
||||
|
||||
it('should synchronize manifest with installed extensions', async function () {
|
||||
await manifest.read();
|
||||
expect(manifest.syncWithInstalledExtensions).to.be.calledOnce;
|
||||
// @ts-ignore
|
||||
manifest.syncWithInstalledExtensions.calledOnce.should.be.true;
|
||||
});
|
||||
|
||||
it('should check if the `package.json` has changed', async function () {
|
||||
await manifest.read();
|
||||
expect(MockPackageChanged.isPackageChanged).to.be.calledOnce;
|
||||
MockPackageChanged.isPackageChanged.calledOnce.should.be.true;
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -258,7 +266,7 @@ describe('Manifest', function () {
|
||||
describe('when called again before the first call resolves', function () {
|
||||
it('should not write the file twice', async function () {
|
||||
await B.all([manifest.write(), manifest.write()]);
|
||||
expect(MockAppiumSupport.fs.writeFile).to.have.been.calledOnce;
|
||||
MockAppiumSupport.fs.writeFile.calledOnce.should.be.true;
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -4,8 +4,6 @@ import {PKG_HASHFILE_RELATIVE_PATH} from '../../../lib/constants';
|
||||
import {rewiremock} from '../../helpers';
|
||||
import {initMocks} from './mocks';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('package-changed', function () {
|
||||
/** @type {typeof import('appium/lib/extension/package-changed').packageDidChange} */
|
||||
let packageDidChange;
|
||||
@@ -19,6 +17,16 @@ describe('package-changed', function () {
|
||||
/** @type {import('./mocks').MockAppiumSupport} */
|
||||
let MockAppiumSupport;
|
||||
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
({MockPackageChanged, MockAppiumSupport, sandbox} = initMocks());
|
||||
({packageDidChange} = rewiremock.proxy(
|
||||
@@ -46,17 +54,17 @@ describe('package-changed', function () {
|
||||
|
||||
it('it should attempt to create the parent dir for the hash file', async function () {
|
||||
await packageDidChange('/some/path');
|
||||
expect(MockAppiumSupport.fs.mkdirp).to.have.been.calledWith(
|
||||
MockAppiumSupport.fs.mkdirp.calledWith(
|
||||
path.dirname(path.join('/some/path', PKG_HASHFILE_RELATIVE_PATH))
|
||||
);
|
||||
).should.be.true;
|
||||
});
|
||||
|
||||
it('should call `package-changed` with a cwd and relative path to hash file', async function () {
|
||||
await packageDidChange('/some/path');
|
||||
expect(MockPackageChanged.isPackageChanged).to.have.been.calledWith({
|
||||
MockPackageChanged.isPackageChanged.calledWith({
|
||||
cwd: '/some/path',
|
||||
hashFilename: PKG_HASHFILE_RELATIVE_PATH,
|
||||
});
|
||||
}).should.be.true;
|
||||
});
|
||||
|
||||
describe('when it cannot create the parent dir', function () {
|
||||
@@ -85,14 +93,14 @@ describe('package-changed', function () {
|
||||
|
||||
it('should not write the hash file', async function () {
|
||||
await packageDidChange('/some/where');
|
||||
expect(MockPackageChanged.__writeHash).not.to.have.been.called;
|
||||
MockPackageChanged.__writeHash.called.should.be.false;
|
||||
});
|
||||
});
|
||||
|
||||
describe('when the package has changed per `package-changed`', function () {
|
||||
it('should write the hash file', async function () {
|
||||
await packageDidChange('/some/where');
|
||||
expect(MockPackageChanged.__writeHash).to.have.been.calledOnce;
|
||||
MockPackageChanged.__writeHash.calledOnce.should.be.true;
|
||||
});
|
||||
|
||||
it('should resolve `true`', async function () {
|
||||
|
||||
@@ -6,8 +6,6 @@ import {resetSchema} from '../../../lib/schema';
|
||||
import {resolveFixture, rewiremock} from '../../helpers';
|
||||
import {initMocks} from './mocks';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('PluginConfig', function () {
|
||||
/** @type {string} */
|
||||
let yamlFixture;
|
||||
@@ -31,7 +29,15 @@ describe('PluginConfig', function () {
|
||||
*/
|
||||
let PluginConfig;
|
||||
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
|
||||
yamlFixture = await fs.readFile(resolveFixture('manifest', 'v3.yaml'), 'utf8');
|
||||
});
|
||||
|
||||
@@ -337,7 +343,7 @@ describe('PluginConfig', function () {
|
||||
describe('when the extension schema has not yet been registered', function () {
|
||||
it('should resolve and load the extension schema file', function () {
|
||||
pluginConfig.readExtensionSchema(extName, extData);
|
||||
expect(MockResolveFrom).to.have.been.calledOnce;
|
||||
MockResolveFrom.calledOnce.should.be.true;
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -6,6 +6,13 @@ import {rewiremock} from '../helpers';
|
||||
describe('grid-register', function () {
|
||||
let sandbox;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
});
|
||||
@@ -38,18 +45,18 @@ describe('grid-register', function () {
|
||||
describe('when provided a path to a config file', function () {
|
||||
it('should read the config file', async function () {
|
||||
await registerNode('/path/to/config-file.json');
|
||||
mocks['@appium/support'].fs.readFile.should.have.been.calledOnceWith(
|
||||
mocks['@appium/support'].fs.readFile.calledOnceWith(
|
||||
'/path/to/config-file.json',
|
||||
'utf-8'
|
||||
);
|
||||
).should.be.true;
|
||||
});
|
||||
|
||||
it('should parse the config file as JSON', async function () {
|
||||
sandbox.spy(JSON, 'parse');
|
||||
const parseSpy = sandbox.spy(JSON, 'parse');
|
||||
await registerNode('/path/to/config-file.json');
|
||||
JSON.parse.should.have.been.calledOnceWith(
|
||||
parseSpy.calledOnceWith(
|
||||
await mocks['@appium/support'].fs.readFile.firstCall.returnValue
|
||||
);
|
||||
).should.be.true;
|
||||
});
|
||||
|
||||
describe('when the config file is invalid', function () {
|
||||
@@ -65,13 +72,13 @@ describe('grid-register', function () {
|
||||
describe('when provided a config object', function () {
|
||||
it('should not attempt to read the object as a config file', async function () {
|
||||
await registerNode({my: 'config'});
|
||||
mocks['@appium/support'].fs.readFile.should.not.have.been.called;
|
||||
mocks['@appium/support'].fs.readFile.called.should.be.false;
|
||||
});
|
||||
|
||||
it('should not attempt to parse any JSON', async function () {
|
||||
sandbox.spy(JSON, 'parse');
|
||||
const parseSpy = sandbox.spy(JSON, 'parse');
|
||||
await registerNode({my: 'config'});
|
||||
JSON.parse.should.not.have.been.called;
|
||||
parseSpy.called.should.be.false;
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -11,7 +11,12 @@ describe('logging', function () {
|
||||
let sandbox;
|
||||
let stderrSpy;
|
||||
let stdoutSpy;
|
||||
beforeEach(function () {
|
||||
beforeEach(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
|
||||
sandbox = createSandbox();
|
||||
stderrSpy = sandbox.spy(process.stderr, 'write');
|
||||
stdoutSpy = sandbox.spy(process.stdout, 'write');
|
||||
|
||||
@@ -14,6 +14,14 @@ const LOG_FILTERS_FIXTURE = resolveFixture('log-filters.json');
|
||||
|
||||
describe('parser', function () {
|
||||
let p;
|
||||
let should;
|
||||
|
||||
beforeEach(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
});
|
||||
|
||||
describe('Main Parser', function () {
|
||||
beforeEach(function () {
|
||||
|
||||
@@ -3,9 +3,15 @@
|
||||
import {DRIVER_TYPE} from '../../../lib/constants';
|
||||
import {ArgSpec} from '../../../lib/schema/arg-spec';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('ArgSpec', function () {
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
describe('class method', function () {
|
||||
describe('create()', function () {
|
||||
it('should return a new ArgSpec', function () {
|
||||
@@ -69,9 +75,11 @@ describe('ArgSpec', function () {
|
||||
});
|
||||
|
||||
describe('when provided the schema ID of an extension schema', function () {
|
||||
expect(ArgSpec.extensionInfoFromRootSchemaId('driver-stuff.json')).to.eql({
|
||||
extType: DRIVER_TYPE,
|
||||
normalizedExtName: 'stuff',
|
||||
it('should return an proper object', function () {
|
||||
expect(ArgSpec.extensionInfoFromRootSchemaId('driver-stuff.json')).to.eql({
|
||||
extType: DRIVER_TYPE,
|
||||
normalizedExtName: 'stuff',
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -5,9 +5,17 @@ import {PLUGIN_TYPE} from '../../../lib/constants';
|
||||
import {finalizeSchema, registerSchema, resetSchema} from '../../../lib/schema';
|
||||
import {toParserArgs} from '../../../lib/schema/cli-args';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('cli-args', function () {
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
describe('toParserArgs()', function () {
|
||||
/**
|
||||
*
|
||||
|
||||
@@ -10,12 +10,12 @@ import DRIVER_SCHEMA_FIXTURE from '../../fixtures/driver-schema';
|
||||
import flattenedSchemaFixture from '../../fixtures/flattened-schema';
|
||||
import {rewiremock} from '../../helpers';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('schema', function () {
|
||||
/** @type {sinon.SinonSandbox} */
|
||||
let sandbox;
|
||||
|
||||
let expect;
|
||||
|
||||
/**
|
||||
* @type {import('@appium/types').Class<import('appium/lib/schema/schema').SchemaFinalizationError>}
|
||||
*/
|
||||
@@ -78,6 +78,14 @@ describe('schema', function () {
|
||||
*/
|
||||
let RoachHotelMap;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
|
||||
|
||||
@@ -15,6 +15,15 @@ import logger from '../../lib/logger';
|
||||
import {fs} from '@appium/support';
|
||||
|
||||
describe('utils', function () {
|
||||
let should;
|
||||
|
||||
beforeEach(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
});
|
||||
|
||||
describe('parseCapsForInnerDriver()', function () {
|
||||
it('should return an error if only JSONWP provided', function () {
|
||||
let {error, protocol} = parseCapsForInnerDriver(BASE_CAPS);
|
||||
|
||||
@@ -3,6 +3,57 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
## [9.11.2](https://github.com/appium/appium/compare/@appium/base-driver@9.11.1...@appium/base-driver@9.11.2) (2024-07-10)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **types:** update dependency type-fest to v4.21.0 ([#20335](https://github.com/appium/appium/issues/20335)) ([8894b9a](https://github.com/appium/appium/commit/8894b9adf709646108cc8d6426bbb690550609f2))
|
||||
|
||||
|
||||
|
||||
## [9.11.1](https://github.com/appium/appium/compare/@appium/base-driver@9.11.0...@appium/base-driver@9.11.1) (2024-06-28)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **driver-test-support:** update dependency @types/lodash to v4.17.6 ([82e40c1](https://github.com/appium/appium/commit/82e40c1400e23f341c45d788982ccc5905827d7c))
|
||||
* **images-plugin:** update dependency lru-cache to v10.3.0 ([#20306](https://github.com/appium/appium/issues/20306)) ([e43c7a4](https://github.com/appium/appium/commit/e43c7a4dce1f50fbd4d028cbeac5677422210b20))
|
||||
|
||||
|
||||
|
||||
## [9.11.0](https://github.com/appium/appium/compare/@appium/base-driver@9.10.3...@appium/base-driver@9.11.0) (2024-06-27)
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* **appium:** Improve context logging ([#20250](https://github.com/appium/appium/issues/20250)) ([f675abc](https://github.com/appium/appium/commit/f675abc27b3e6beac2431cc71afb5fc2c2f70534))
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **base-driver:** Check if app path is relative earlier ([#20276](https://github.com/appium/appium/issues/20276)) ([2882e71](https://github.com/appium/appium/commit/2882e7163159b7918d54cc4521105a1fdf55da9a))
|
||||
* **base-driver:** update dependency path-to-regexp to v7 ([#20279](https://github.com/appium/appium/issues/20279)) ([a746eef](https://github.com/appium/appium/commit/a746eefbbb627c7f7dd9d1ce13226a88d9527129))
|
||||
* **types:** update dependency type-fest to v4.20.1 ([#20255](https://github.com/appium/appium/issues/20255)) ([1984553](https://github.com/appium/appium/commit/19845531f558e2b16dfae807c768e1b9f2cab25d))
|
||||
|
||||
|
||||
|
||||
## [9.10.3](https://github.com/appium/appium/compare/@appium/base-driver@9.10.2...@appium/base-driver@9.10.3) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/base-driver
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [9.10.2](https://github.com/appium/appium/compare/@appium/base-driver@9.10.1...@appium/base-driver@9.10.2) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/base-driver
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [9.10.1](https://github.com/appium/appium/compare/@appium/base-driver@9.10.0...@appium/base-driver@9.10.1) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/base-driver
|
||||
|
||||
@@ -20,6 +20,7 @@ import {
|
||||
import B from 'bluebird';
|
||||
import _ from 'lodash';
|
||||
import {fixCaps, isW3cCaps} from '../helpers/capabilities';
|
||||
import {calcSignature} from '../helpers/session';
|
||||
import {DELETE_SESSION_COMMAND, determineProtocol, errors} from '../protocol';
|
||||
import {processCapabilities, validateCaps} from './capabilities';
|
||||
import {DriverCore} from './core';
|
||||
@@ -309,6 +310,11 @@ export class BaseDriver<
|
||||
|
||||
this._log.prefix = helpers.generateDriverLogPrefix(this);
|
||||
|
||||
this.log.updateAsyncContext({
|
||||
sessionId: this.sessionId,
|
||||
sessionSignature: calcSignature(this.sessionId),
|
||||
});
|
||||
|
||||
this.log.info(`Session created with session id: ${this.sessionId}`);
|
||||
|
||||
return [this.sessionId, caps] as CreateResult;
|
||||
|
||||
@@ -105,6 +105,14 @@ export async function configureApp(
|
||||
};
|
||||
const {protocol, pathname} = parseAppLink(app);
|
||||
const isUrl = isSupportedUrl(app);
|
||||
if (!isUrl && !path.isAbsolute(newApp)) {
|
||||
newApp = path.resolve(process.cwd(), newApp);
|
||||
logger.warn(
|
||||
`The current application path '${app}' is not absolute ` +
|
||||
`and has been rewritten to '${newApp}'. Consider using absolute paths rather than relative`
|
||||
);
|
||||
app = newApp;
|
||||
}
|
||||
const appCacheKey = toCacheKey(app);
|
||||
|
||||
const cachedAppInfo = APPLICATIONS_CACHE.get(appCacheKey);
|
||||
@@ -276,13 +284,6 @@ export async function configureApp(
|
||||
}
|
||||
}
|
||||
logger.info(`Unzipped local app to '${newApp}'`);
|
||||
} else if (!path.isAbsolute(newApp)) {
|
||||
newApp = path.resolve(process.cwd(), newApp);
|
||||
logger.warn(
|
||||
`The current application path '${app}' is not absolute ` +
|
||||
`and has been rewritten to '${newApp}'. Consider using absolute paths rather than relative`
|
||||
);
|
||||
app = newApp;
|
||||
}
|
||||
|
||||
const storeAppInCache = async (appPathToCache) => {
|
||||
|
||||
@@ -144,6 +144,9 @@ async function handleIdempotency(req, res, next) {
|
||||
}
|
||||
|
||||
const key = _.isArray(keyOrArr) ? keyOrArr[0] : keyOrArr;
|
||||
|
||||
log.updateAsyncContext({idempotencyKey: key});
|
||||
|
||||
if (!MONITORED_METHODS.includes(req.method)) {
|
||||
// GET, DELETE, etc. requests are idempotent by default
|
||||
// there is no need to cache them
|
||||
|
||||
@@ -3,6 +3,8 @@ import log from './logger';
|
||||
import {errors} from '../protocol';
|
||||
export {handleIdempotency} from './idempotency';
|
||||
import {pathToRegexp} from 'path-to-regexp';
|
||||
import {util} from '@appium/support';
|
||||
import {calcSignature} from '../helpers/session';
|
||||
|
||||
/**
|
||||
*
|
||||
@@ -76,15 +78,13 @@ export function fixPythonContentType(basePath) {
|
||||
* @returns {any}
|
||||
*/
|
||||
export function handleLogContext(req, res, next) {
|
||||
const contextStorage = global._global_npmlog?.asyncStorage;
|
||||
if (!contextStorage) {
|
||||
return next();
|
||||
}
|
||||
const requestId = util.uuidV4();
|
||||
|
||||
const sessionId = SESSION_ID_PATTERN.exec(req.url)?.[1];
|
||||
const sessionInfo = sessionId ? {sessionId, sessionSignature: calcSignature(sessionId)} : {};
|
||||
|
||||
log.updateAsyncContext({requestId, ...sessionInfo}, true);
|
||||
|
||||
const sessionIdMatch = SESSION_ID_PATTERN.exec(req.url);
|
||||
contextStorage.enterWith(
|
||||
sessionIdMatch ? {sessionSignature: sessionIdMatch[1].substring(0, 8)} : {}
|
||||
);
|
||||
return next();
|
||||
}
|
||||
|
||||
|
||||
@@ -28,10 +28,10 @@ import {
|
||||
} from './websocket';
|
||||
import B from 'bluebird';
|
||||
import {DEFAULT_BASE_PATH} from '../constants';
|
||||
import {EventEmitter} from 'events';
|
||||
import {fs} from '@appium/support';
|
||||
import {fs, timing} from '@appium/support';
|
||||
|
||||
const KEEP_ALIVE_TIMEOUT_MS = 10 * 60 * 1000; // 10 minutes
|
||||
const SERVER_CLOSE_TIMEOUT_MS = 5000;
|
||||
|
||||
/**
|
||||
*
|
||||
@@ -192,10 +192,6 @@ function configureServer({
|
||||
* @returns {AppiumServer}
|
||||
*/
|
||||
function configureHttp({httpServer, reject, keepAliveTimeout}) {
|
||||
const serverState = {
|
||||
notifier: new EventEmitter(),
|
||||
closed: false,
|
||||
};
|
||||
/**
|
||||
* @type {AppiumServer}
|
||||
*/
|
||||
@@ -208,23 +204,34 @@ function configureHttp({httpServer, reject, keepAliveTimeout}) {
|
||||
|
||||
// http.Server.close() only stops new connections, but we need to wait until
|
||||
// all connections are closed and the `close` event is emitted
|
||||
const close = appiumServer.close.bind(appiumServer);
|
||||
const originalClose = appiumServer.close.bind(appiumServer);
|
||||
appiumServer.close = async () =>
|
||||
await new B((resolve, reject) => {
|
||||
// https://github.com/nodejs/node-v0.x-archive/issues/9066#issuecomment-124210576
|
||||
serverState.closed = true;
|
||||
serverState.notifier.emit('shutdown');
|
||||
log.info('Waiting until the server is closed');
|
||||
httpServer.on('close', () => {
|
||||
log.info('Received server close event');
|
||||
resolve();
|
||||
await new B((_resolve, _reject) => {
|
||||
log.info('Closing Appium HTTP server');
|
||||
const timer = new timing.Timer().start();
|
||||
const onTimeout = setTimeout(() => {
|
||||
log.info(
|
||||
`Not all active connections have been closed within ` +
|
||||
`${timer.getDuration().asMilliSeconds.toFixed(0)}ms. Exiting anyway.`
|
||||
);
|
||||
process.exit(process.exitCode ?? 0);
|
||||
}, SERVER_CLOSE_TIMEOUT_MS);
|
||||
httpServer.once('close', () => {
|
||||
log.info(
|
||||
`Appium HTTP server has been succesfully closed after ` +
|
||||
`${timer.getDuration().asMilliSeconds.toFixed(0)}ms`
|
||||
);
|
||||
clearTimeout(onTimeout);
|
||||
_resolve();
|
||||
});
|
||||
close((err) => {
|
||||
if (err) reject(err); // eslint-disable-line curly
|
||||
originalClose((/** @type {Error|undefined} */ err) => {
|
||||
if (err) {
|
||||
_reject(err);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
appiumServer.on(
|
||||
appiumServer.once(
|
||||
'error',
|
||||
/** @param {NodeJS.ErrnoException} err */ (err) => {
|
||||
if (err.code === 'EADDRNOTAVAIL') {
|
||||
@@ -242,31 +249,7 @@ function configureHttp({httpServer, reject, keepAliveTimeout}) {
|
||||
}
|
||||
);
|
||||
|
||||
appiumServer.on(
|
||||
'connection',
|
||||
/** @param {AppiumServerSocket} socket */ (socket) => {
|
||||
socket.setTimeout(keepAliveTimeout);
|
||||
socket.on('error', reject);
|
||||
|
||||
function destroy() {
|
||||
socket.destroy();
|
||||
}
|
||||
socket._openReqCount = 0;
|
||||
socket.once('close', () => serverState.notifier.removeListener('shutdown', destroy));
|
||||
serverState.notifier.once('shutdown', destroy);
|
||||
}
|
||||
);
|
||||
|
||||
appiumServer.on('request', function (req, res) {
|
||||
const socket = /** @type {AppiumServerSocket} */ (req.connection || req.socket);
|
||||
socket._openReqCount++;
|
||||
res.on('finish', function () {
|
||||
socket._openReqCount--;
|
||||
if (serverState.closed && socket._openReqCount === 0) {
|
||||
socket.destroy();
|
||||
}
|
||||
});
|
||||
});
|
||||
appiumServer.on('connection', (socket) => socket.setTimeout(keepAliveTimeout));
|
||||
|
||||
return appiumServer;
|
||||
}
|
||||
@@ -324,7 +307,6 @@ export {server, configureServer, normalizeBasePath};
|
||||
|
||||
/**
|
||||
* @typedef {import('@appium/types').AppiumServer} AppiumServer
|
||||
* @typedef {import('@appium/types').AppiumServerSocket} AppiumServerSocket
|
||||
*/
|
||||
|
||||
/**
|
||||
|
||||
@@ -0,0 +1,8 @@
|
||||
/**
|
||||
* Extract the first 8 characters of session ID to prefix the log.
|
||||
*
|
||||
* @param sessionId session identifier
|
||||
*/
|
||||
export function calcSignature(sessionId: string): string {
|
||||
return sessionId.substring(0, 8);
|
||||
}
|
||||
@@ -3,6 +3,7 @@
|
||||
import _ from 'lodash';
|
||||
import {util} from '@appium/support';
|
||||
import {PROTOCOLS, DEFAULT_BASE_PATH} from '../constants';
|
||||
import {pathToRegexp} from 'path-to-regexp';
|
||||
|
||||
const SET_ALERT_TEXT_PAYLOAD_PARAMS = {
|
||||
validate: (jsonObj) =>
|
||||
@@ -20,7 +21,7 @@ const SET_ALERT_TEXT_PAYLOAD_PARAMS = {
|
||||
* `optional`
|
||||
* @satisfies {import('@appium/types').MethodMap<import('../basedriver/driver').BaseDriver>}
|
||||
*/
|
||||
const METHOD_MAP = /** @type {const} */ ({
|
||||
export const METHOD_MAP = /** @type {const} */ ({
|
||||
'/status': {
|
||||
GET: {command: 'getStatus'},
|
||||
},
|
||||
@@ -918,90 +919,48 @@ const METHOD_MAP = /** @type {const} */ ({
|
||||
});
|
||||
|
||||
// driver command names
|
||||
let ALL_COMMANDS = [];
|
||||
for (let v of _.values(METHOD_MAP)) {
|
||||
for (let m of _.values(v)) {
|
||||
if ('command' in m && m.command) {
|
||||
ALL_COMMANDS.push(m.command);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const RE_ESCAPE = /[-[\]{}()+?.,\\^$|#\s]/g;
|
||||
const RE_PARAM = /([:*])(\w+)/g;
|
||||
|
||||
class Route {
|
||||
constructor(route) {
|
||||
this.paramNames = [];
|
||||
|
||||
let reStr = route.replace(RE_ESCAPE, '\\$&');
|
||||
reStr = reStr.replace(RE_PARAM, (_, mode, name) => {
|
||||
this.paramNames.push(name);
|
||||
return mode === ':' ? '([^/]*)' : '(.*)';
|
||||
});
|
||||
this.routeRegexp = new RegExp(`^${reStr}$`);
|
||||
}
|
||||
|
||||
parse(url) {
|
||||
//if (url.indexOf('timeouts') !== -1 && this.routeRegexp.toString().indexOf('timeouts') !== -1) {
|
||||
//debugger;
|
||||
//}
|
||||
let matches = url.match(this.routeRegexp);
|
||||
if (!matches) return; // eslint-disable-line curly
|
||||
let i = 0;
|
||||
let params = {};
|
||||
while (i < this.paramNames.length) {
|
||||
const paramName = this.paramNames[i++];
|
||||
params[paramName] = matches[i];
|
||||
}
|
||||
return params;
|
||||
}
|
||||
}
|
||||
export const ALL_COMMANDS = _.flatMap(_.values(METHOD_MAP).map(_.values))
|
||||
.filter((m) => Boolean(m.command))
|
||||
.map((m) => m.command);
|
||||
|
||||
/**
|
||||
*
|
||||
* @param {string} endpoint
|
||||
* @param {import('@appium/types').HTTPMethod} method
|
||||
* @param {string} [basePath]
|
||||
* @param {string} [basePath=DEFAULT_BASE_PATH]
|
||||
* @returns {string|undefined}
|
||||
*/
|
||||
function routeToCommandName(endpoint, method, basePath = DEFAULT_BASE_PATH) {
|
||||
let dstRoute = null;
|
||||
|
||||
// remove any query string
|
||||
// TODO: would this be better handled as a `URL` object?
|
||||
if (endpoint.includes('?')) {
|
||||
endpoint = endpoint.slice(0, endpoint.indexOf('?'));
|
||||
export function routeToCommandName(endpoint, method, basePath = DEFAULT_BASE_PATH) {
|
||||
let normalizedEndpoint = basePath
|
||||
? endpoint.replace(new RegExp(`^${_.escapeRegExp(basePath)}`), '')
|
||||
: endpoint;
|
||||
normalizedEndpoint = `${_.startsWith(normalizedEndpoint, '/') ? '' : '/'}${normalizedEndpoint}`;
|
||||
/** @type {string} */
|
||||
let normalizedPathname;
|
||||
try {
|
||||
// we could use any prefix there as we anyway need to only extract the pathname
|
||||
normalizedPathname = new URL(`https://appium.io${normalizedEndpoint}`).pathname;
|
||||
} catch (err) {
|
||||
throw new Error(`'${endpoint}' cannot be translated to a command name: ${err.message}`);
|
||||
}
|
||||
|
||||
const actualEndpoint =
|
||||
endpoint === '/' ? '' : _.startsWith(endpoint, '/') ? endpoint : `/${endpoint}`;
|
||||
|
||||
for (let currentRoute of _.keys(METHOD_MAP)) {
|
||||
const route = new Route(`${basePath}${currentRoute}`);
|
||||
// we don't care about the actual session id for matching
|
||||
if (
|
||||
route.parse(`${basePath}/session/ignored-session-id${actualEndpoint}`) ||
|
||||
route.parse(`${basePath}${actualEndpoint}`) ||
|
||||
route.parse(actualEndpoint)
|
||||
) {
|
||||
dstRoute = currentRoute;
|
||||
break;
|
||||
}
|
||||
/** @type {string[]} */
|
||||
const possiblePathnames = [];
|
||||
if (!normalizedPathname.startsWith('/session/')) {
|
||||
possiblePathnames.push(`/session/any-session-id${normalizedPathname}`);
|
||||
}
|
||||
if (!dstRoute) return; // eslint-disable-line curly
|
||||
|
||||
const methods = METHOD_MAP[dstRoute];
|
||||
method = /** @type {Uppercase<typeof method>} */ (_.toUpper(method));
|
||||
if (method in methods) {
|
||||
const dstMethod = _.get(methods, method);
|
||||
if (dstMethod.command) {
|
||||
return dstMethod.command;
|
||||
possiblePathnames.push(normalizedPathname);
|
||||
const normalizedMethod = _.toUpper(method);
|
||||
for (const [routePath, routeSpec] of _.toPairs(METHOD_MAP)) {
|
||||
const routeRegexp = pathToRegexp(routePath);
|
||||
if (possiblePathnames.some((pp) => routeRegexp.test(pp))) {
|
||||
const commandName = routeSpec?.[normalizedMethod]?.command;
|
||||
if (commandName) {
|
||||
return commandName;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// driver commands that do not require a session to already exist
|
||||
const NO_SESSION_ID_COMMANDS = ['createSession', 'getStatus', 'getSessions'];
|
||||
|
||||
export {METHOD_MAP, ALL_COMMANDS, NO_SESSION_ID_COMMANDS, routeToCommandName};
|
||||
export const NO_SESSION_ID_COMMANDS = ['createSession', 'getStatus', 'getSessions'];
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@appium/base-driver",
|
||||
"version": "9.10.1",
|
||||
"version": "9.11.2",
|
||||
"description": "Base driver class for Appium drivers",
|
||||
"keywords": [
|
||||
"automation",
|
||||
@@ -44,13 +44,13 @@
|
||||
"test:types": "tsd"
|
||||
},
|
||||
"dependencies": {
|
||||
"@appium/support": "^5.0.1",
|
||||
"@appium/types": "^0.20.1",
|
||||
"@appium/support": "^5.1.2",
|
||||
"@appium/types": "^0.21.1",
|
||||
"@colors/colors": "1.6.0",
|
||||
"@types/async-lock": "1.4.2",
|
||||
"@types/bluebird": "3.5.42",
|
||||
"@types/express": "4.17.21",
|
||||
"@types/lodash": "4.17.5",
|
||||
"@types/lodash": "4.17.6",
|
||||
"@types/method-override": "0.0.35",
|
||||
"@types/serve-favicon": "2.5.7",
|
||||
"async-lock": "1.4.1",
|
||||
@@ -61,13 +61,13 @@
|
||||
"express": "4.19.2",
|
||||
"http-status-codes": "2.3.0",
|
||||
"lodash": "4.17.21",
|
||||
"lru-cache": "10.2.2",
|
||||
"lru-cache": "10.3.0",
|
||||
"method-override": "3.0.0",
|
||||
"morgan": "1.10.0",
|
||||
"path-to-regexp": "6.2.2",
|
||||
"path-to-regexp": "7.0.0",
|
||||
"serve-favicon": "2.5.0",
|
||||
"source-map-support": "0.5.21",
|
||||
"type-fest": "4.20.0",
|
||||
"type-fest": "4.21.0",
|
||||
"validate.js": "0.13.1"
|
||||
},
|
||||
"optionalDependencies": {
|
||||
|
||||
@@ -15,6 +15,13 @@ function getFixture(file) {
|
||||
}
|
||||
|
||||
describe('app download and configuration', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaisAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaisAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe('configureApp', function () {
|
||||
it('should get the path for a local .app', async function () {
|
||||
let newAppPath = await configureApp(getFixture('FakeIOSApp.app'), '.app');
|
||||
|
||||
@@ -13,6 +13,11 @@ describe('Websockets (e2e)', function () {
|
||||
const WS_DATA = 'Hello';
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaisAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaisAsPromised.default);
|
||||
chai.should();
|
||||
|
||||
driver = new FakeDriver();
|
||||
driver.sessionId = SESSION_ID;
|
||||
port = await getTestPort();
|
||||
|
||||
@@ -21,6 +21,11 @@ describe('server', function () {
|
||||
let port;
|
||||
let sandbox;
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaisAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaisAsPromised.default);
|
||||
chai.should();
|
||||
|
||||
port = await getTestPort(true);
|
||||
|
||||
function configureRoutes(app) {
|
||||
@@ -119,6 +124,11 @@ describe('tls server', function () {
|
||||
});
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaisAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaisAsPromised.default);
|
||||
chai.should();
|
||||
|
||||
try {
|
||||
await generateCertificate(certPath, keyPath);
|
||||
} catch (e) {
|
||||
@@ -167,6 +177,11 @@ describe('server plugins', function () {
|
||||
let port;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaisAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaisAsPromised.default);
|
||||
chai.should();
|
||||
|
||||
port = await getTestPort(true);
|
||||
});
|
||||
|
||||
|
||||
@@ -4,7 +4,14 @@ import {FakeDriver} from '../protocol/fake-driver';
|
||||
describe('proxy', function () {
|
||||
const jwproxy = new JWProxy();
|
||||
let baseServer;
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaisAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaisAsPromised.default);
|
||||
should = chai.should();
|
||||
|
||||
baseServer = await server({
|
||||
routeConfiguringFunction: routeConfiguringFunction(new FakeDriver()),
|
||||
port: 4444,
|
||||
|
||||
@@ -12,6 +12,7 @@ let baseUrl;
|
||||
|
||||
describe('Protocol', function () {
|
||||
let sandbox;
|
||||
let should;
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
@@ -22,6 +23,11 @@ describe('Protocol', function () {
|
||||
});
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaisAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaisAsPromised.default);
|
||||
should = chai.should();
|
||||
|
||||
port = await getTestPort();
|
||||
baseUrl = `http://${TEST_HOST}:${port}`;
|
||||
});
|
||||
|
||||
@@ -14,6 +14,15 @@ import {BASE_DESIRED_CAP_CONSTRAINTS} from '@appium/types';
|
||||
import {isW3cCaps} from '../../../lib/helpers/capabilities';
|
||||
|
||||
describe('caps', function () {
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
});
|
||||
|
||||
// Tests based on: https://www.w3.org/TR/webdriver/#dfn-validate-caps
|
||||
describe('#validateCaps', function () {
|
||||
it('returns invalid argument error if "capability" is not a JSON object (1)', function () {
|
||||
|
||||
@@ -11,12 +11,24 @@ describe('Desired Capabilities', function () {
|
||||
/** @type {BaseDriver} */
|
||||
let d;
|
||||
let sandbox;
|
||||
/** @type {import('sinon').SinonSpy} */
|
||||
let logWarnSpy;
|
||||
/** @type {import('sinon').SinonStub} */
|
||||
let deprecatedStub;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
|
||||
beforeEach(function () {
|
||||
d = new BaseDriver();
|
||||
sandbox = createSandbox();
|
||||
sandbox.spy(d.log, 'warn');
|
||||
sandbox.stub(validator.validators, 'deprecated');
|
||||
logWarnSpy = sandbox.spy(d.log, 'warn');
|
||||
deprecatedStub = sandbox.stub(validator.validators, 'deprecated');
|
||||
});
|
||||
|
||||
afterEach(function () {
|
||||
@@ -118,7 +130,7 @@ describe('Desired Capabilities', function () {
|
||||
firstMatch: [{}],
|
||||
});
|
||||
|
||||
d.log.warn.should.have.been.called;
|
||||
logWarnSpy.called.should.be.true;
|
||||
});
|
||||
|
||||
it('should be sensitive to the case of caps', async function () {
|
||||
@@ -143,7 +155,7 @@ describe('Desired Capabilities', function () {
|
||||
},
|
||||
firstMatch: [{}],
|
||||
});
|
||||
d.log.warn.should.have.been.called;
|
||||
logWarnSpy.called.should.be.true;
|
||||
|
||||
let sessions = await d.getSessions();
|
||||
sessions[0].capabilities.noReset.should.eql(false);
|
||||
@@ -158,7 +170,7 @@ describe('Desired Capabilities', function () {
|
||||
},
|
||||
firstMatch: [{}],
|
||||
});
|
||||
d.log.warn.should.have.been.called;
|
||||
logWarnSpy.called.should.be.true;
|
||||
|
||||
let sessions = await d.getSessions();
|
||||
sessions[0].capabilities.noReset.should.eql(true);
|
||||
@@ -172,7 +184,7 @@ describe('Desired Capabilities', function () {
|
||||
},
|
||||
firstMatch: [{}],
|
||||
});
|
||||
d.log.warn.should.not.have.been.called;
|
||||
logWarnSpy.called.should.be.false;
|
||||
|
||||
let sessions = await d.getSessions();
|
||||
sessions[0].capabilities.language.should.eql('true');
|
||||
@@ -189,7 +201,7 @@ describe('Desired Capabilities', function () {
|
||||
},
|
||||
firstMatch: [{}],
|
||||
});
|
||||
d.log.warn.should.have.been.called;
|
||||
logWarnSpy.called.should.be.true;
|
||||
|
||||
let sessions = await d.getSessions();
|
||||
sessions[0].capabilities.newCommandTimeout.should.eql(1);
|
||||
@@ -204,7 +216,7 @@ describe('Desired Capabilities', function () {
|
||||
},
|
||||
firstMatch: [{}],
|
||||
});
|
||||
d.log.warn.should.have.been.called;
|
||||
logWarnSpy.called.should.be.true;
|
||||
|
||||
let sessions = await d.getSessions();
|
||||
sessions[0].capabilities.newCommandTimeout.should.eql(1.1);
|
||||
@@ -218,7 +230,7 @@ describe('Desired Capabilities', function () {
|
||||
},
|
||||
firstMatch: [{}],
|
||||
});
|
||||
d.log.warn.should.not.have.been.called;
|
||||
logWarnSpy.called.should.be.false;
|
||||
|
||||
let sessions = await d.getSessions();
|
||||
sessions[0].capabilities.language.should.eql('1');
|
||||
@@ -254,7 +266,7 @@ describe('Desired Capabilities', function () {
|
||||
firstMatch: [{}],
|
||||
});
|
||||
|
||||
validator.validators.deprecated.should.have.been.calledWith(5, true, 'lynx-version');
|
||||
(deprecatedStub.calledWith(5, true, 'lynx-version')).should.be.true;
|
||||
});
|
||||
|
||||
it('should not warn if deprecated=false', async function () {
|
||||
@@ -274,7 +286,7 @@ describe('Desired Capabilities', function () {
|
||||
firstMatch: [{}],
|
||||
});
|
||||
|
||||
d.log.warn.should.not.have.been.called;
|
||||
logWarnSpy.called.should.be.false;
|
||||
});
|
||||
|
||||
it('should not validate against null/undefined caps', async function () {
|
||||
|
||||
@@ -2,6 +2,13 @@ import _ from 'lodash';
|
||||
import {BaseDriver} from '../../../../lib';
|
||||
|
||||
describe('logging custom events', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
it('should allow logging of events', async function () {
|
||||
const d = new BaseDriver();
|
||||
d._eventHistory.should.eql({commands: []});
|
||||
@@ -19,6 +26,13 @@ describe('logging custom events', function () {
|
||||
});
|
||||
|
||||
describe('#getLogEvents', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
it('should allow to get all events', async function () {
|
||||
const d = new BaseDriver();
|
||||
d._eventHistory.should.eql({commands: []});
|
||||
|
||||
@@ -3,8 +3,6 @@ import {createSandbox} from 'sinon';
|
||||
import _ from 'lodash';
|
||||
import BaseDriver from '../../../../lib';
|
||||
|
||||
const expect = chai.expect;
|
||||
|
||||
const FIRST_LOGS = ['first', 'logs'];
|
||||
const SECOND_LOGS = ['second', 'logs'];
|
||||
const SUPPORTED_LOG_TYPES = {
|
||||
@@ -20,8 +18,14 @@ const SUPPORTED_LOG_TYPES = {
|
||||
|
||||
describe('log commands -', function () {
|
||||
let sandbox;
|
||||
|
||||
let driver;
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
|
||||
@@ -3,10 +3,17 @@ import sinon from 'sinon';
|
||||
import {DeviceSettings, MAX_SETTINGS_SIZE} from '../../../lib/basedriver/device-settings';
|
||||
import {InvalidArgumentError} from '../../../lib/protocol/errors';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
describe('DeviceSettings', function () {
|
||||
let sandbox;
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = sinon.createSandbox();
|
||||
@@ -91,7 +98,7 @@ describe('DeviceSettings', function () {
|
||||
it('should not call the `_onSettingsUpdate` listener', async function () {
|
||||
const deviceSettings = new DeviceSettings({stuff: 'things'}, onSettingsUpdate);
|
||||
await deviceSettings.update({stuff: 'things'});
|
||||
expect(onSettingsUpdate).not.to.have.been.called;
|
||||
onSettingsUpdate.called.should.be.false;
|
||||
});
|
||||
});
|
||||
|
||||
@@ -99,11 +106,11 @@ describe('DeviceSettings', function () {
|
||||
it('should call the `_onSettingsUpdate` listener', async function () {
|
||||
const deviceSettings = new DeviceSettings({}, onSettingsUpdate);
|
||||
await deviceSettings.update({stuff: 'things'});
|
||||
expect(onSettingsUpdate).to.have.been.calledOnceWithExactly(
|
||||
onSettingsUpdate.calledOnceWithExactly(
|
||||
'stuff',
|
||||
'things',
|
||||
undefined
|
||||
);
|
||||
).should.be.true;
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -1,14 +1,20 @@
|
||||
import BaseDriver from '../../../lib';
|
||||
import {driverUnitTestSuite} from '@appium/driver-test-support';
|
||||
|
||||
const {expect} = chai;
|
||||
|
||||
driverUnitTestSuite(BaseDriver, {
|
||||
platformName: 'iOS',
|
||||
'appium:deviceName': 'Delorean',
|
||||
});
|
||||
|
||||
describe('BaseDriver', function () {
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
describe('constructor', function () {
|
||||
it('should initialize "opts"', function () {
|
||||
const driver = new BaseDriver();
|
||||
|
||||
@@ -8,6 +8,15 @@ import {
|
||||
import sinon from 'sinon';
|
||||
|
||||
describe('helpers', function () {
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
});
|
||||
|
||||
describe('#isPackageOrBundle', function () {
|
||||
it('should accept packages and bundles', function () {
|
||||
isPackageOrBundle('io.appium.testapp').should.be.true;
|
||||
|
||||
@@ -4,6 +4,13 @@ import BaseDriver from '../../../lib';
|
||||
import {createSandbox} from 'sinon';
|
||||
|
||||
describe('timeout', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
let driver = new BaseDriver();
|
||||
let implicitWaitSpy;
|
||||
let sandbox;
|
||||
|
||||
@@ -0,0 +1,24 @@
|
||||
import {pathToRegexp} from 'path-to-regexp';
|
||||
|
||||
describe('middleware', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe('pathToRegexp', function () {
|
||||
it('should match static path pattern', function () {
|
||||
const pathname = '/ws/session/1234/appium/device/syslog';
|
||||
const url = 'ws://127.0.0.1:8000/ws/session/1234/appium/device/syslog';
|
||||
const currentPathname = new URL(url).pathname;
|
||||
pathToRegexp(pathname).test(currentPathname).should.be.true;
|
||||
});
|
||||
|
||||
it('should match dynamic path pattern', function () {
|
||||
const pathname = '/ws/session/:sessionId/appium/device/syslog';
|
||||
const url = 'ws://127.0.0.1:8000/ws/session/1234/appium/device/syslog';
|
||||
const currentPathname = new URL(url).pathname;
|
||||
pathToRegexp(pathname).test(currentPathname).should.be.true;
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -23,8 +23,15 @@ function fakeDriver() {
|
||||
|
||||
describe('server configuration', function () {
|
||||
let port;
|
||||
|
||||
let sandbox;
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
});
|
||||
|
||||
function fakeApp() {
|
||||
const app = {
|
||||
|
||||
@@ -6,6 +6,11 @@ import {createSandbox} from 'sinon';
|
||||
describe('welcome', function () {
|
||||
let sandbox;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
});
|
||||
|
||||
@@ -7,6 +7,13 @@ import ProtocolConverter, {
|
||||
const {MJSONWP, W3C} = PROTOCOLS;
|
||||
|
||||
describe('Protocol Converter', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe('getTimeoutRequestObjects', function () {
|
||||
let converter;
|
||||
before(function () {
|
||||
|
||||
@@ -25,6 +25,14 @@ function buildReqRes(url, method, body) {
|
||||
|
||||
describe('proxy', function () {
|
||||
let port;
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
});
|
||||
|
||||
function mockProxy(opts = {}) {
|
||||
// sets default server/port
|
||||
|
||||
@@ -21,6 +21,11 @@ describe('JWProxy', function () {
|
||||
}
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
|
||||
port = await getTestPort();
|
||||
createTestURL = createAppiumURL(TEST_HOST, port);
|
||||
testStatusURL = createTestURL('', 'status');
|
||||
|
||||
@@ -2,6 +2,15 @@ import _ from 'lodash';
|
||||
import {statusCodes, getSummaryByCode} from '../../../lib';
|
||||
|
||||
describe('jsonwp-status', function () {
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
should = chai.should();
|
||||
});
|
||||
|
||||
describe('codes', function () {
|
||||
it('should export code numbers and summaries', function () {
|
||||
for (let obj of _.values(statusCodes)) {
|
||||
|
||||
@@ -227,6 +227,11 @@ let errorsList = [
|
||||
];
|
||||
|
||||
describe('errors', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
for (let error of errorsList) {
|
||||
it(error.errorName + ' should have a JSONWP code or W3C code and message', function () {
|
||||
if (error.errorCode) {
|
||||
@@ -247,6 +252,11 @@ describe('errors', function () {
|
||||
});
|
||||
});
|
||||
describe('errorFromMJSONWPStatusCode', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
for (let error of errorsList) {
|
||||
if (error.errorName !== 'NotYetImplementedError') {
|
||||
it(error.errorCode + ' should return correct error', function () {
|
||||
@@ -285,6 +295,11 @@ describe('errorFromMJSONWPStatusCode', function () {
|
||||
});
|
||||
});
|
||||
describe('errorFromW3CJsonCode', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
for (let error of errorsList) {
|
||||
if (error.errorName !== 'NotYetImplementedError') {
|
||||
it(error.errorName + ' should return correct error', function () {
|
||||
@@ -307,6 +322,11 @@ describe('errorFromW3CJsonCode', function () {
|
||||
});
|
||||
});
|
||||
describe('w3c Status Codes', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
it('should match the correct error codes', function () {
|
||||
let non400Errors = [
|
||||
['NoSuchDriverError', 404],
|
||||
@@ -341,6 +361,11 @@ describe('w3c Status Codes', function () {
|
||||
});
|
||||
});
|
||||
describe('.getResponseForW3CError', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
it('should return an error, message and stacktrace for just a generic exception', function () {
|
||||
try {
|
||||
throw new Error('Some random error');
|
||||
@@ -388,6 +413,11 @@ describe('.getResponseForW3CError', function () {
|
||||
});
|
||||
});
|
||||
describe('.getActualError', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe('MJSONWP', function () {
|
||||
it('should map a status code 7 no such element error as a NoSuchElementError', function () {
|
||||
const actualError = new errors.ProxyRequestError('Error message does not matter', {
|
||||
|
||||
@@ -7,6 +7,14 @@ import crypto from 'crypto';
|
||||
describe('Protocol', function () {
|
||||
// TODO test against an explicit protocol rather than a hash of a previous
|
||||
// protocol
|
||||
let chai;
|
||||
|
||||
before(async function () {
|
||||
chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe('ensure protocol consistency', function () {
|
||||
it('should not change protocol between patch versions', function () {
|
||||
@@ -55,6 +63,16 @@ describe('Protocol', function () {
|
||||
cmdName.should.equal('getStatus');
|
||||
});
|
||||
|
||||
it('should properly lookup correct command name for endpoint with query params', function () {
|
||||
const cmdName = routeToCommandName('/status?foo=1&bar=2', 'GET');
|
||||
cmdName.should.equal('getStatus');
|
||||
});
|
||||
|
||||
it('should properly lookup correct command name with custom base path', function () {
|
||||
const cmdName = routeToCommandName('/wd/hub/status?foo=1&bar=2', 'GET', '/wd/hub');
|
||||
cmdName.should.equal('getStatus');
|
||||
});
|
||||
|
||||
it('should properly lookup correct command name for endpoint without leading slash', function () {
|
||||
const cmdName = routeToCommandName('status', 'GET');
|
||||
cmdName.should.equal('getStatus');
|
||||
|
||||
@@ -3,6 +3,11 @@
|
||||
import {validators} from '../../../lib/protocol/validators';
|
||||
|
||||
describe('Protocol', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe('direct to driver', function () {
|
||||
describe('setUrl', function () {
|
||||
it('should fail when no url passed', function () {
|
||||
|
||||
@@ -3,6 +3,46 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
## [2.2.42](https://github.com/appium/appium/compare/@appium/base-plugin@2.2.41...@appium/base-plugin@2.2.42) (2024-07-10)
|
||||
|
||||
**Note:** Version bump only for package @appium/base-plugin
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [2.2.41](https://github.com/appium/appium/compare/@appium/base-plugin@2.2.40...@appium/base-plugin@2.2.41) (2024-06-28)
|
||||
|
||||
**Note:** Version bump only for package @appium/base-plugin
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [2.2.40](https://github.com/appium/appium/compare/@appium/base-plugin@2.2.39...@appium/base-plugin@2.2.40) (2024-06-27)
|
||||
|
||||
**Note:** Version bump only for package @appium/base-plugin
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [2.2.39](https://github.com/appium/appium/compare/@appium/base-plugin@2.2.38...@appium/base-plugin@2.2.39) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/base-plugin
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [2.2.38](https://github.com/appium/appium/compare/@appium/base-plugin@2.2.37...@appium/base-plugin@2.2.38) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/base-plugin
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [2.2.37](https://github.com/appium/appium/compare/@appium/base-plugin@2.2.36...@appium/base-plugin@2.2.37) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/base-plugin
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@appium/base-plugin",
|
||||
"version": "2.2.37",
|
||||
"version": "2.2.42",
|
||||
"description": "The base plugin used to create Appium 2.0 plugins",
|
||||
"keywords": [
|
||||
"automation",
|
||||
@@ -40,8 +40,8 @@
|
||||
"test:unit": "mocha \"./test/unit/**/*.spec.js\""
|
||||
},
|
||||
"dependencies": {
|
||||
"@appium/base-driver": "^9.10.1",
|
||||
"@appium/support": "^5.0.1"
|
||||
"@appium/base-driver": "^9.11.2",
|
||||
"@appium/support": "^5.1.2"
|
||||
},
|
||||
"engines": {
|
||||
"node": "^14.17.0 || ^16.13.0 || >=18.0.0",
|
||||
|
||||
@@ -1,6 +1,13 @@
|
||||
import BasePlugin from '../../lib/plugin';
|
||||
|
||||
describe('base plugin', function () {
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
should = chai.should();
|
||||
});
|
||||
|
||||
it('should exist', function () {
|
||||
should.exist(BasePlugin);
|
||||
});
|
||||
|
||||
@@ -3,6 +3,55 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
## [2.1.9](https://github.com/appium/appium/compare/@appium/doctor@2.1.8...@appium/doctor@2.1.9) (2024-07-10)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **doctor:** update dependency appium-adb to v12.4.6 ([5281f5a](https://github.com/appium/appium/commit/5281f5a01a63e12454093cb296286da02adc77ee))
|
||||
* **doctor:** update dependency appium-adb to v12.4.8 ([177dff4](https://github.com/appium/appium/commit/177dff4f0ed84880ce9df55f94ff62b922a80ae5))
|
||||
* **support:** update dependency teen_process to v2.1.10 ([86f843b](https://github.com/appium/appium/commit/86f843b9e1fc56576d7a08bf95838a58971e98b3))
|
||||
* **support:** update dependency teen_process to v2.1.7 ([5226fa8](https://github.com/appium/appium/commit/5226fa897b90e9fec9be3e79a7d48fc7b4e0016d))
|
||||
* **support:** update dependency teen_process to v2.2.0 ([06607da](https://github.com/appium/appium/commit/06607da92e93d015747fd6d6d5bdabe1b3ac58d2))
|
||||
|
||||
|
||||
|
||||
## [2.1.8](https://github.com/appium/appium/compare/@appium/doctor@2.1.7...@appium/doctor@2.1.8) (2024-06-28)
|
||||
|
||||
**Note:** Version bump only for package @appium/doctor
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [2.1.7](https://github.com/appium/appium/compare/@appium/doctor@2.1.6...@appium/doctor@2.1.7) (2024-06-27)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **doctor:** update dependency appium-adb to v12.4.3 ([4345a40](https://github.com/appium/appium/commit/4345a40a15d2473bb13524593ab66ff8ae3d8a7e))
|
||||
* **doctor:** update dependency appium-adb to v12.4.4 ([15234bc](https://github.com/appium/appium/commit/15234bc05502157ebf847856d38e35da4d542df7))
|
||||
* **support:** update dependency teen_process to v2.1.5 ([bc388db](https://github.com/appium/appium/commit/bc388db1116f411f4b241105f5feae30418c9a27))
|
||||
* **support:** update dependency teen_process to v2.1.6 ([5412461](https://github.com/appium/appium/commit/541246184dc7521c825ec1902775e681ea6f0db3))
|
||||
|
||||
|
||||
|
||||
## [2.1.6](https://github.com/appium/appium/compare/@appium/doctor@2.1.5...@appium/doctor@2.1.6) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/doctor
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [2.1.5](https://github.com/appium/appium/compare/@appium/doctor@2.1.4...@appium/doctor@2.1.5) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/doctor
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [2.1.4](https://github.com/appium/appium/compare/@appium/doctor@2.1.3...@appium/doctor@2.1.4) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/doctor
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@appium/doctor",
|
||||
"version": "2.1.4",
|
||||
"version": "2.1.9",
|
||||
"description": "Test environment for fitness to run Appium",
|
||||
"keywords": [
|
||||
"automation",
|
||||
@@ -44,16 +44,16 @@
|
||||
"test:unit": "mocha \"./test/unit/**/*.spec.js\""
|
||||
},
|
||||
"dependencies": {
|
||||
"@appium/support": "^5.0.1",
|
||||
"@appium/support": "^5.1.2",
|
||||
"@colors/colors": "1.6.0",
|
||||
"@types/bluebird": "3.5.42",
|
||||
"@types/teen_process": "2.0.4",
|
||||
"appium-adb": "12.4.2",
|
||||
"appium-adb": "12.4.8",
|
||||
"bluebird": "3.7.2",
|
||||
"inquirer": "9.2.12",
|
||||
"lodash": "4.17.21",
|
||||
"source-map-support": "0.5.21",
|
||||
"teen_process": "2.1.4",
|
||||
"teen_process": "2.2.0",
|
||||
"yargs": "17.7.2"
|
||||
},
|
||||
"engines": {
|
||||
|
||||
@@ -18,6 +18,14 @@ describe('android', function () {
|
||||
const apkAnalyzerFilename = system.isWindows() ? 'apkanalyzer.bat' : 'apkanalyzer';
|
||||
const gstLaunchFilename = system.isWindows() ? 'gst-launch-1.0.exe' : 'gst-launch-1.0';
|
||||
const gstInspectFilename = system.isWindows() ? 'gst-inspect-1.0.exe' : 'gst-inspect-1.0';
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe(
|
||||
'EnvVarAndPathCheck',
|
||||
withMocks({fs}, (mocks) => {
|
||||
|
||||
@@ -8,6 +8,13 @@ import {withMocks, withSandbox, stubLog} from '@appium/test-support';
|
||||
import B from 'bluebird';
|
||||
|
||||
describe('demo', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe(
|
||||
'DirCheck',
|
||||
withMocks({fs}, (mocks) => {
|
||||
|
||||
@@ -7,6 +7,13 @@ import B from 'bluebird';
|
||||
import {removeColors} from './helper';
|
||||
|
||||
describe('dev', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe(
|
||||
'BinaryIsInPathCheck',
|
||||
withMocks({tp, fs}, (mocks) => {
|
||||
|
||||
@@ -4,6 +4,13 @@ import log from '../../lib/logger';
|
||||
import B from 'bluebird';
|
||||
|
||||
describe('doctor', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
it('register', function () {
|
||||
let doctor = new Doctor();
|
||||
doctor.checks.should.have.length(0);
|
||||
|
||||
@@ -1,6 +1,11 @@
|
||||
import newDoctor from '../../lib/factory';
|
||||
|
||||
describe('factory', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
function getTest(config) {
|
||||
return function runTest() {
|
||||
let doctor = newDoctor(config);
|
||||
|
||||
@@ -12,6 +12,13 @@ import B from 'bluebird';
|
||||
import {removeColors} from './helper';
|
||||
|
||||
describe('general', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe(
|
||||
'NodeBinaryCheck',
|
||||
withMocks({NodeDetector}, (mocks) => {
|
||||
|
||||
@@ -1,6 +1,11 @@
|
||||
import {newDoctor, Doctor, DoctorCheck} from '../../lib';
|
||||
|
||||
describe('index', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
it('should work', function () {
|
||||
newDoctor.should.exist;
|
||||
Doctor.should.exist;
|
||||
|
||||
@@ -19,6 +19,13 @@ import {withMocks, withSandbox, stubLog} from '@appium/test-support';
|
||||
import {removeColors} from './helper';
|
||||
|
||||
describe('ios', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
chai.should();
|
||||
});
|
||||
|
||||
describe(
|
||||
'XcodeCheck',
|
||||
withMocks({tp, fs}, (mocks) => {
|
||||
|
||||
@@ -3,11 +3,18 @@ import NodeDetector from '../../lib/node-detector';
|
||||
import B from 'bluebird';
|
||||
import {withSandbox} from '@appium/test-support';
|
||||
|
||||
let expect = chai.expect;
|
||||
|
||||
describe(
|
||||
'NodeDetector',
|
||||
withSandbox({mocks: {fs, system}}, (S) => {
|
||||
let expect;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
expect = chai.expect;
|
||||
});
|
||||
|
||||
|
||||
it('retrieveUsingSystemCall - success - where returns multiple lines ', async function () {
|
||||
S.mocks.fs.expects('which').once().returns(B.resolve('/a/b/node.exe'));
|
||||
S.mocks.fs.expects('exists').once().returns(B.resolve(true));
|
||||
|
||||
@@ -6,6 +6,11 @@ import B from 'bluebird';
|
||||
describe(
|
||||
'prompt',
|
||||
withMocks({utils}, (mocks) => {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
it('fixit - yes', async function () {
|
||||
clear();
|
||||
mocks.utils
|
||||
|
||||
@@ -4,6 +4,11 @@ import path from 'path';
|
||||
import {Doctor} from '../../lib/doctor';
|
||||
|
||||
describe('utils', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
it('fs.readFile', async function () {
|
||||
(await fs.readFile(path.resolve(__dirname, 'fixtures', 'wow.txt'), 'utf8')).should.include(
|
||||
'WOW'
|
||||
|
||||
@@ -3,6 +3,55 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
## [1.0.18](https://github.com/appium/appium/compare/@appium/docutils@1.0.17...@appium/docutils@1.0.18) (2024-07-10)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **docutils:** update dependency typescript to v5.5.3 ([234ad59](https://github.com/appium/appium/commit/234ad597988be2560a63ba346dc5e4afbfb6e20d))
|
||||
* **support:** update dependency teen_process to v2.1.10 ([86f843b](https://github.com/appium/appium/commit/86f843b9e1fc56576d7a08bf95838a58971e98b3))
|
||||
* **support:** update dependency teen_process to v2.1.7 ([5226fa8](https://github.com/appium/appium/commit/5226fa897b90e9fec9be3e79a7d48fc7b4e0016d))
|
||||
* **support:** update dependency teen_process to v2.2.0 ([06607da](https://github.com/appium/appium/commit/06607da92e93d015747fd6d6d5bdabe1b3ac58d2))
|
||||
* **types:** update dependency type-fest to v4.21.0 ([#20335](https://github.com/appium/appium/issues/20335)) ([8894b9a](https://github.com/appium/appium/commit/8894b9adf709646108cc8d6426bbb690550609f2))
|
||||
|
||||
|
||||
|
||||
## [1.0.17](https://github.com/appium/appium/compare/@appium/docutils@1.0.16...@appium/docutils@1.0.17) (2024-06-28)
|
||||
|
||||
**Note:** Version bump only for package @appium/docutils
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [1.0.16](https://github.com/appium/appium/compare/@appium/docutils@1.0.15...@appium/docutils@1.0.16) (2024-06-27)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **docutils:** update dependency typescript to v5.5.2 ([189bce8](https://github.com/appium/appium/commit/189bce88a09c4b3146c48bedf6e8c1dcb50c3a6d))
|
||||
* **support:** update dependency teen_process to v2.1.5 ([bc388db](https://github.com/appium/appium/commit/bc388db1116f411f4b241105f5feae30418c9a27))
|
||||
* **support:** update dependency teen_process to v2.1.6 ([5412461](https://github.com/appium/appium/commit/541246184dc7521c825ec1902775e681ea6f0db3))
|
||||
* **types:** update dependency type-fest to v4.20.1 ([#20255](https://github.com/appium/appium/issues/20255)) ([1984553](https://github.com/appium/appium/commit/19845531f558e2b16dfae807c768e1b9f2cab25d))
|
||||
|
||||
|
||||
|
||||
## [1.0.15](https://github.com/appium/appium/compare/@appium/docutils@1.0.14...@appium/docutils@1.0.15) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/docutils
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [1.0.14](https://github.com/appium/appium/compare/@appium/docutils@1.0.13...@appium/docutils@1.0.14) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/docutils
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [1.0.13](https://github.com/appium/appium/compare/@appium/docutils@1.0.12...@appium/docutils@1.0.13) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/docutils
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@appium/docutils",
|
||||
"version": "1.0.13",
|
||||
"version": "1.0.18",
|
||||
"description": "Documentation generation utilities for Appium and related projects",
|
||||
"keywords": [
|
||||
"automation",
|
||||
@@ -48,7 +48,7 @@
|
||||
"start": "node ./build/lib/cli/index.js"
|
||||
},
|
||||
"dependencies": {
|
||||
"@appium/support": "^5.0.1",
|
||||
"@appium/support": "^5.1.2",
|
||||
"@appium/tsconfig": "^0.3.3",
|
||||
"@sliphua/lilconfig-ts-loader": "3.2.2",
|
||||
"@types/which": "3.0.4",
|
||||
@@ -62,9 +62,9 @@
|
||||
"read-pkg": "5.2.0",
|
||||
"semver": "7.6.2",
|
||||
"source-map-support": "0.5.21",
|
||||
"teen_process": "2.1.4",
|
||||
"type-fest": "4.20.0",
|
||||
"typescript": "5.4.5",
|
||||
"teen_process": "2.2.0",
|
||||
"type-fest": "4.21.0",
|
||||
"typescript": "5.5.3",
|
||||
"yaml": "2.4.5",
|
||||
"yargs": "17.7.2",
|
||||
"yargs-parser": "21.1.1"
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
mkdocs==1.6.0
|
||||
mkdocs-git-revision-date-localized-plugin==1.2.6
|
||||
mkdocs-material==9.5.26
|
||||
mkdocs-material==9.5.28
|
||||
mkdocs-redirects==1.2.1
|
||||
mike==2.1.1
|
||||
mike==2.1.2
|
||||
|
||||
@@ -2,6 +2,11 @@ import {argify} from '../../lib/util';
|
||||
import _ from 'lodash';
|
||||
|
||||
describe('argify', function () {
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
chai.should();
|
||||
});
|
||||
|
||||
it('should create args from params', function () {
|
||||
// deploy example
|
||||
const version = '2.0';
|
||||
|
||||
@@ -3,6 +3,49 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
||||
|
||||
## [0.6.6](https://github.com/appium/appium/compare/@appium/driver-test-support@0.6.5...@appium/driver-test-support@0.6.6) (2024-07-10)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **types:** update dependency type-fest to v4.21.0 ([#20335](https://github.com/appium/appium/issues/20335)) ([8894b9a](https://github.com/appium/appium/commit/8894b9adf709646108cc8d6426bbb690550609f2))
|
||||
|
||||
|
||||
|
||||
## [0.6.5](https://github.com/appium/appium/compare/@appium/driver-test-support@0.6.4...@appium/driver-test-support@0.6.5) (2024-06-28)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **driver-test-support:** update dependency @types/lodash to v4.17.6 ([82e40c1](https://github.com/appium/appium/commit/82e40c1400e23f341c45d788982ccc5905827d7c))
|
||||
|
||||
|
||||
|
||||
## [0.6.4](https://github.com/appium/appium/compare/@appium/driver-test-support@0.6.3...@appium/driver-test-support@0.6.4) (2024-06-27)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **types:** update dependency type-fest to v4.20.1 ([#20255](https://github.com/appium/appium/issues/20255)) ([1984553](https://github.com/appium/appium/commit/19845531f558e2b16dfae807c768e1b9f2cab25d))
|
||||
|
||||
|
||||
|
||||
## [0.6.3](https://github.com/appium/appium/compare/@appium/driver-test-support@0.6.2...@appium/driver-test-support@0.6.3) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/driver-test-support
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [0.6.2](https://github.com/appium/appium/compare/@appium/driver-test-support@0.6.1...@appium/driver-test-support@0.6.2) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/driver-test-support
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
## [0.6.1](https://github.com/appium/appium/compare/@appium/driver-test-support@0.6.0...@appium/driver-test-support@0.6.1) (2024-06-11)
|
||||
|
||||
**Note:** Version bump only for package @appium/driver-test-support
|
||||
|
||||
@@ -3,13 +3,9 @@ import {server, routeConfiguringFunction, DeviceSettings} from 'appium/driver';
|
||||
import axios from 'axios';
|
||||
import B from 'bluebird';
|
||||
import {TEST_HOST, getTestPort, createAppiumURL} from './helpers';
|
||||
import chai from 'chai';
|
||||
import sinon from 'sinon';
|
||||
import {Agent} from 'node:http';
|
||||
|
||||
const should = chai.should();
|
||||
const {expect} = chai;
|
||||
|
||||
/**
|
||||
* Creates some helper functions for E2E tests to manage sessions.
|
||||
* @template [CommandData=unknown]
|
||||
@@ -129,7 +125,16 @@ export function driverE2ETestSuite(DriverClass, defaultCaps = {}) {
|
||||
let getCommand;
|
||||
/** @type {SessionHelpers['postCommand']} */
|
||||
let postCommand;
|
||||
let expect;
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
expect = chai.expect;
|
||||
should = chai.should();
|
||||
|
||||
port = port ?? (await getTestPort());
|
||||
defaultCaps = {...defaultCaps};
|
||||
d = new DriverClass({port, address});
|
||||
@@ -143,9 +148,8 @@ export function driverE2ETestSuite(DriverClass, defaultCaps = {}) {
|
||||
({startSession, getSession, endSession, newSessionURL, getCommand, postCommand} =
|
||||
createSessionHelpers(port, address));
|
||||
});
|
||||
|
||||
after(async function () {
|
||||
await baseServer.close();
|
||||
await baseServer?.close();
|
||||
});
|
||||
|
||||
describe('session handling', function () {
|
||||
|
||||
@@ -2,11 +2,6 @@ import _ from 'lodash';
|
||||
import B from 'bluebird';
|
||||
import {createSandbox} from 'sinon';
|
||||
|
||||
import chai from 'chai';
|
||||
|
||||
const should = chai.should();
|
||||
const {expect} = chai;
|
||||
|
||||
// wrap these tests in a function so we can export the tests and re-use them
|
||||
// for actual driver implementations
|
||||
|
||||
@@ -31,6 +26,16 @@ export function driverUnitTestSuite(
|
||||
let w3cCaps;
|
||||
/** @type {import('sinon').SinonSandbox} */
|
||||
let sandbox;
|
||||
let expect;
|
||||
let should;
|
||||
|
||||
before(async function () {
|
||||
const chai = await import('chai');
|
||||
const chaiAsPromised = await import('chai-as-promised');
|
||||
chai.use(chaiAsPromised.default);
|
||||
expect = chai.expect;
|
||||
should = chai.should();
|
||||
});
|
||||
|
||||
beforeEach(function () {
|
||||
sandbox = createSandbox();
|
||||
@@ -45,8 +50,8 @@ export function driverUnitTestSuite(
|
||||
};
|
||||
});
|
||||
afterEach(async function () {
|
||||
sandbox.restore();
|
||||
await d.deleteSession();
|
||||
sandbox?.restore();
|
||||
await d?.deleteSession();
|
||||
});
|
||||
|
||||
describe('static property', function () {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@appium/driver-test-support",
|
||||
"version": "0.6.1",
|
||||
"version": "0.6.6",
|
||||
"description": "Test utilities for Appium drivers",
|
||||
"keywords": [
|
||||
"automation",
|
||||
@@ -41,18 +41,19 @@
|
||||
},
|
||||
"types": "./build/lib/index.d.ts",
|
||||
"dependencies": {
|
||||
"@appium/types": "^0.20.1",
|
||||
"@types/lodash": "4.17.5",
|
||||
"@appium/types": "^0.21.1",
|
||||
"@types/lodash": "4.17.6",
|
||||
"@types/stoppable": "1.1.3",
|
||||
"axios": "1.7.2",
|
||||
"bluebird": "3.7.2",
|
||||
"chai": "4.4.1",
|
||||
"chai": "5.1.1",
|
||||
"chai-as-promised": "8.0.0",
|
||||
"get-port": "5.1.1",
|
||||
"lodash": "4.17.21",
|
||||
"sinon": "18.0.0",
|
||||
"source-map-support": "0.5.21",
|
||||
"stoppable": "1.1.0",
|
||||
"type-fest": "4.20.0"
|
||||
"type-fest": "4.21.0"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"appium": "^2.0.0-beta.43",
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user