Skip to content

Commit 5e4108f

Browse files
Tsenov/extend device support (#123)
* feat(sauceLabs): get device density and run in background * chore: update dependencies * fix: find array of elements
1 parent 0f830ab commit 5e4108f

10 files changed

+112
-73
lines changed

Diff for: lib/appium-driver.d.ts

+5
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,7 @@ export declare class AppiumDriver {
5555
*/
5656
readonly storageByDeviceName: string;
5757
static createAppiumDriver(port: number, args: INsCapabilities): Promise<AppiumDriver>;
58+
private static applyDeviceAdditionsSettings(args, sessionIfno);
5859
/**
5960
*
6061
* @param xPath
@@ -203,5 +204,9 @@ export declare class AppiumDriver {
203204
* @param waitForElement
204205
*/
205206
findElementByAccessibilityIdIfExists(id: string, waitForElement?: number): Promise<UIElement>;
207+
executeShellCommand(commandAndargs: {
208+
command: string;
209+
"args": Array<any>;
210+
}): Promise<any>;
206211
setDontKeepActivities(value: boolean): Promise<void>;
207212
}

Diff for: lib/appium-driver.ts

+44-8
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,8 @@ import {
1616
DeviceController,
1717
IDevice,
1818
DeviceType,
19-
AndroidController
19+
AndroidController,
20+
IOSController
2021
} from "mobile-devices-controller";
2122
import {
2223
addExt,
@@ -179,11 +180,15 @@ export class AppiumDriver {
179180

180181
const driver = await wd.promiseChainRemote(driverConfig);
181182
AppiumDriver.configureLogging(driver, args.verbose);
183+
182184
let hasStarted = false;
183185
let retries = 10;
184186
while (retries > 0 && !hasStarted) {
185187
try {
186-
await driver.init(args.appiumCaps);
188+
const sessionIfno = await driver.init(args.appiumCaps);
189+
log(sessionIfno, args.verbose);
190+
AppiumDriver.applyDeviceAdditionsSettings(args, sessionIfno);
191+
187192
hasStarted = true;
188193
} catch (error) {
189194
console.log(error);
@@ -204,6 +209,29 @@ export class AppiumDriver {
204209
return new AppiumDriver(driver, wd, webio, driverConfig, args);
205210
}
206211

212+
private static applyDeviceAdditionsSettings(args: INsCapabilities, sessionIfno: any) {
213+
if (!args.device.config || !args.device.config.density || !args.device.config.offset) {
214+
args.device.config = {};
215+
const density: number = sessionIfno[1].deviceScreenDensity / 100;
216+
args.device.config['density'] = density;
217+
218+
if (args.appiumCaps.platformName.toLowerCase() === "android") {
219+
args.device.config['offsetPixels'] = AndroidController.calculateScreenOffset(density);
220+
} else {
221+
IOSController.getDevicesScreenInfo().forEach((v, k, m) => {
222+
if (args.device.name.includes(k)) {
223+
args.device.config = {
224+
density: args.device.config['density'] || v.density,
225+
offsetPixels: v.actionBarHeight
226+
};
227+
}
228+
});
229+
}
230+
231+
console.log(`Device setting:`, args.device.config);
232+
}
233+
}
234+
207235
/**
208236
*
209237
* @param xPath
@@ -600,15 +628,15 @@ export class AppiumDriver {
600628
}
601629

602630
private async convertArrayToUIElements(array, searchM, args) {
603-
let i = 0;
604631
const arrayOfUIElements = new Array<UIElement>();
605632
if (!array || array === null) {
606633
return arrayOfUIElements;
607634
}
608-
array.forEach(async element => {
609-
arrayOfUIElements.push(new UIElement(await element, this._driver, this._wd, this._webio, this._args, searchM, args, i));
610-
i++;
611-
});
635+
636+
for (let index = 0; index < array.length; index++) {
637+
const element = array[index];
638+
arrayOfUIElements.push(new UIElement(await element, this._driver, this._wd, this._webio, this._args, searchM, args, index));
639+
}
612640

613641
return arrayOfUIElements;
614642
}
@@ -705,9 +733,17 @@ export class AppiumDriver {
705733
}
706734
}
707735

736+
public async executeShellCommand(commandAndargs: { command: string, "args": Array<any> }) {
737+
const output = await this._driver.execute("mobile: shell", commandAndargs);
738+
return output;
739+
}
708740
public async setDontKeepActivities(value: boolean) {
709741
if (this._args.isAndroid) {
710-
AndroidController.setDontKeepActivities(value, this._args.device);
742+
const status = value ? 1 : 0;
743+
const output = await this.executeShellCommand({ command: "settings", args: ['put', 'global', 'always_finish_activities', status] });
744+
//check if set
745+
const check = await this.executeShellCommand({ command: "settings", args: ['get', 'global', 'always_finish_activities'] })
746+
console.info(`always_finish_activities: ${check}`)
711747
} else {
712748
// Do nothing for iOS ...
713749
}

Diff for: lib/appium-server.ts

+2-1
Original file line numberDiff line numberDiff line change
@@ -84,7 +84,8 @@ export class AppiumServer {
8484
}
8585

8686
private startAppiumServer(logLevel: string, isSauceLab: boolean) {
87-
const startingServerArgs = isSauceLab ? [ "--log-level", logLevel] : ["-p", this.port.toString(), "--log-level", logLevel];
87+
const startingServerArgs: Array<string> = isSauceLab ? ["--log-level", logLevel] : ["-p", this.port.toString(), "--log-level", logLevel];
88+
startingServerArgs.push("--relaxed-security");
8889
this._server = child_process.spawn(this._appium, startingServerArgs, {
8990
shell: true,
9091
detached: false

Diff for: lib/frame-comparer.ts

-1
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
import { mkdirSync } from "fs";
22
import { resolve, getStorageByDeviceName, getReportPath } from "./utils";
33
import { INsCapabilities } from "./interfaces/ns-capabilities";
4-
import { IDevice } from "mobile-devices-controller";
54
import * as frComparer from "frame-comparer";
65
import { IRectangle } from "..";
76
import { ImageHelper } from "./image-helper";

Diff for: lib/image-helper.d.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ export declare class ImageHelper {
1010
blockOutAreas: IRectangle[];
1111
imageOutputLimit(): ImageOptions;
1212
thresholdType(): ImageOptions;
13-
threshold(thresholdType: any): 10 | 0.01;
13+
threshold(thresholdType: any): 0.01 | 10;
1414
delta(): number;
1515
static cropImageDefault(_args: INsCapabilities): {
1616
x: number;

Diff for: lib/interfaces/ns-capabilities.d.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import { IDevice } from "mobile-devices-controller";
22
export declare enum AutomationName {
33
UiAutomator2 = "UIAutomator2",
44
Appium = "Appium",
5-
XCUITest = "XCUITest"
5+
XCUITest = "XCUITest",
66
}
77
export interface INsCapabilities {
88
projectDir: string;

Diff for: lib/ns-capabilities.ts

+4-4
Original file line numberDiff line numberDiff line change
@@ -93,12 +93,12 @@ export class NsCapabilities implements INsCapabilities {
9393

9494
private setAutomationName() {
9595
if (this.appiumCaps["automationName"]) {
96-
switch (this.appiumCaps["automationName"]) {
97-
case AutomationName.UiAutomator2.toString():
96+
switch (this.appiumCaps["automationName"].toLowerCase()) {
97+
case AutomationName.UiAutomator2.toString().toLowerCase():
9898
this._automationName = AutomationName.UiAutomator2; break;
99-
case AutomationName.Appium.toString():
99+
case AutomationName.Appium.toString().toLowerCase():
100100
this._automationName = AutomationName.Appium; break;
101-
case AutomationName.XCUITest.toString():
101+
case AutomationName.XCUITest.toString().toLowerCase():
102102
this._automationName = AutomationName.XCUITest; break;
103103
}
104104
} else {

Diff for: lib/utils.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -302,8 +302,8 @@ function getAppName(args: INsCapabilities) {
302302
}
303303

304304
export function getAppPath(caps: INsCapabilities) {
305-
let basePath = caps.appPath;
306-
if (isFile(basePath)) {
305+
let basePath = caps.appiumCaps.app || caps.appPath;
306+
if (fs.existsSync(basePath) && ((basePath.endsWith(".apk") || basePath.endsWith(".app") || basePath.endsWith(".ipa")))) {
307307
return basePath;
308308
}
309309

Diff for: package.json

+49-51
Original file line numberDiff line numberDiff line change
@@ -1,53 +1,51 @@
11
{
2-
"name": "nativescript-dev-appium",
3-
"version": "3.3.0",
4-
"description": "A NativeScript plugin to help integrate and run Appium tests",
5-
"author": "NativeScript",
6-
"license": "MIT",
7-
"main": "./index.js",
8-
"directories": {
9-
"lib": "./lib"
10-
},
11-
"repository": {
12-
"type": "git",
13-
"url": "https://github.com/NativeScript/nativescript-dev-appium.git"
14-
},
15-
"keywords": [
16-
"nativescript",
17-
"appium",
18-
"test"
19-
],
20-
"maintainers": [
21-
{
22-
"name": "SvetoslavTsenov",
23-
"email": "[email protected]"
2+
"name": "nativescript-dev-appium",
3+
"version": "3.3.0",
4+
"description": "A NativeScript plugin to help integrate and run Appium tests",
5+
"author": "NativeScript",
6+
"license": "MIT",
7+
"main": "./index.js",
8+
"directories": {
9+
"lib": "./lib"
10+
},
11+
"repository": {
12+
"type": "git",
13+
"url": "https://github.com/NativeScript/nativescript-dev-appium.git"
14+
},
15+
"keywords": [
16+
"nativescript",
17+
"appium",
18+
"test"
19+
],
20+
"maintainers": [{
21+
"name": "SvetoslavTsenov",
22+
"email": "[email protected]"
23+
}],
24+
"dependencies": {
25+
"app-root-path": "~2.0.1",
26+
"blink-diff": "~1.0.13",
27+
"chai": "~4.1.0",
28+
"chai-as-promised": "~7.1.0",
29+
"frame-comparer": "^1.0.3",
30+
"glob": "7.1.0",
31+
"mobile-devices-controller": "~2.5.0",
32+
"mocha": "~5.1.0",
33+
"mocha-junit-reporter": "~1.17.0",
34+
"mocha-multi": "~1.0.0",
35+
"wd": "~1.8.0",
36+
"webdriverio": "~4.12.0",
37+
"yargs": "~8.0.2"
38+
},
39+
"devDependencies": {
40+
"@types/chai": "^4.1.3",
41+
"@types/mocha": "^5.2.0",
42+
"@types/node": "^8.10.13",
43+
"@types/webdriverio": "~4.8.4",
44+
"typescript": "^2.8.0"
45+
},
46+
"scripts": {
47+
"postinstall": "node ./postinstall.js",
48+
"prepare": "tsc",
49+
"watch": "tsc --watch"
2450
}
25-
],
26-
"dependencies": {
27-
"app-root-path": "^2.0.1",
28-
"blink-diff": "^1.0.13",
29-
"chai": "^4.1.0",
30-
"chai-as-promised": "^7.1.0",
31-
"frame-comparer": "^1.0.3",
32-
"glob": "7.1.0",
33-
"mobile-devices-controller": "^2.5.0",
34-
"mocha": "^5.1.0",
35-
"mocha-junit-reporter": "^1.17.0",
36-
"mocha-multi": "^1.0.0",
37-
"wd": "^1.6.0",
38-
"webdriverio": "^4.12.0",
39-
"yargs": "^8.0.2"
40-
},
41-
"devDependencies": {
42-
"@types/chai": "^4.1.3",
43-
"@types/mocha": "^5.2.0",
44-
"@types/node": "^8.10.13",
45-
"@types/webdriverio": "~4.8.4",
46-
"typescript": "^2.8.0"
47-
},
48-
"scripts": {
49-
"postinstall": "node ./postinstall.js",
50-
"prepare": "tsc",
51-
"watch": "tsc --watch"
52-
}
53-
}
51+
}

Diff for: postinstall.js

+4-4
Original file line numberDiff line numberDiff line change
@@ -72,8 +72,8 @@ function getDevDependencies() {
7272
// There is need to explicitly install them to the project.
7373
const typeScriptDevDependencies = [
7474
//{ name: "tslib", version: "^1.7.1" },
75-
{ name: "@types/chai", version: "^4.0.2" },
76-
{ name: "@types/mocha", version: "^2.2.41" },
75+
{ name: "@types/chai", version: "~4.1.3" },
76+
{ name: "@types/mocha", version: "~5.2.1" },
7777
{ name: "@types/node", version: "^7.0.5" },
7878
];
7979

@@ -100,7 +100,7 @@ function configureDevDependencies(packageJson) {
100100
if (devDependenciesToInstall.length) {
101101
console.info("Installing new devDependencies ...");
102102
// Execute `npm install` after everything else
103-
setTimeout(function () {
103+
setTimeout(function() {
104104
executeNpmInstall(appRootPath);
105105
}, 300);
106106
}
@@ -136,4 +136,4 @@ if (basename(appRootPath) !== "nativescript-dev-appium") {
136136
console.info("JavaScript project - not adding sample config and test ...");
137137
}
138138
}
139-
}
139+
}

0 commit comments

Comments
 (0)