Cross Platform Appium Tests: How To

Preview:

DESCRIPTION

This is a presentation about mobile apps testing using Appium. The presentation conrtains tips on comprehensive testing of apps written for various devices and platforms. Presentation by Yaroslav Pernerovskyy (Lead Test Engineer, GlobalLogic, Kyiv), delivered at UA Mobile, November 22, 2014. More details - http://uamobile.org

Citation preview

Cross platform Appium tests

How To

Who?

Yaroslav Pernerovskyy

• Test Automation Lead in Global Logic

y.pernerovskyy

y.pernerovskyy@globallogic.com

www.linkedin.com/pub/yaroslav-pernerovsky/1/9b5/55

What?

Why?

• Web application

• Selenium based test framework (Java)

• iOS and Android clients

• Reuse framework features for mobile

• Open Source (Free of charge)

• Easy setup and configuration

• Scalable and flexible

Appium Rules

• Test the same app you submit to the marketplace

• Write your tests in any language, using any framework

• Use a standard automation specification and API

• Build a large and thriving open-source community effort

http://appium.io/slate/en/master/?ruby#appium-philosophy

iOSAndroid

Firefox OSTest Script

JSON Wire protocol

How it works

Native automation instruments

Remote Web Driver

node.js

UiAutomator

Selendroid

Instruments

Marionette

Features

• Native automation instruments – Android: UiAutomator (4.2), Selendroid (2.3)

– iOS: UIAutomation

– Firefox OS: Marionette

• Emulators/simulators and real devices

• Web Driver API

• Selenium Grid

• Ruby, Python, Java, JavaScript, PHP, C#...

• Documentation

• http://appium.io/

Install

• npm install -g appium

• Appium.dmg

• Appium.exe• https://bitbucket.org/appium/appium.app/downloads/

Appium GUI

Command line

appium -a 192.168.10.11 -p 4723

--device-name "iPad Simulator" --force-ipad

--orientation LANDSCAPE --pre-launch

--app /products/testapp.app

--nodeconfig /appium/nodeconfig.json

nodeconfig.json

Issues

• Stability issues

• Actions depends on platform

• Problems with accessing some elements

• iOS specific issues

– Single app test

– Hardware keys support

– One emulator instance

– xpath

Application types

Mobile Browser

Device APIs

Native App

0101010101010101010101010100010011110101001001110010100

00001

<html><body>

<input type="button" value=" + " onclick="plus()"><script language="JavaScript">unction plus()

{rezultat.value=znah_1.value-(-1)*znah_2.value;}

</body></html>

Device APIs

Native Container

<html><body>

<input type="button" value=" + " onclick="plus()"><script language="JavaScript">unction plus()

{rezultat.value=znah_1.value

Web apps

• Similar layouts

• Same locators

• Absolutely the same tests can be executed

• Not require additional efforts

Native apps

• Different layout

• Different locators

• Platform specific UI elements

• Test cases should be specially designed

• Require additional efforts

Test environment

SVN

Jenkins

Web Firefox

Web Chrome

Mobile iOS

Mobile Android

……

Selenium Grid

Chrome, FF

IE

Safari

adb

iPad simulator

iPhone simulator

Nexus 7

Nexus 5

Ap

piu

mreports

Sele

niu

m

Test framework overview

class Drivers

class Bindings

Page ObjectsPage Objects

Page ObjectsPage Objects

TestsTests

TestsTests

Global ConfigurationTest data

loggers/db tools/service tools etc.

Tests

• Test steps should be similar for both platforms

@Test (dataProvider = "Logins")

@Features ("Login")

@Stories ("User should not be able to login with incorrect credentials")

public void verify_Incorrect_Login(Map<String, String> testData){

loginScreen.verifyScreenLoaded();

loginScreen.submitLogin(testData.get("User"),testData.get("Password"));

loginScreen.verifyAndCloseErrorMessage(testData.get("Message"));

loginScreen.verifyScreenLoaded();

}

Page Objects

• Do not hardcode locators in Page objects

• Store it in external object

• Implement platform specific code

• Create bindings for platform specific actions

Page Object

public class LoginScreen extends Bindings {

public LoginScreen(Instance instance) {super(instance);initLocators();

}

private static String LoginScreenUserField;private static String LoginScreenPasswordField;private static String LoginScreenSubmitLoginBtn;private static String LoginScreenErrorMsg;private static String LoginScreenErrorMsgCloseBtn;

private void initLocators() {

LoginScreenUserField = locators.get("LoginScreenUserField");LoginScreenPasswordField = locators.get("LoginScreenPasswordField");LoginScreenSubmitLoginButton = locators.get("LoginScreenSubmitLoginButton");LoginScreenErrorMsg = locators.get("LoginScreenErrorMsg");LoginScreenErrorMsgCloseBtn = locators.get("LoginScreenErrorMsgCloseBtn");

}... ...

Page Object

@Steppublic void submitLogin(String login, String pass) {

typeKeys(LoginScreenUserField, login);typeKeys(LoginScreenPasswordField, pass);tap(LoginScreenSubmitLoginBtn);

}

@Steppublic void verifyAndCloseErrorMessage(String Message) {

verifyElementPresent(LoginScreenErrorMsg);assetEqual(getText(LoginScreenErrorMsg),Message);

if (instance.getPlatform().equals("ios"))tap(LoginScreenErrorMsgCloseBtn);elseclickBackBtn();

}

Locators

<?xml version='1.0' encoding='UTF-8'?><dataset><LOCATORNAME="LoginScreenUserField" ANDROID="id=com.example.myapp:id/txtUser"IOS="xpath=//window[1]/textfield[1]"/>

<LOCATORNAME="LoginScreenPasswordField" ANDROID="id=com.example.myapp:id/txtPassword"IOS="xpath=//window[1]/textfield[2]"/>

<LOCATORNAME="LoginScreenSubmitLoginButton" ANDROID="name=Login " IOS="name=Login"/>

<LOCATORNAME="LoginScreenErrorMsg" ANDROID="id=com.example.myapp:id/errText" IOS="xpath=//*/UIAPopover[contains(@name,'ErrorText')]"/>

<LOCATORNAME="LoginScreenErrorMsgCloseBtn" IOS="name=Ok"/>

...

...

Get locators for Android

Get locators for iOS

Summary

• WebDriver concept

• Cross platform

• Open Source

• Easy integration into Selenium based frameworks

• Supported by community

• One test for two platforms

KEEPCALM

AND

ASKQUESTIONS

Recommended