Merge pull request #2526 from bootstraponline/always_setCompressedLayoutHeirarchy

Always setCompressedLayoutHeirarchy
This commit is contained in:
Jonathan Lipps
2014-05-12 13:03:33 -07:00
11 changed files with 54 additions and 89 deletions

View File

@@ -21,7 +21,6 @@
|`app-package`| 你想运行的Android应用的包名|比如`com.example.android.myApp`, `com.android.settings`|
|`app-wait-activity`| 你想要等待启动的Android Activity名称|比如`SplashActivity`|
|`device-ready-timeout`| 设置一个模拟器或真机准备就绪的时间|比如`5`|
|``compressXml``| 参考[setCompressedLayoutHeirarchy(true)](http://developer.android.com/tools/help/uiautomator/UiDevice.html#setCompressedLayoutHeirarchy(boolean\))| `true`|
### iOS特有

View File

@@ -24,7 +24,6 @@
|`appWaitActivity`| Activity name for the Android activity you want to wait for|`SplashActivity`|
|`appWaitPackage`| Java package of the Android app you want to wait for|`com.example.android.myApp`, `com.android.settings`|
|`deviceReadyTimeout`| Timeout in seconds while waiting for device to become ready|`5`|
|`compressXml`| [setCompressedLayoutHeirarchy(true)](http://developer.android.com/tools/help/uiautomator/UiDevice.html#setCompressedLayoutHeirarchy%28boolean%29)| `true`|
|`androidCoverage`| Fully qualified instrumentation class. Passed to -w in adb shell am instrument -e coverage true -w | `com.my.Pkg/com.my.Pkg.instrumentation.MyInstrumentation`|
|`enablePerformanceLogging`| (Chrome and webview only) Enable Chromedriver's performance logging (default `false`)| `true`, `false`|
|`avdLaunchTimeout`| How long to wait in milliseconds for an avd to launch and connect to ADB (default `120000`)| `300000`|

View File

@@ -30,7 +30,6 @@ var ADB = function (opts) {
if (typeof opts.sdkRoot === "undefined") {
opts.sdkRoot = process.env.ANDROID_HOME || '';
}
this.compressXml = opts.compressXml;
this.sdkRoot = opts.sdkRoot;
this.udid = opts.udid;
this.appDeviceReadyTimeout = opts.appDeviceReadyTimeout;

View File

@@ -75,11 +75,7 @@ androidCommon.setAndroidArgs = function () {
this.setArgFromCap("androidWaitPackage", "appWaitPackage");
this.setArgFromCap("androidWaitActivity", "appWaitActivity");
this.setArgFromCap("androidDeviceReadyTimeout", "deviceReadyTimeout");
// must be enabled by default or XPath will be broken on API >= 18
// compressXml is not available on API <= 17
this.args.compressXml = true;
this.setArgFromCap("compressXml", "compressXml");
this.setArgFromCap("androidCoverage", "androidCoverage");
this.args.systemPort = this.args.bootstrapPort;
this.args.appPackage = this.args.androidPackage;
this.args.appActivity = this.args.androidActivity;

View File

@@ -361,8 +361,7 @@ androidController.getPageSource = function (cb) {
async.series(
[
function (cb) {
var dumpCommand = this.args.compressXml ? "dumpWindowHierarchyCompressed" : "dumpWindowHierarchy";
this.proxy([dumpCommand], cb);
this.proxy(["dumpWindowHierarchy"], cb);
}.bind(this),
function (cb) {
var cmd = this.adb.adbCmd + ' pull ' + onDeviceXmlPath + ' "' + xmlFile + '"';

View File

@@ -5,7 +5,6 @@ import io.appium.android.bootstrap.handler.Clear;
import io.appium.android.bootstrap.handler.Click;
import io.appium.android.bootstrap.handler.Drag;
import io.appium.android.bootstrap.handler.DumpWindowHierarchy;
import io.appium.android.bootstrap.handler.DumpWindowHierarchyCompressed;
import io.appium.android.bootstrap.handler.Find;
import io.appium.android.bootstrap.handler.Flick;
import io.appium.android.bootstrap.handler.GetAttribute;
@@ -69,11 +68,7 @@ class AndroidCommandExecutor {
map.put("getSize", new GetSize());
map.put("wake", new Wake());
map.put("pressBack", new PressBack());
final DumpWindowHierarchy dumpWindowHierarchy = new DumpWindowHierarchy();
DumpWindowHierarchy.instance = dumpWindowHierarchy;
map.put("dumpWindowHierarchy", dumpWindowHierarchy);
map.put("dumpWindowHierarchyCompressed",
new DumpWindowHierarchyCompressed());
map.put("dumpWindowHierarchy", new DumpWindowHierarchy());
map.put("pressKeyCode", new PressKeyCode());
map.put("takeScreenshot", new TakeScreenshot());
map.put("getStrings", new GetStrings());

View File

@@ -4,6 +4,7 @@ import io.appium.android.bootstrap.exceptions.AndroidCommandException;
import io.appium.android.bootstrap.exceptions.CommandTypeException;
import io.appium.android.bootstrap.exceptions.SocketServerException;
import io.appium.android.bootstrap.handler.Find;
import io.appium.android.bootstrap.utils.NotImportantViews;
import io.appium.android.bootstrap.utils.TheWatchers;
import java.io.BufferedReader;
@@ -46,6 +47,7 @@ class SocketServer {
* @throws SocketServerException
*/
public SocketServer(final int port) throws SocketServerException {
NotImportantViews.discard(true); // must be set for API 18+
keepListening = true;
executor = new AndroidCommandExecutor();
try {

View File

@@ -3,11 +3,9 @@ package io.appium.android.bootstrap.handler;
import io.appium.android.bootstrap.AndroidCommand;
import io.appium.android.bootstrap.AndroidCommandResult;
import io.appium.android.bootstrap.CommandHandler;
import io.appium.android.bootstrap.Logger;
import java.io.File;
import android.os.Build;
import android.os.Environment;
import android.os.SystemClock;
@@ -20,54 +18,44 @@ import com.android.uiautomator.core.UiDevice;
* /library/core-src/com/android/uiautomator/core/UiDevice.java
*/
public class DumpWindowHierarchy extends CommandHandler {
public static DumpWindowHierarchy instance = null;
// Note that
// "new File(new File(Environment.getDataDirectory(), "local/tmp"), fileName)"
// is directly from the UiDevice.java source code.
private static final File dumpFolder = new File(Environment.getDataDirectory(), "local/tmp");
private static final String dumpFileName = "dump.xml";
private static final File dumpFile = new File(dumpFolder, dumpFileName);
// Note that
// "new File(new File(Environment.getDataDirectory(), "local/tmp"), fileName)"
// is directly from the UiDevice.java source code.
private static final File dumpFolder = new File(Environment.getDataDirectory(), "local/tmp");
private static final String dumpFileName = "dump.xml";
private static final File dumpFile = new File(dumpFolder, dumpFileName);
private static boolean compressed = false;
/*
* @param command The {@link AndroidCommand} used for this handler.
*
* @return {@link AndroidCommandResult}
*
* @throws JSONException
*
* @see io.appium.android.bootstrap.CommandHandler#execute(io.appium.android.
* bootstrap.AndroidCommand)
*/
@Override
public AndroidCommandResult execute(final AndroidCommand command) {
dumpFolder.mkdirs();
public static boolean isCompressed() {
return compressed;
if (dumpFile.exists()) {
dumpFile.delete();
}
public static void setCompressed(final boolean compress) {
compressed = compress;
}
/*
* @param command The {@link AndroidCommand} used for this handler.
*
* @return {@link AndroidCommandResult}
*
* @throws JSONException
*
* @see io.appium.android.bootstrap.CommandHandler#execute(io.appium.android.
* bootstrap.AndroidCommand)
*/
@Override
public AndroidCommandResult execute(final AndroidCommand command) {
dumpFolder.mkdirs();
if (dumpFile.exists()) {
dumpFile.delete();
}
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
Logger.debug("dumpWindowHierarchy. Compressed? " + compressed);
UiDevice.getInstance().setCompressedLayoutHeirarchy(compressed);
}
UiDevice.getInstance().dumpWindowHierarchy(dumpFileName);
if (!dumpFile.exists()) {
for (int count = 0; count < 30; count++) {
SystemClock.sleep(1000);
UiDevice.getInstance().dumpWindowHierarchy(dumpFileName);
if (!dumpFile.exists()) {
SystemClock.sleep(1000);
UiDevice.getInstance().dumpWindowHierarchy(dumpFileName);
if (dumpFile.exists()) {
break;
}
return getSuccessResult(dumpFile.exists());
}
}
return getSuccessResult(dumpFile.exists());
}
}

View File

@@ -1,28 +0,0 @@
package io.appium.android.bootstrap.handler;
import io.appium.android.bootstrap.AndroidCommand;
import io.appium.android.bootstrap.AndroidCommandResult;
import io.appium.android.bootstrap.CommandHandler;
public class DumpWindowHierarchyCompressed extends CommandHandler {
private static void enableCompression() {
DumpWindowHierarchy.setCompressed(true);
}
/*
* @param command The {@link AndroidCommand} used for this handler.
*
* @return {@link AndroidCommandResult}
*
* @throws JSONException
*
* @see io.appium.android.bootstrap.CommandHandler#execute(io.appium.android.
* bootstrap.AndroidCommand)
*/
@Override
public AndroidCommandResult execute(final AndroidCommand command) {
enableCompression();
return DumpWindowHierarchy.instance.execute(command);
}
}

View File

@@ -0,0 +1,17 @@
package io.appium.android.bootstrap.utils;
import android.os.Build;
import com.android.uiautomator.core.UiDevice;
public abstract class NotImportantViews {
// setCompressedLayoutHeirarchy doesn't exist on API <= 17
// http://developer.android.com/reference/android/accessibilityservice/AccessibilityServiceInfo.html#FLAG_INCLUDE_NOT_IMPORTANT_VIEWS
private static boolean canDiscard = Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2;
public static void discard(boolean discard) {
if (canDiscard) {
UiDevice.getInstance().setCompressedLayoutHeirarchy(discard);
}
}
}

View File

@@ -130,7 +130,6 @@ describe("apidemo - find elements -", function () {
var f = "android.widget.FrameLayout";
var l = alv;
var t = atv;
var v = "android.view.View";
it('should find element by type', function (done) {
driver
.elementByXPath('//' + t).text()
@@ -158,7 +157,7 @@ describe("apidemo - find elements -", function () {
});
it('should find element by xpath index and child', function (done) {
driver
.elementByXPath("//" + f + "[1]/" + v + "[1]/" + f + "[2]/" + l + "[1]/" + t + "[3]").text()
.elementByXPath("//" + f + "[1]/" + l + "[1]/" + t + "[3]").text()
.should.become("App")
.nodeify(done);
});