Secure your code as it's written. Use Snyk Code to scan source code in minutes - no build needed - and fix issues immediately.
async pushAppBundle (app, timeout = DEFAULT_ITEM_PUSH_TIMEOUT) {
const timer = new timing.Timer().start();
const afcService = await services.startAfcService(this.udid);
// We are pushing serially due to this https://github.com/appium/appium/issues/13115. There is nothing else we can do besides this
try {
const bundlePathOnPhone = await this.createAppPath(afcService, app);
await fs.walkDir(app, true, async (itemPath, isDir) => {
const pathOnPhone = path.join(bundlePathOnPhone, path.relative(app, itemPath));
if (isDir) {
await afcService.createDirectory(pathOnPhone);
} else {
const readStream = fs.createReadStream(itemPath, {autoClose: true});
const writeStream = await afcService.createWriteStream(pathOnPhone, {autoDestroy: true});
writeStream.on('finish', writeStream.destroy);
const itemPushWait = new B((resolve, reject) => {
writeStream.on('close', resolve);
const onStreamError = (e) => {
readStream.unpipe(writeStream);
appPath
], installOpts);
// this.remoteAppsCacheLimit <= 0 means no caching should be applied
if (this.remoteAppsCacheLimit > 0) {
const cachedRemotePath = await this.cacheApk(appPath, {
timeout: options.timeout,
});
performAppInstall = async () => await this.shell([
'pm',
'install',
...installArgs,
cachedRemotePath
], installOpts);
}
try {
const timer = new timing.Timer().start();
const output = await performAppInstall();
log.info(`The installation of '${path.basename(appPath)}' took ${timer.getDuration().asMilliSeconds.toFixed(0)}ms`);
const truncatedOutput = (!_.isString(output) || output.length <= 300) ?
output : `${output.substr(0, 150)}...${output.substr(output.length - 150)}`;
log.debug(`Install command stdout: ${truncatedOutput}`);
if (/\[INSTALL[A-Z_]+FAILED[A-Z_]+\]/.test(output)) {
if (this.isTestPackageOnlyError(output)) {
const msg = `Set 'allowTestPackages' capability to true in order to allow test packages installation.`;
log.warn(msg);
throw new Error(`${output}\n${msg}`);
}
throw new Error(output);
}
} catch (err) {
// on some systems this will throw an error if the app already
// exists
async selectPage (appIdKey, pageIdKey, skipReadyCheck = false) {
this.appIdKey = `PID:${appIdKey}`;
this.pageIdKey = pageIdKey;
log.debug(`Selecting page '${pageIdKey}' on app '${this.appIdKey}' and forwarding socket setup`);
const timer = new timing.Timer().start();
await this.rpcClient.selectPage(this.appIdKey, pageIdKey);
// make sure everything is ready to go
if (!skipReadyCheck && !await this.checkPageIsReady()) {
await this.pageUnload();
}
log.debug(`Selected page after ${timer.getDuration().asMilliSeconds.toFixed(0)}ms`);
}
async selectApp (currentUrl = null, maxTries = SELECT_APP_RETRIES, ignoreAboutBlankUrl = false) {
const shouldCheckForTarget = this.rpcClient.shouldCheckForTarget;
this.rpcClient.shouldCheckForTarget = false;
try {
const timer = new timing.Timer().start();
log.debug('Selecting application');
if (!this.appDict || _.isEmpty(this.appDict)) {
log.debug('No applications currently connected.');
return [];
}
const { appIdKey, pageDict } = await this.searchForApp(currentUrl, maxTries, ignoreAboutBlankUrl);
// if, after all this, we have no dictionary, we have failed
if (!appIdKey || !pageDict) {
log.errorAndThrow(`Could not connect to a valid app after ${maxTries} tries.`);
}
if (this.appIdKey !== appIdKey) {
log.debug(`Received altered app id, updating from '${this.appIdKey}' to '${appIdKey}'`);
this.appIdKey = appIdKey;
return (async () => {
try {
const timer = new timing.Timer().start();
await this.xcodebuild.start(true);
if (!buildOnly) {
let status = await this.waitForStart(timer);
resolve(status);
}
} catch (err) {
let msg = `Unable to start WebDriverAgent: ${err}`;
log.error(msg);
reject(new Error(msg));
}
})();
});
async send (command, opts = {}, waitForResponse = true) {
const timer = new timing.Timer().start();
const {
appIdKey,
pageIdKey
} = opts;
try {
if (!_.isEmpty(appIdKey) && !_.isEmpty(pageIdKey)) {
await this.waitForTarget(appIdKey, pageIdKey);
}
return await this.sendToDevice(command, opts, waitForResponse);
} catch (err) {
if (err.message.includes(`'Target' domain was not found`)) {
this.setCommunicationProtocol(false);
return await this.sendToDevice(command, opts, waitForResponse);
} else if (err.message.includes(`domain was not found`) || err.message.includes(`Some arguments of method`)) {
this.setCommunicationProtocol(true);
await this.waitForTarget(appIdKey, pageIdKey);
async run (opts = {}) {
opts = Object.assign({
startupTimeout: this.startupTimeout,
}, opts);
const {state} = await this.stat();
const isServerRunning = state === 'Booted';
const isUIClientRunning = await this.isUIClientRunning();
if (isServerRunning && isUIClientRunning) {
log.info(`Both Simulator with UDID ${this.udid} and the UI client are currently running`);
return;
}
const timer = new timing.Timer().start();
try {
await this.shutdown();
} catch (err) {
log.warn(`Error on Simulator shutdown: ${err.message}`);
}
await this.startUIClient(opts);
await this.waitForBoot(opts.startupTimeout);
log.info(`Simulator with UDID ${this.udid} booted in ${timer.getDuration().asSeconds.toFixed(3)}s`);
}
if (!_.isEmpty(this._screenRecordingProperties)) {
for (const record of (this._screenRecordingProperties.records || [])) {
await this.adb.rimraf(record);
}
this._screenRecordingProperties = null;
}
const timeout = parseFloat(timeLimit);
if (isNaN(timeout) || timeout > MAX_TIME_SEC || timeout <= 0) {
throw new Error(`The timeLimit value must be in range [1, ${MAX_TIME_SEC}] seconds. ` +
`The value of '${timeLimit}' has been passed instead.`);
}
this._screenRecordingProperties = {
timer: new timing.Timer().start(),
videoSize,
timeLimit,
currentTimeLimit: timeLimit,
bitRate,
bugReport,
records: [],
recordingProcess: null,
stopped: false,
};
await scheduleScreenRecord(this.adb, this._screenRecordingProperties);
return result;
};
if (onError) {
onError(error);
}
}
});
await bootMonitor.start(0);
const stopMonitor = async () => {
if (bootMonitor.isRunning) {
try {
await bootMonitor.stop();
} catch (e) {
log.warn(e.message);
}
}
};
const timer = new timing.Timer().start();
if (onFinished) {
timeoutHandler = setTimeout(stopMonitor, timeout);
} else {
try {
await waitForCondition(() => {
if (error) {
throw error;
}
return isBootingFinished;
}, {waitMs: timeout, intervalMs: 500});
} catch (err) {
await stopMonitor();
throw new Error(`The simulator ${udid} has failed to finish booting after ${timer.getDuration().asSeconds.toFixed(3)}s. ` +
`Original status: ${status}`);
}
}