我正在从uiautomator迁移到uiautomator 2.0。我在使用旧的UiWatcher时遇到了一些麻烦。

我正在使用此功能设置电池电量并检查应用程序是否打印正确的电量。这是代码。

private void setLevel(int oldL, int newL) throws UiObjectNotFoundException {
    UiWatcher okBatteryDialogWatcher = new UiWatcher() {
        @Override
        public boolean checkForCondition() {
            UiObject okCancelDialog = new UiObject(new UiSelector().textContains("Connect charger"));
            if(okCancelDialog != null){
                UiObject okButton = new UiObject(new UiSelector().className(Button.class.getName()).text("OK"));
                okButton.click();
                return device.waitForWindowUpdate("",10000);
            }
            return false;
        }
    };

    getUiDevice().registerWatcher("Battery dialog watcher", okBatteryDialogWatcher);
    getUiDevice().runWatchers();

    UiObject batteryLevel = new UiObject(new UiSelector().text(oldL + " %"));
    assertTrue("Battery level not found", batteryLevel.exists());

    BatteryDelegate.getInstance().setBatteryLevel(newL);

    batteryLevel = new UiObject(new UiSelector().text(newL + " %"));
    assertTrue("Battery level not found", batteryLevel.exists());
}


此代码可以正常工作。现在,我想对其进行更改以使用uiautomator 2.0提供的新功能。

private void setLevel(int oldL, int newL) {
    UiWatcher okBatteryDialogWatcher = new UiWatcher() {
            @Override
            public boolean checkForCondition() {
                UiObject2 okCancelDialog = device.findObject(By.textContains("Connect charger"));
                if(okCancelDialog != null){
                    UiObject2 okButton = device.findObject(By.clazz(Button.class.getName()).text("OK"));
                    okButton.click();
                    return device.waitForWindowUpdate("",10000);
                }
                return false;
            }
        };

    device.registerWatcher("Battery dialog watcher", okBatteryDialogWatcher);
    device.runWatchers();

    UiObject2 batteryLevel = device.findObject(By.text(oldL + " %"));
    assertTrue("Battery level not found", batteryLevel != null);

    BatteryDelegate.getInstance().setBatteryLevel(newL);

    Boolean b = batteryLevel.wait(Until.textEquals(newL + " %"), 10000);
    assertTrue("Battery level not found", b != null && b.booleanValue());
}


当我使用此代码将电池电量设置为5%(出现“电池电量低”对话框时),在Boolean b = batteryLevel.wait(Until.textEquals(newL + " %"), 10000);行上引发StaleObjectException

这是例外

android.support.test.uiautomator.StaleObjectException
at android.support.test.uiautomator.UiObject2.getAccessibilityNodeInfo(UiObject2.java:622)
at android.support.test.uiautomator.UiObject2.getText(UiObject2.java:287)
at android.support.test.uiautomator.Until$15.apply(Until.java:277)
at android.support.test.uiautomator.Until$15.apply(Until.java:274)
at android.support.test.uiautomator.WaitMixin.wait(WaitMixin.java:49)
at android.support.test.uiautomator.WaitMixin.wait(WaitMixin.java:34)
at android.support.test.uiautomator.UiObject2.wait(UiObject2.java:144)
at com.mycompany.myproject.demo.sensor.BatteryTestCase.setLevel(BatteryTestCase.java:89)
at com.mycompany.myproject.demo.sensor.BatteryTestCase.testUS2(BatteryTestCase.java:44)
...


我知道执行是由于对话框引起的,但是我的观察者变得毫无用处。我可以用一些技巧来处理此异常

....
Boolean b = null;
try {
    b = batteryLevel.wait(Until.textEquals(newL + " %"), 10000);
} catch (StaleObjectException e) {
    UiObject2 okCancelDialog = device.findObject(By.textContains("Connect charger"));
    if(okCancelDialog != null){
        UiObject2 okButton = device.findObject(By.clazz(Button.class.getName()).text("OK"));
        okButton.click();
        device.waitForWindowUpdate("",10000);
        b = batteryLevel.wait(Until.textEquals(newL + " %"), 10000);
    }
}
assertTrue("Battery level not found", b != null && b.booleanValue());
...


但这绝对不漂亮。有人吗


遇到同样的问题?
有一个好的工作解决方案?


谢谢

最佳答案

此问题应在UiAutomator 2.1.0中修复。监视程序仅在初始调用UiDevice.findObject(..)时被触发,并且不会阻止StaleObjectExceptions。

在最新版本中,还会在您收到StaleObjectException的情况下触发监视程序。如果您获取最新的Android支持存储库(rev.13)并更新构建文件以依赖uiautomator-v18:2.1+,则问题将消失。

关于android - UiAutomator 2.0的StaleObjectException,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/29149559/

10-10 08:22