Skip to content

Commit c158b00

Browse files
appium#105 & appium#108 IOSDriver. AppiumDriver. InteractsWithApps.
1 parent 59c1486 commit c158b00

File tree

4 files changed

+147
-101
lines changed

4 files changed

+147
-101
lines changed

src/main/java/io/appium/java_client/AppiumDriver.java

Lines changed: 15 additions & 97 deletions
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@
8686
public class AppiumDriver extends RemoteWebDriver implements MobileDriver,
8787
ContextAware, Rotatable, FindsByIosUIAutomation,
8888
FindsByAndroidUIAutomator, FindsByAccessibilityId, LocationContext,
89-
DeviceActionShortcuts, TouchShortcuts, InteractsWithFiles {
89+
DeviceActionShortcuts, TouchShortcuts, InteractsWithFiles, InteractsWithApps {
9090

9191
private final static ErrorHandler errorHandler = new ErrorHandler(
9292
new ErrorCodesMobile(), true);
@@ -231,8 +231,9 @@ public ExecuteMethod getExecuteMethod() {
231231
}
232232

233233
/**
234-
* Reset the currently running app for this session
234+
* @see InteractsWithApps#resetApp()
235235
*/
236+
@Override
236237
public void resetApp() {
237238
execute(MobileCommand.RESET);
238239
}
@@ -293,48 +294,9 @@ public void hideKeyboard() {
293294
}
294295

295296
/**
296-
* Hides the keyboard if it is showing. Available strategies are PRESS_KEY
297-
* and TAP_OUTSIDE. One taps outside the keyboard, the other presses a key
298-
* of your choosing (probably the 'Done' key). Hiding the keyboard often
299-
* depends on the way an app is implemented, no single strategy always
300-
* works.
301-
*
302-
* These parameters are only for iOS, and ignored by Android.
303-
*
304-
* @param strategy
305-
* HideKeyboardStrategy
306-
* @param keyName
307-
* a String, representing the text displayed on the button of the
308-
* keyboard you want to press. For example: "Done"
309-
*/
310-
//Should be moved to the subclass
311-
public void hideKeyboard(String strategy, String keyName) {
312-
String[] parameters = new String[] { "strategy", "key" };
313-
Object[] values = new Object[] { strategy, keyName };
314-
execute(HIDE_KEYBOARD, getCommandImmutableMap(parameters, values));
315-
}
316-
317-
/**
318-
* Hides the keyboard by pressing the button specified by keyName if it is
319-
* showing. This is an iOS only command.
320-
*
321-
* @param keyName
322-
* The button pressed by the mobile driver to attempt hiding the
323-
* keyboard
324-
*/
325-
//Should be moved to the subclass
326-
public void hideKeyboard(String keyName) {
327-
execute(HIDE_KEYBOARD, ImmutableMap.of("keyName", keyName));
328-
}
329-
330-
/**
331-
* Runs the current app as a background app for the number of seconds
332-
* requested. This is a synchronous method, it returns after the back has
333-
* been returned to the foreground.
334-
*
335-
* @param seconds
336-
* Number of seconds to run App in background
297+
* @see InteractsWithApps#runAppInBackground(int)
337298
*/
299+
@Override
338300
public void runAppInBackground(int seconds) {
339301
execute(RUN_APP_IN_BACKGROUND, ImmutableMap.of("seconds", seconds));
340302
}
@@ -487,31 +449,9 @@ public void zoom(int x, int y) {
487449
}
488450

489451
/**
490-
* In iOS apps, named TextFields have the same accessibility Id as their
491-
* containing TableElement. This is a convenience method for getting the
492-
* named TextField, rather than its containing element.
493-
*
494-
* @param name
495-
* accessiblity id of TextField
496-
* @return The textfield with the given accessibility id
497-
*/
498-
//Should be moved to the subclass
499-
public WebElement getNamedTextField(String name) {
500-
MobileElement element = (MobileElement) findElementByAccessibilityId(name);
501-
if (element.getTagName() != "TextField") {
502-
return element.findElementByAccessibilityId(name);
503-
}
504-
505-
return element;
506-
}
507-
508-
/**
509-
* Checks if an app is installed on the device
510-
*
511-
* @param bundleId
512-
* bundleId of the app
513-
* @return True if app is installed, false otherwise
452+
* @see InteractsWithApps#isAppInstalled(String)
514453
*/
454+
@Override
515455
public boolean isAppInstalled(String bundleId) {
516456
Response response = execute(IS_APP_INSTALLED,
517457
ImmutableMap.of("bundleId", bundleId));
@@ -520,59 +460,37 @@ public boolean isAppInstalled(String bundleId) {
520460
}
521461

522462
/**
523-
* Install an app on the mobile device
524-
*
525-
* @param appPath
526-
* path to app to install
463+
* @see InteractsWithApps#installApp(String)
527464
*/
465+
@Override
528466
public void installApp(String appPath) {
529467
execute(INSTALL_APP, ImmutableMap.of("appPath", appPath));
530468
}
531469

532470
/**
533-
* Remove the specified app from the device (uninstall)
534-
*
535-
* @param bundleId
536-
* the bunble identifier (or app id) of the app to remove
471+
* @see InteractsWithApps#removeApp(String)
537472
*/
473+
@Override
538474
public void removeApp(String bundleId) {
539475
execute(REMOVE_APP, ImmutableMap.of("bundleId", bundleId));
540476
}
541477

542478
/**
543-
* Launch the app which was provided in the capabilities at session creation
479+
* @see InteractsWithApps#launchApp()
544480
*/
481+
@Override
545482
public void launchApp() {
546483
execute(LAUNCH_APP);
547484
}
548485

549486
/**
550-
* Close the app which was provided in the capabilities at session creation
487+
* @see InteractsWithApps#closeApp()
551488
*/
489+
@Override
552490
public void closeApp() {
553491
execute(CLOSE_APP);
554492
}
555493

556-
/**
557-
* Lock the device (bring it to the lock screen) for a given number of
558-
* seconds
559-
*
560-
* @param seconds
561-
* number of seconds to lock the screen for
562-
*/
563-
//Should be moved to the subclass (supposed to be in iOS)
564-
public void lockScreen(int seconds) {
565-
execute(LOCK, ImmutableMap.of("seconds", seconds));
566-
}
567-
568-
/**
569-
* Simulate shaking the device This is an iOS-only method
570-
*/
571-
//Should be moved to the subclass
572-
public void shake() {
573-
execute(SHAKE);
574-
}
575-
576494
/**
577495
* Get settings stored for this test session It's probably better to use a
578496
* convenience function, rather than use this function directly. Try finding
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
package io.appium.java_client;
2+
3+
public interface InteractsWithApps {
4+
/**
5+
* Launch the app which was provided in the capabilities at session creation
6+
*/
7+
public void launchApp();
8+
9+
/**
10+
* Install an app on the mobile device
11+
*
12+
* @param appPath
13+
* path to app to install
14+
*/
15+
public void installApp(String appPath);
16+
17+
/**
18+
* Checks if an app is installed on the device
19+
*
20+
* @param bundleId
21+
* bundleId of the app
22+
* @return True if app is installed, false otherwise
23+
*/
24+
public boolean isAppInstalled(String bundleId);
25+
26+
/**
27+
* Reset the currently running app for this session
28+
*/
29+
public void resetApp();
30+
31+
/**
32+
* Runs the current app as a background app for the number of seconds
33+
* requested. This is a synchronous method, it returns after the back has
34+
* been returned to the foreground.
35+
*
36+
* @param seconds
37+
* Number of seconds to run App in background
38+
*/
39+
public void runAppInBackground(int seconds);
40+
41+
/**
42+
* Remove the specified app from the device (uninstall)
43+
*
44+
* @param bundleId
45+
* the bunble identifier (or app id) of the app to remove
46+
*/
47+
public void removeApp(String bundleId);
48+
49+
/**
50+
* Close the app which was provided in the capabilities at session creation
51+
*/
52+
public void closeApp();
53+
54+
}
Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,74 @@
1+
package io.appium.java_client.ios;
2+
3+
import static io.appium.java_client.MobileCommand.HIDE_KEYBOARD;
4+
import static io.appium.java_client.MobileCommand.LOCK;
5+
import static io.appium.java_client.MobileCommand.SHAKE;
6+
7+
import java.net.URL;
8+
9+
import org.openqa.selenium.Capabilities;
10+
import org.openqa.selenium.WebElement;
11+
12+
import com.google.common.collect.ImmutableMap;
13+
14+
import io.appium.java_client.AppiumDriver;
15+
import io.appium.java_client.MobileElement;
16+
import io.appium.java_client.remote.MobilePlatform;
17+
18+
public class IOSDriver extends AppiumDriver implements IOSDeviceActionShortcuts, GetsNamedTextField{
19+
private static final String IOS_PLATFORM = MobilePlatform.IOS;
20+
21+
public IOSDriver(URL remoteAddress, Capabilities desiredCapabilities) {
22+
super(remoteAddress, substituteMobilePlatform(desiredCapabilities,
23+
IOS_PLATFORM));
24+
}
25+
26+
/**
27+
* @see IOSDeviceActionShortcuts#hideKeyboard(String, String)
28+
*/
29+
@Override
30+
public void hideKeyboard(String strategy, String keyName) {
31+
String[] parameters = new String[] { "strategy", "key" };
32+
Object[] values = new Object[] { strategy, keyName };
33+
execute(HIDE_KEYBOARD, getCommandImmutableMap(parameters, values));
34+
}
35+
36+
/**
37+
* @see IOSDeviceActionShortcuts#hideKeyboard(String)
38+
*/
39+
@Override
40+
public void hideKeyboard(String keyName) {
41+
execute(HIDE_KEYBOARD, ImmutableMap.of("keyName", keyName));
42+
}
43+
44+
/**
45+
* @see IOSDeviceActionShortcuts#shake()
46+
*/
47+
@Override
48+
public void shake() {
49+
execute(SHAKE);
50+
}
51+
52+
/**
53+
* @see GetsNamedTextField#getNamedTextField(String)
54+
*/
55+
@Override
56+
public WebElement getNamedTextField(String name) {
57+
MobileElement element = (MobileElement) findElementByAccessibilityId(name);
58+
if (element.getTagName() != "TextField") {
59+
return element.findElementByAccessibilityId(name);
60+
}
61+
return element;
62+
}
63+
64+
/**
65+
* Lock the device (bring it to the lock screen) for a given number of
66+
* seconds
67+
*
68+
* @param seconds
69+
* number of seconds to lock the screen for
70+
*/
71+
public void lockScreen(int seconds) {
72+
execute(LOCK, ImmutableMap.of("seconds", seconds));
73+
}
74+
}

src/test/java/io/appium/java_client/MobileDriverIOSTest.java

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -17,9 +17,9 @@
1717

1818
package io.appium.java_client;
1919

20+
import io.appium.java_client.ios.IOSDriver;
2021
import io.appium.java_client.remote.HideKeyboardStrategy;
2122
import io.appium.java_client.remote.MobileCapabilityType;
22-
import io.appium.java_client.remote.MobilePlatform;
2323

2424
import org.junit.After;
2525
import org.junit.Before;
@@ -38,7 +38,7 @@
3838
*/
3939
public class MobileDriverIOSTest {
4040

41-
private AppiumDriver driver;
41+
private IOSDriver driver;
4242

4343
@Before
4444
public void setup() throws Exception {
@@ -47,10 +47,10 @@ public void setup() throws Exception {
4747
DesiredCapabilities capabilities = new DesiredCapabilities();
4848
capabilities.setCapability(MobileCapabilityType.BROWSER_NAME, "");
4949
capabilities.setCapability(MobileCapabilityType.PLATFORM_VERSION, "7.1");
50-
capabilities.setCapability(MobileCapabilityType.PLATFORM_NAME, MobilePlatform.IOS);
50+
//capabilities.setCapability(MobileCapabilityType.PLATFORM_NAME, MobilePlatform.IOS);
5151
capabilities.setCapability(MobileCapabilityType.DEVICE_NAME, "iPhone Simulator");
5252
capabilities.setCapability(MobileCapabilityType.APP, app.getAbsolutePath());
53-
driver = new AppiumDriver(new URL("http://127.0.0.1:4723/wd/hub"), capabilities);
53+
driver = new IOSDriver(new URL("http://127.0.0.1:4723/wd/hub"), capabilities);
5454
}
5555

5656
@After

0 commit comments

Comments
 (0)