appium 2.0.0-beta.25 → 2.0.0-beta.28
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/build/lib/appium.d.ts +215 -0
- package/build/lib/appium.d.ts.map +1 -0
- package/build/lib/appium.js +94 -101
- package/build/lib/cli/args.d.ts +20 -0
- package/build/lib/cli/args.d.ts.map +1 -0
- package/build/lib/cli/args.js +19 -39
- package/build/lib/cli/driver-command.d.ts +36 -0
- package/build/lib/cli/driver-command.d.ts.map +1 -0
- package/build/lib/cli/driver-command.js +10 -13
- package/build/lib/cli/extension-command.d.ts +345 -0
- package/build/lib/cli/extension-command.d.ts.map +1 -0
- package/build/lib/cli/extension-command.js +117 -94
- package/build/lib/cli/extension.d.ts +14 -0
- package/build/lib/cli/extension.d.ts.map +1 -0
- package/build/lib/cli/extension.js +14 -22
- package/build/lib/cli/parser.d.ts +79 -0
- package/build/lib/cli/parser.d.ts.map +1 -0
- package/build/lib/cli/parser.js +9 -19
- package/build/lib/cli/plugin-command.d.ts +39 -0
- package/build/lib/cli/plugin-command.d.ts.map +1 -0
- package/build/lib/cli/plugin-command.js +9 -14
- package/build/lib/cli/utils.d.ts +29 -0
- package/build/lib/cli/utils.d.ts.map +1 -0
- package/build/lib/cli/utils.js +2 -4
- package/build/lib/config-file.d.ts +100 -0
- package/build/lib/config-file.d.ts.map +1 -0
- package/build/lib/config-file.js +2 -4
- package/build/lib/config.d.ts +40 -0
- package/build/lib/config.d.ts.map +1 -0
- package/build/lib/config.js +8 -7
- package/build/lib/constants.d.ts +48 -0
- package/build/lib/constants.d.ts.map +1 -0
- package/build/lib/constants.js +60 -0
- package/build/lib/extension/driver-config.d.ts +84 -0
- package/build/lib/extension/driver-config.d.ts.map +1 -0
- package/build/lib/extension/driver-config.js +190 -0
- package/build/lib/extension/extension-config.d.ts +170 -0
- package/build/lib/extension/extension-config.d.ts.map +1 -0
- package/build/lib/extension/extension-config.js +297 -0
- package/build/lib/extension/index.d.ts +39 -0
- package/build/lib/extension/index.d.ts.map +1 -0
- package/build/lib/extension/index.js +77 -0
- package/build/lib/extension/manifest.d.ts +174 -0
- package/build/lib/extension/manifest.d.ts.map +1 -0
- package/build/lib/extension/manifest.js +246 -0
- package/build/lib/extension/package-changed.d.ts +11 -0
- package/build/lib/extension/package-changed.d.ts.map +1 -0
- package/build/lib/extension/package-changed.js +68 -0
- package/build/lib/extension/plugin-config.d.ts +62 -0
- package/build/lib/extension/plugin-config.d.ts.map +1 -0
- package/build/lib/extension/plugin-config.js +87 -0
- package/build/lib/grid-register.d.ts +10 -0
- package/build/lib/grid-register.d.ts.map +1 -0
- package/build/lib/grid-register.js +2 -4
- package/build/lib/logger.d.ts +3 -0
- package/build/lib/logger.d.ts.map +1 -0
- package/build/lib/logger.js +2 -4
- package/build/lib/logsink.d.ts +4 -0
- package/build/lib/logsink.d.ts.map +1 -0
- package/build/lib/logsink.js +2 -4
- package/build/lib/main.d.ts +51 -0
- package/build/lib/main.d.ts.map +1 -0
- package/build/lib/main.js +40 -68
- package/build/lib/schema/arg-spec.d.ts +143 -0
- package/build/lib/schema/arg-spec.d.ts.map +1 -0
- package/build/lib/schema/arg-spec.js +11 -14
- package/build/lib/schema/cli-args.d.ts +19 -0
- package/build/lib/schema/cli-args.d.ts.map +1 -0
- package/build/lib/schema/cli-args.js +2 -4
- package/build/lib/schema/cli-transformers.d.ts +5 -0
- package/build/lib/schema/cli-transformers.d.ts.map +1 -0
- package/build/lib/schema/cli-transformers.js +2 -4
- package/build/lib/schema/index.d.ts +3 -0
- package/build/lib/schema/index.d.ts.map +1 -0
- package/build/lib/schema/index.js +2 -4
- package/build/lib/schema/keywords.d.ts +24 -0
- package/build/lib/schema/keywords.d.ts.map +1 -0
- package/build/lib/schema/keywords.js +2 -4
- package/build/lib/schema/schema.d.ts +259 -0
- package/build/lib/schema/schema.d.ts.map +1 -0
- package/build/lib/schema/schema.js +57 -39
- package/build/lib/utils.d.ts +66 -0
- package/build/lib/utils.d.ts.map +1 -0
- package/build/lib/utils.js +6 -35
- package/build/tsconfig.tsbuildinfo +1 -0
- package/lib/appium.js +188 -117
- package/lib/cli/args.js +19 -24
- package/lib/cli/driver-command.js +19 -8
- package/lib/cli/extension-command.js +314 -184
- package/lib/cli/extension.js +18 -16
- package/lib/cli/parser.js +7 -16
- package/lib/cli/plugin-command.js +16 -7
- package/lib/cli/utils.js +1 -1
- package/lib/config-file.js +6 -7
- package/lib/config.js +17 -12
- package/lib/constants.js +78 -0
- package/lib/extension/driver-config.js +249 -0
- package/lib/extension/extension-config.js +458 -0
- package/lib/extension/index.js +102 -0
- package/lib/extension/manifest.js +486 -0
- package/lib/extension/package-changed.js +63 -0
- package/lib/extension/plugin-config.js +113 -0
- package/lib/grid-register.js +4 -4
- package/lib/logsink.js +4 -0
- package/lib/main.js +54 -92
- package/lib/schema/arg-spec.js +11 -7
- package/lib/schema/cli-args.js +1 -1
- package/lib/schema/cli-transformers.js +0 -1
- package/lib/schema/keywords.js +1 -2
- package/lib/schema/schema.js +62 -31
- package/lib/utils.js +48 -45
- package/package.json +30 -24
- package/{postinstall.js → scripts/postinstall.js} +1 -1
- package/types/appium-manifest.d.ts +61 -0
- package/types/cli.d.ts +134 -0
- package/types/extension.d.ts +56 -0
- package/types/external-manifest.d.ts +58 -0
- package/types/index.d.ts +7 -0
- package/bin/ios-webkit-debug-proxy-launcher.js +0 -71
- package/build/check-npm-pack-files.js +0 -23
- package/build/commands-yml/parse.js +0 -319
- package/build/commands-yml/validator.js +0 -130
- package/build/index.js +0 -19
- package/build/lib/appium-config.schema.json +0 -0
- package/build/lib/cli/npm.js +0 -220
- package/build/lib/driver-config.js +0 -100
- package/build/lib/drivers.js +0 -100
- package/build/lib/ext-config-io.js +0 -165
- package/build/lib/extension-config.js +0 -320
- package/build/lib/plugin-config.js +0 -69
- package/build/lib/plugins.js +0 -18
- package/build/lib/schema/appium-config-schema.js +0 -253
- package/build/postinstall.js +0 -90
- package/build/test/cli/cli-e2e-specs.js +0 -221
- package/build/test/cli/cli-helpers.js +0 -86
- package/build/test/cli/cli-specs.js +0 -71
- package/build/test/cli/fixtures/test-driver/package.json +0 -27
- package/build/test/cli/schema-args-specs.js +0 -48
- package/build/test/cli/schema-e2e-specs.js +0 -47
- package/build/test/config-e2e-specs.js +0 -112
- package/build/test/config-file-e2e-specs.js +0 -191
- package/build/test/config-file-specs.js +0 -281
- package/build/test/config-specs.js +0 -258
- package/build/test/driver-e2e-specs.js +0 -435
- package/build/test/driver-specs.js +0 -386
- package/build/test/ext-config-io-specs.js +0 -181
- package/build/test/extension-config-specs.js +0 -365
- package/build/test/fixtures/allow-feat.txt +0 -5
- package/build/test/fixtures/caps.json +0 -3
- package/build/test/fixtures/config/allow-insecure.txt +0 -3
- package/build/test/fixtures/config/appium.config.bad-nodeconfig.json +0 -5
- package/build/test/fixtures/config/appium.config.bad.json +0 -32
- package/build/test/fixtures/config/appium.config.ext-good.json +0 -9
- package/build/test/fixtures/config/appium.config.ext-unknown-props.json +0 -10
- package/build/test/fixtures/config/appium.config.good.js +0 -40
- package/build/test/fixtures/config/appium.config.good.json +0 -33
- package/build/test/fixtures/config/appium.config.good.yaml +0 -30
- package/build/test/fixtures/config/appium.config.invalid.json +0 -31
- package/build/test/fixtures/config/appium.config.security-array.json +0 -5
- package/build/test/fixtures/config/appium.config.security-delimited.json +0 -5
- package/build/test/fixtures/config/appium.config.security-path.json +0 -5
- package/build/test/fixtures/config/driver-fake.config.json +0 -8
- package/build/test/fixtures/config/nodeconfig.json +0 -3
- package/build/test/fixtures/config/plugin-fake.config.json +0 -0
- package/build/test/fixtures/default-args.js +0 -35
- package/build/test/fixtures/deny-feat.txt +0 -5
- package/build/test/fixtures/driver.schema.js +0 -20
- package/build/test/fixtures/extensions.yaml +0 -27
- package/build/test/fixtures/flattened-schema.js +0 -532
- package/build/test/fixtures/plugin.schema.js +0 -20
- package/build/test/fixtures/schema-with-extensions.js +0 -28
- package/build/test/grid-register-specs.js +0 -74
- package/build/test/helpers.js +0 -75
- package/build/test/logger-specs.js +0 -76
- package/build/test/npm-specs.js +0 -20
- package/build/test/parser-specs.js +0 -319
- package/build/test/plugin-e2e-specs.js +0 -316
- package/build/test/schema/arg-spec-specs.js +0 -70
- package/build/test/schema/cli-args-specs.js +0 -408
- package/build/test/schema/schema-specs.js +0 -407
- package/build/test/utils-specs.js +0 -288
- package/lib/cli/npm.js +0 -251
- package/lib/driver-config.js +0 -101
- package/lib/drivers.js +0 -84
- package/lib/ext-config-io.js +0 -287
- package/lib/extension-config.js +0 -366
- package/lib/plugin-config.js +0 -63
- package/lib/plugins.js +0 -13
- package/lib/schema/appium-config-schema.js +0 -287
- package/types/appium-config.d.ts +0 -197
- package/types/types.d.ts +0 -206
package/lib/main.js
CHANGED
|
@@ -1,26 +1,26 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
|
|
3
|
-
// transpile:main
|
|
4
|
-
// @ts-check
|
|
5
3
|
|
|
6
|
-
import
|
|
4
|
+
import { init as logsinkInit } from './logsink'; // this import needs to come first since it sets up global npmlog
|
|
5
|
+
import logger from './logger'; // logger needs to remain second
|
|
7
6
|
// @ts-ignore
|
|
8
7
|
import { routeConfiguringFunction as makeRouter, server as baseServer } from '@appium/base-driver';
|
|
9
|
-
import { logger as logFactory, util } from '@appium/support';
|
|
8
|
+
import { logger as logFactory, util, env } from '@appium/support';
|
|
10
9
|
import { asyncify } from 'asyncbox';
|
|
11
10
|
import _ from 'lodash';
|
|
12
11
|
import { AppiumDriver } from './appium';
|
|
13
|
-
import { driverConfig, pluginConfig, USE_ALL_PLUGINS } from './cli/args';
|
|
14
12
|
import { runExtensionCommand } from './cli/extension';
|
|
15
|
-
import {
|
|
16
|
-
import { APPIUM_VER, checkNodeOk, getGitRev, getNonDefaultServerArgs, showBuildInfo, validateTmpDir, warnNodeDeprecations
|
|
13
|
+
import { getParser } from './cli/parser';
|
|
14
|
+
import { APPIUM_VER, checkNodeOk, getGitRev, getNonDefaultServerArgs, showConfig, showBuildInfo, validateTmpDir, warnNodeDeprecations } from './config';
|
|
17
15
|
import { readConfigFile } from './config-file';
|
|
18
|
-
import {
|
|
16
|
+
import { loadExtensions, getActivePlugins, getActiveDrivers } from './extension';
|
|
17
|
+
import { DRIVER_TYPE, PLUGIN_TYPE, SERVER_SUBCOMMAND } from './constants';
|
|
19
18
|
import registerNode from './grid-register';
|
|
20
|
-
import {
|
|
21
|
-
import { getDefaultsForSchema } from './schema/schema';
|
|
19
|
+
import { getDefaultsForSchema, validate } from './schema/schema';
|
|
22
20
|
import { inspect } from './utils';
|
|
23
21
|
|
|
22
|
+
const {resolveAppiumHome} = env;
|
|
23
|
+
|
|
24
24
|
/**
|
|
25
25
|
*
|
|
26
26
|
* @param {ParsedArgs} args
|
|
@@ -38,6 +38,8 @@ async function preflightChecks (args, throwInsteadOfExit = false) {
|
|
|
38
38
|
}
|
|
39
39
|
warnNodeDeprecations();
|
|
40
40
|
|
|
41
|
+
validate(args);
|
|
42
|
+
|
|
41
43
|
if (args.tmpDir) {
|
|
42
44
|
await validateTmpDir(args.tmpDir);
|
|
43
45
|
}
|
|
@@ -102,63 +104,11 @@ function logServerPort (address, port) {
|
|
|
102
104
|
logger.info(logMessage);
|
|
103
105
|
}
|
|
104
106
|
|
|
105
|
-
/**
|
|
106
|
-
* Find any plugin name which has been installed, and which has been requested for activation by
|
|
107
|
-
* using the --use-plugins flag, and turn each one into its class, so we can send them as objects
|
|
108
|
-
* to the server init. We also want to send/assign them to the umbrella driver so it can use them
|
|
109
|
-
* to wrap command execution
|
|
110
|
-
*
|
|
111
|
-
* @param {Object} args - argparser parsed dict
|
|
112
|
-
* @param {import('./plugin-config').default} pluginConfig - a plugin extension config
|
|
113
|
-
* @returns {PluginExtensionClass[]}
|
|
114
|
-
*/
|
|
115
|
-
function getActivePlugins (args, pluginConfig) {
|
|
116
|
-
return _.compact(Object.keys(pluginConfig.installedExtensions).filter((pluginName) =>
|
|
117
|
-
_.includes(args.usePlugins, pluginName) ||
|
|
118
|
-
(args.usePlugins.length === 1 && args.usePlugins[0] === USE_ALL_PLUGINS)
|
|
119
|
-
).map((pluginName) => {
|
|
120
|
-
try {
|
|
121
|
-
logger.info(`Attempting to load plugin ${pluginName}...`);
|
|
122
|
-
const PluginClass = /** @type {PluginExtensionClass} */(pluginConfig.require(pluginName));
|
|
123
|
-
|
|
124
|
-
PluginClass.pluginName = pluginName; // store the plugin name on the class so it can be used later
|
|
125
|
-
return PluginClass;
|
|
126
|
-
} catch (err) {
|
|
127
|
-
logger.error(`Could not load plugin '${pluginName}', so it will not be available. Error ` +
|
|
128
|
-
`in loading the plugin was: ${err.message}`);
|
|
129
|
-
logger.debug(err.stack);
|
|
130
|
-
}
|
|
131
|
-
}));
|
|
132
|
-
}
|
|
133
|
-
|
|
134
|
-
/**
|
|
135
|
-
* Find any driver name which has been installed, and turn each one into its class, so we can send
|
|
136
|
-
* them as objects to the server init in case they need to add methods/routes or update the server.
|
|
137
|
-
* If the --drivers flag was given, this method only loads the given drivers.
|
|
138
|
-
*
|
|
139
|
-
* @param {Object} args - argparser parsed dict
|
|
140
|
-
* @param {import('./driver-config').default} driverConfig - a driver extension config
|
|
141
|
-
*/
|
|
142
|
-
function getActiveDrivers (args, driverConfig) {
|
|
143
|
-
return _.compact(Object.keys(driverConfig.installedExtensions).filter((driverName) =>
|
|
144
|
-
_.includes(args.useDrivers, driverName) || args.useDrivers.length === 0
|
|
145
|
-
).map((driverName) => {
|
|
146
|
-
try {
|
|
147
|
-
logger.info(`Attempting to load driver ${driverName}...`);
|
|
148
|
-
return driverConfig.require(driverName);
|
|
149
|
-
} catch (err) {
|
|
150
|
-
logger.error(`Could not load driver '${driverName}', so it will not be available. Error ` +
|
|
151
|
-
`in loading the driver was: ${err.message}`);
|
|
152
|
-
logger.debug(err.stack);
|
|
153
|
-
}
|
|
154
|
-
}));
|
|
155
|
-
}
|
|
156
|
-
|
|
157
107
|
/**
|
|
158
108
|
* Gets a list of `updateServer` functions from all extensions
|
|
159
|
-
* @param {
|
|
160
|
-
* @param {
|
|
161
|
-
* @returns {
|
|
109
|
+
* @param {DriverClass[]} driverClasses
|
|
110
|
+
* @param {PluginClass[]} pluginClasses
|
|
111
|
+
* @returns {import('@appium/base-driver/lib/basedriver/driver').UpdateServerCallback[]}
|
|
162
112
|
*/
|
|
163
113
|
function getServerUpdaters (driverClasses, pluginClasses) {
|
|
164
114
|
return _.compact(_.map([...driverClasses, ...pluginClasses], 'updateServer'));
|
|
@@ -166,9 +116,9 @@ function getServerUpdaters (driverClasses, pluginClasses) {
|
|
|
166
116
|
|
|
167
117
|
/**
|
|
168
118
|
* Makes a big `MethodMap` from all the little `MethodMap`s in the extensions
|
|
169
|
-
* @param {
|
|
170
|
-
* @param {
|
|
171
|
-
* @returns {import('@appium/
|
|
119
|
+
* @param {DriverClass[]} driverClasses
|
|
120
|
+
* @param {PluginClass[]} pluginClasses
|
|
121
|
+
* @returns {import('@appium/types').MethodMap}
|
|
172
122
|
*/
|
|
173
123
|
function getExtraMethodMap (driverClasses, pluginClasses) {
|
|
174
124
|
return [...driverClasses, ...pluginClasses].reduce(
|
|
@@ -182,11 +132,10 @@ function getExtraMethodMap (driverClasses, pluginClasses) {
|
|
|
182
132
|
*
|
|
183
133
|
* Use this to get at the configuration schema.
|
|
184
134
|
*
|
|
185
|
-
* If `args` contains a non-empty `subcommand` which is not `server`, this function
|
|
186
|
-
* will resolve with an empty object.
|
|
135
|
+
* If `args` contains a non-empty `subcommand` which is not `server`, this function will return an empty object.
|
|
187
136
|
*
|
|
188
|
-
* @param {
|
|
189
|
-
* @returns {Promise<
|
|
137
|
+
* @param {PartialArgs} [args] - Partial args (progammatic usage only)
|
|
138
|
+
* @returns {Promise<ServerInitResult | ExtCommandInitResult>}
|
|
190
139
|
* @example
|
|
191
140
|
* import {init, getSchema} from 'appium';
|
|
192
141
|
* const options = {}; // config object
|
|
@@ -194,11 +143,15 @@ function getExtraMethodMap (driverClasses, pluginClasses) {
|
|
|
194
143
|
* const schema = getSchema(); // entire config schema including plugins and drivers
|
|
195
144
|
*/
|
|
196
145
|
async function init (args) {
|
|
197
|
-
const
|
|
146
|
+
const appiumHome = args?.appiumHome ?? await resolveAppiumHome();
|
|
147
|
+
|
|
148
|
+
const {driverConfig, pluginConfig} = await loadExtensions(appiumHome);
|
|
149
|
+
|
|
150
|
+
const parser = getParser();
|
|
198
151
|
let throwInsteadOfExit = false;
|
|
199
152
|
/** @type {ParsedArgs} */
|
|
200
153
|
let preConfigParsedArgs;
|
|
201
|
-
/** @type {
|
|
154
|
+
/** @type {ParsedArgs} */
|
|
202
155
|
let parsedArgs;
|
|
203
156
|
/**
|
|
204
157
|
* This is a definition (instead of declaration) because TS can't figure out
|
|
@@ -215,7 +168,7 @@ async function init (args) {
|
|
|
215
168
|
// but remove it since it's not a real server arg per se
|
|
216
169
|
delete args.throwInsteadOfExit;
|
|
217
170
|
}
|
|
218
|
-
preConfigParsedArgs = {...args, subcommand: args.subcommand ?? SERVER_SUBCOMMAND};
|
|
171
|
+
preConfigParsedArgs = /** @type {ParsedArgs} */({...args, subcommand: args.subcommand ?? SERVER_SUBCOMMAND});
|
|
219
172
|
} else {
|
|
220
173
|
// otherwise parse from CLI
|
|
221
174
|
preConfigParsedArgs = parser.parseArgs();
|
|
@@ -227,7 +180,6 @@ async function init (args) {
|
|
|
227
180
|
throw new Error(`Errors in config file ${configResult.filepath}:\n ${configResult.reason ?? configResult.errors}`);
|
|
228
181
|
}
|
|
229
182
|
|
|
230
|
-
|
|
231
183
|
// merge config and apply defaults.
|
|
232
184
|
// the order of precendece is:
|
|
233
185
|
// 1. command line args
|
|
@@ -256,11 +208,11 @@ async function init (args) {
|
|
|
256
208
|
// if the user has requested the 'driver' CLI, don't run the normal server,
|
|
257
209
|
// but instead pass control to the driver CLI
|
|
258
210
|
if (parsedArgs.subcommand === DRIVER_TYPE) {
|
|
259
|
-
await runExtensionCommand(parsedArgs,
|
|
211
|
+
await runExtensionCommand(parsedArgs, driverConfig);
|
|
260
212
|
return {};
|
|
261
213
|
}
|
|
262
214
|
if (parsedArgs.subcommand === PLUGIN_TYPE) {
|
|
263
|
-
await runExtensionCommand(parsedArgs,
|
|
215
|
+
await runExtensionCommand(parsedArgs, pluginConfig);
|
|
264
216
|
return {};
|
|
265
217
|
}
|
|
266
218
|
|
|
@@ -282,32 +234,32 @@ async function init (args) {
|
|
|
282
234
|
appiumDriver.driverConfig = driverConfig;
|
|
283
235
|
await preflightChecks(parsedArgs, throwInsteadOfExit);
|
|
284
236
|
|
|
285
|
-
return {appiumDriver, parsedArgs};
|
|
237
|
+
return /** @type {ServerInitResult} */({appiumDriver, parsedArgs, driverConfig, pluginConfig});
|
|
286
238
|
}
|
|
287
239
|
|
|
288
240
|
/**
|
|
289
241
|
* Initializes Appium's config. Starts server if appropriate and resolves the
|
|
290
242
|
* server instance if so; otherwise resolves w/ `undefined`.
|
|
291
|
-
* @param {
|
|
292
|
-
* @returns {Promise<import('
|
|
243
|
+
* @param {PartialArgs} [args] - Arguments from CLI or otherwise
|
|
244
|
+
* @returns {Promise<import('http').Server|undefined>}
|
|
293
245
|
*/
|
|
294
246
|
async function main (args) {
|
|
295
|
-
const {appiumDriver, parsedArgs} = await init(args);
|
|
247
|
+
const {appiumDriver, parsedArgs, pluginConfig, driverConfig} = /** @type {ServerInitResult} */(await init(args));
|
|
296
248
|
|
|
297
|
-
if (!appiumDriver || !parsedArgs) {
|
|
249
|
+
if (!appiumDriver || !parsedArgs || !pluginConfig || !driverConfig) {
|
|
298
250
|
// if this branch is taken, we've run a different subcommand, so there's nothing
|
|
299
251
|
// left to do here.
|
|
300
252
|
return;
|
|
301
253
|
}
|
|
302
254
|
|
|
303
|
-
const pluginClasses = getActivePlugins(
|
|
255
|
+
const pluginClasses = getActivePlugins(pluginConfig, parsedArgs.usePlugins);
|
|
304
256
|
// set the active plugins on the umbrella driver so it can use them for commands
|
|
305
257
|
appiumDriver.pluginClasses = pluginClasses;
|
|
306
258
|
|
|
307
259
|
await logStartupInfo(parsedArgs);
|
|
308
260
|
let routeConfiguringFunction = makeRouter(appiumDriver);
|
|
309
261
|
|
|
310
|
-
const driverClasses = getActiveDrivers(
|
|
262
|
+
const driverClasses = getActiveDrivers(driverConfig, parsedArgs.useDrivers);
|
|
311
263
|
const serverUpdaters = getServerUpdaters(driverClasses, pluginClasses);
|
|
312
264
|
const extraMethodMap = getExtraMethodMap(driverClasses, pluginClasses);
|
|
313
265
|
|
|
@@ -382,23 +334,33 @@ if (require.main === module) {
|
|
|
382
334
|
}
|
|
383
335
|
|
|
384
336
|
// everything below here is intended to be a public API.
|
|
385
|
-
export { main, init };
|
|
386
|
-
export { APPIUM_HOME } from './extension-config';
|
|
387
|
-
export { getSchema, validate, finalizeSchema } from './schema/schema';
|
|
388
337
|
export { readConfigFile } from './config-file';
|
|
338
|
+
export { finalizeSchema, getSchema, validate } from './schema/schema';
|
|
339
|
+
export { main, init, resolveAppiumHome };
|
|
340
|
+
|
|
341
|
+
/**
|
|
342
|
+
* @typedef {import('../types/cli').ParsedArgs} ParsedArgs
|
|
343
|
+
*/
|
|
389
344
|
|
|
390
345
|
/**
|
|
391
|
-
* @typedef {import('../types/
|
|
346
|
+
* @typedef {import('../types/cli').PartialArgs} PartialArgs
|
|
347
|
+
* @typedef {import('../types').DriverType} DriverType
|
|
348
|
+
* @typedef {import('../types').PluginType} PluginType
|
|
349
|
+
* @typedef {import('../types/extension').DriverClass} DriverClass
|
|
350
|
+
* @typedef {import('../types/extension').PluginClass} PluginClass
|
|
392
351
|
*/
|
|
393
352
|
|
|
394
353
|
/**
|
|
395
|
-
*
|
|
354
|
+
* Literally an empty object
|
|
355
|
+
* @typedef { {} } ExtCommandInitResult
|
|
396
356
|
*/
|
|
397
357
|
|
|
398
358
|
/**
|
|
399
|
-
* @typedef
|
|
359
|
+
* @typedef ServerInitData
|
|
360
|
+
* @property {AppiumDriver} appiumDriver - The Appium driver
|
|
361
|
+
* @property {ParsedArgs} parsedArgs - The parsed arguments
|
|
400
362
|
*/
|
|
401
363
|
|
|
402
364
|
/**
|
|
403
|
-
* @typedef {import('./
|
|
365
|
+
* @typedef {ServerInitData & import('./extension').ExtensionConfigs} ServerInitResult
|
|
404
366
|
*/
|
package/lib/schema/arg-spec.js
CHANGED
|
@@ -28,6 +28,7 @@ const PROPERTIES = 'properties';
|
|
|
28
28
|
* option) used for cross-referencing.
|
|
29
29
|
*
|
|
30
30
|
* This class has no instance methods, and is basically just a read-only "struct".
|
|
31
|
+
* @template D
|
|
31
32
|
*/
|
|
32
33
|
export class ArgSpec {
|
|
33
34
|
/**
|
|
@@ -81,7 +82,7 @@ export class ArgSpec {
|
|
|
81
82
|
/**
|
|
82
83
|
* Whatever the default value of this argument is, as specified by the
|
|
83
84
|
* `default` property of the schema.
|
|
84
|
-
* @type {D}
|
|
85
|
+
* @type {D|undefined}
|
|
85
86
|
*/
|
|
86
87
|
defaultValue;
|
|
87
88
|
|
|
@@ -92,7 +93,6 @@ export class ArgSpec {
|
|
|
92
93
|
*
|
|
93
94
|
* The _constructor_ is private. Use {@link ArgSpec.create} instead.
|
|
94
95
|
* @private
|
|
95
|
-
* @template D
|
|
96
96
|
* @param {string} name
|
|
97
97
|
* @param {ArgSpecOptions<D>} [opts]
|
|
98
98
|
*/
|
|
@@ -176,12 +176,15 @@ export class ArgSpec {
|
|
|
176
176
|
/**
|
|
177
177
|
* When given the root ID of a schema for an extension (`<extType>-<normalizedExtName>.json`) Returns an object containing the extension type and the _normalized_ extension name.
|
|
178
178
|
* @param {string} schemaId - Root schema ID
|
|
179
|
-
* @returns { {extType
|
|
179
|
+
* @returns { {extType?: ExtensionType, normalizedExtName?: string} }
|
|
180
180
|
*/
|
|
181
181
|
static extensionInfoFromRootSchemaId (schemaId) {
|
|
182
182
|
const matches = schemaId.match(SCHEMA_ID_REGEXP);
|
|
183
183
|
if (matches?.groups) {
|
|
184
|
-
const {extType, normalizedExtName} =
|
|
184
|
+
const {extType, normalizedExtName} =
|
|
185
|
+
/** @type { {extType: ExtensionType, normalizedExtName: string} } */ (
|
|
186
|
+
matches.groups
|
|
187
|
+
);
|
|
185
188
|
return {extType, normalizedExtName};
|
|
186
189
|
}
|
|
187
190
|
return {};
|
|
@@ -192,7 +195,8 @@ export class ArgSpec {
|
|
|
192
195
|
*
|
|
193
196
|
* @param {string} name - The canonical name of the argument. Corresponds to a key in a schema's
|
|
194
197
|
* `properties` property.
|
|
195
|
-
* @
|
|
198
|
+
* @template D
|
|
199
|
+
* @param {ArgSpecOptions<D>} [opts] - Options
|
|
196
200
|
* @returns {Readonly<ArgSpec>}
|
|
197
201
|
*/
|
|
198
202
|
static create (name, opts) {
|
|
@@ -216,7 +220,7 @@ export class ArgSpec {
|
|
|
216
220
|
/**
|
|
217
221
|
* Options for {@link ArgSpec.create}
|
|
218
222
|
* @template D
|
|
219
|
-
* @typedef
|
|
223
|
+
* @typedef ArgSpecOptions
|
|
220
224
|
* @property {string} [extName]
|
|
221
225
|
* @property {ExtensionType} [extType]
|
|
222
226
|
* @property {string} [dest]
|
|
@@ -224,5 +228,5 @@ export class ArgSpec {
|
|
|
224
228
|
*/
|
|
225
229
|
|
|
226
230
|
/**
|
|
227
|
-
* @typedef {import('../
|
|
231
|
+
* @typedef {import('../extension/manifest').ExtensionType} ExtensionType
|
|
228
232
|
*/
|
package/lib/schema/cli-args.js
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
// @ts-check
|
|
2
1
|
|
|
3
2
|
import {ArgumentTypeError} from 'argparse';
|
|
4
3
|
import _ from 'lodash';
|
|
@@ -139,6 +138,7 @@ function subSchemaToArgDef (subSchema, argSpec) {
|
|
|
139
138
|
// handle special cases for various types
|
|
140
139
|
switch (type) {
|
|
141
140
|
// booleans do not have a type per `ArgumentOptions`, just an "action"
|
|
141
|
+
// NOTE: due to limitations of `argparse`, we cannot provide fancy help text, and must rely on its internal error messaging.
|
|
142
142
|
case TYPENAMES.BOOLEAN: {
|
|
143
143
|
argOpts.action = 'store_const';
|
|
144
144
|
argOpts.const = true;
|
package/lib/schema/keywords.js
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
// @ts-check
|
|
2
1
|
|
|
3
2
|
import { transformers } from './cli-transformers';
|
|
4
3
|
|
|
@@ -120,7 +119,7 @@ export const keywords = {
|
|
|
120
119
|
/**
|
|
121
120
|
* These are the custom keywords that Appium recognizes.
|
|
122
121
|
*
|
|
123
|
-
* @typedef
|
|
122
|
+
* @typedef AppiumJSONSchemaKeywords
|
|
124
123
|
* @property {string} [appiumCliDest]
|
|
125
124
|
* @property {string} [appiumCliDescription]
|
|
126
125
|
* @property {string[]} [appiumCliAliases]
|
package/lib/schema/schema.js
CHANGED
|
@@ -1,15 +1,44 @@
|
|
|
1
|
-
// @ts-check
|
|
2
1
|
|
|
3
2
|
import Ajv from 'ajv';
|
|
4
3
|
import addFormats from 'ajv-formats';
|
|
5
4
|
import _ from 'lodash';
|
|
6
5
|
import path from 'path';
|
|
7
|
-
import { DRIVER_TYPE, PLUGIN_TYPE } from '../
|
|
8
|
-
import {
|
|
9
|
-
import appiumConfigSchema from './appium-config-schema';
|
|
6
|
+
import { DRIVER_TYPE, PLUGIN_TYPE } from '../constants';
|
|
7
|
+
import { AppiumConfigJsonSchema } from '@appium/schema';
|
|
10
8
|
import { APPIUM_CONFIG_SCHEMA_ID, ArgSpec, SERVER_PROP_NAME } from './arg-spec';
|
|
11
9
|
import { keywords } from './keywords';
|
|
12
10
|
|
|
11
|
+
/**
|
|
12
|
+
* Key/value pairs go in... but they don't come out.
|
|
13
|
+
*
|
|
14
|
+
* @template K,V
|
|
15
|
+
* @extends {Map<K,V>}
|
|
16
|
+
*/
|
|
17
|
+
export class RoachHotelMap extends Map {
|
|
18
|
+
/**
|
|
19
|
+
* @param {K} key
|
|
20
|
+
* @param {V} value
|
|
21
|
+
*/
|
|
22
|
+
set (key, value) {
|
|
23
|
+
if (this.has(key)) {
|
|
24
|
+
throw new Error(`${key} is already set`);
|
|
25
|
+
}
|
|
26
|
+
return super.set(key, value);
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
/**
|
|
30
|
+
* @param {K} key
|
|
31
|
+
*/
|
|
32
|
+
// eslint-disable-next-line no-unused-vars
|
|
33
|
+
delete (key) {
|
|
34
|
+
return false;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
clear () {
|
|
38
|
+
throw new Error(`Cannot clear RoachHotelMap`);
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
|
|
13
42
|
/**
|
|
14
43
|
* Extensions that an extension schema file can have.
|
|
15
44
|
*/
|
|
@@ -28,9 +57,9 @@ class AppiumSchema {
|
|
|
28
57
|
*
|
|
29
58
|
* Used to provide easy lookups of argument metadata when converting between different representations of those arguments.
|
|
30
59
|
* @private
|
|
31
|
-
* @type {
|
|
60
|
+
* @type {RoachHotelMap<string,ArgSpec>}
|
|
32
61
|
*/
|
|
33
|
-
_argSpecs = new
|
|
62
|
+
_argSpecs = new RoachHotelMap();
|
|
34
63
|
|
|
35
64
|
/**
|
|
36
65
|
* A map of extension types to extension names to schema objects.
|
|
@@ -83,25 +112,27 @@ class AppiumSchema {
|
|
|
83
112
|
* @returns {AppiumSchema}
|
|
84
113
|
*/
|
|
85
114
|
static create () {
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
115
|
+
if (!AppiumSchema._instance) {
|
|
116
|
+
const instance = new AppiumSchema();
|
|
117
|
+
AppiumSchema._instance = instance;
|
|
118
|
+
_.bindAll(instance, [
|
|
119
|
+
'finalize',
|
|
120
|
+
'flatten',
|
|
121
|
+
'getAllArgSpecs',
|
|
122
|
+
'getArgSpec',
|
|
123
|
+
'getDefaults',
|
|
124
|
+
'getDefaultsForExtension',
|
|
125
|
+
'getSchema',
|
|
126
|
+
'hasArgSpec',
|
|
127
|
+
'isFinalized',
|
|
128
|
+
'registerSchema',
|
|
129
|
+
'hasRegisteredSchema',
|
|
130
|
+
'reset',
|
|
131
|
+
'validate',
|
|
132
|
+
]);
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
return AppiumSchema._instance;
|
|
105
136
|
}
|
|
106
137
|
|
|
107
138
|
/**
|
|
@@ -150,7 +181,7 @@ class AppiumSchema {
|
|
|
150
181
|
*/
|
|
151
182
|
finalize () {
|
|
152
183
|
if (this.isFinalized()) {
|
|
153
|
-
return /** @type {
|
|
184
|
+
return /** @type {NonNullable<typeof this._finalizedSchemas>} */ (
|
|
154
185
|
this._finalizedSchemas
|
|
155
186
|
);
|
|
156
187
|
}
|
|
@@ -158,7 +189,7 @@ class AppiumSchema {
|
|
|
158
189
|
const ajv = this._ajv;
|
|
159
190
|
|
|
160
191
|
// Ajv will _mutate_ the schema, so we need to clone it.
|
|
161
|
-
const baseSchema = _.cloneDeep(
|
|
192
|
+
const baseSchema = _.cloneDeep(AppiumConfigJsonSchema);
|
|
162
193
|
|
|
163
194
|
/**
|
|
164
195
|
*
|
|
@@ -259,7 +290,7 @@ class AppiumSchema {
|
|
|
259
290
|
for (const schemaId of Object.keys(this._finalizedSchemas ?? {})) {
|
|
260
291
|
this._ajv.removeSchema(schemaId);
|
|
261
292
|
}
|
|
262
|
-
this._argSpecs = new
|
|
293
|
+
this._argSpecs = new RoachHotelMap();
|
|
263
294
|
this._registeredSchemas = {
|
|
264
295
|
[DRIVER_TYPE]: new Map(),
|
|
265
296
|
[PLUGIN_TYPE]: new Map(),
|
|
@@ -276,7 +307,7 @@ class AppiumSchema {
|
|
|
276
307
|
* This is "fail-fast" in that the schema will immediately be validated against JSON schema draft-07 _or_ whatever the value of the schema's `$schema` prop is.
|
|
277
308
|
*
|
|
278
309
|
* Does _not_ add the schema to the `ajv` instance (this is done by {@link AppiumSchema.finalize}).
|
|
279
|
-
* @param {
|
|
310
|
+
* @param {ExtensionType} extType - Extension type
|
|
280
311
|
* @param {string} extName - Unique extension name for `type`
|
|
281
312
|
* @param {SchemaObject} schema - Schema object
|
|
282
313
|
* @throws {SchemaNameConflictError} If the schema is an invalid
|
|
@@ -666,12 +697,12 @@ export const {isAllowedSchemaFileExtension} = AppiumSchema;
|
|
|
666
697
|
*/
|
|
667
698
|
|
|
668
699
|
/**
|
|
669
|
-
* @typedef {import('../
|
|
700
|
+
* @typedef {import('../extension/manifest').ExtensionType} ExtensionType
|
|
670
701
|
*/
|
|
671
702
|
|
|
672
703
|
/**
|
|
673
704
|
* An object having property `additionalProperties: false`
|
|
674
|
-
* @typedef
|
|
705
|
+
* @typedef StrictProp
|
|
675
706
|
* @property {false} additionalProperties
|
|
676
707
|
*/
|
|
677
708
|
|